65 lines
1.7 KiB
Go
65 lines
1.7 KiB
Go
|
|
package cassandra
|
|||
|
|
|
|||
|
|
import (
|
|||
|
|
"context"
|
|||
|
|
"testing"
|
|||
|
|
"time"
|
|||
|
|
|
|||
|
|
"github.com/stretchr/testify/assert"
|
|||
|
|
)
|
|||
|
|
|
|||
|
|
type LockTest struct {
|
|||
|
|
ID string `db:"id" partition_key:"true"`
|
|||
|
|
Holder string `db:"holder"`
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
func (l *LockTest) TableName() string { return "lock_test" }
|
|||
|
|
|
|||
|
|
func TestTryLockAndUnLock(t *testing.T) {
|
|||
|
|
ctx := context.Background()
|
|||
|
|
|
|||
|
|
assert.NoError(t, cassandraDBTest.EnsureTable(`
|
|||
|
|
CREATE TABLE IF NOT EXISTS my_keyspace.lock_test (
|
|||
|
|
id TEXT PRIMARY KEY,
|
|||
|
|
holder TEXT
|
|||
|
|
);
|
|||
|
|
`))
|
|||
|
|
|
|||
|
|
lockID := "lock-123"
|
|||
|
|
holder := "daniel"
|
|||
|
|
|
|||
|
|
lockDoc := &LockTest{ID: lockID, Holder: holder}
|
|||
|
|
|
|||
|
|
t.Run("acquire lock - success", func(t *testing.T) {
|
|||
|
|
err := cassandraDBTest.TryLock(ctx, lockDoc, "my_keyspace")
|
|||
|
|
assert.NoError(t, err, "TryLock 應該成功")
|
|||
|
|
})
|
|||
|
|
|
|||
|
|
t.Run("acquire lock again - fail", func(t *testing.T) {
|
|||
|
|
err := cassandraDBTest.TryLock(ctx, lockDoc, "my_keyspace")
|
|||
|
|
assert.Error(t, err, "重複上鎖應該失敗")
|
|||
|
|
})
|
|||
|
|
|
|||
|
|
t.Run("unlock", func(t *testing.T) {
|
|||
|
|
err := cassandraDBTest.UnLock(ctx, lockDoc, "my_keyspace")
|
|||
|
|
assert.NoError(t, err, "UnLock 應該成功")
|
|||
|
|
})
|
|||
|
|
|
|||
|
|
t.Run("lock with TTL", func(t *testing.T) {
|
|||
|
|
lockWithTTL := &LockTest{ID: "lock-ttl", Holder: "jack"}
|
|||
|
|
err := cassandraDBTest.TryLock(ctx, lockWithTTL, "my_keyspace", WithLockTTL(2*time.Second))
|
|||
|
|
assert.NoError(t, err)
|
|||
|
|
// 兩秒後嘗試再次上鎖應該成功(TTL 過期)
|
|||
|
|
time.Sleep(3 * time.Second)
|
|||
|
|
err = cassandraDBTest.TryLock(ctx, lockWithTTL, "my_keyspace")
|
|||
|
|
assert.NoError(t, err)
|
|||
|
|
_ = cassandraDBTest.UnLock(ctx, lockWithTTL, "my_keyspace")
|
|||
|
|
})
|
|||
|
|
|
|||
|
|
t.Run("unlock not exist", func(t *testing.T) {
|
|||
|
|
nonExist := &LockTest{ID: "not-exist", Holder: "nobody"}
|
|||
|
|
err := cassandraDBTest.UnLock(ctx, nonExist, "my_keyspace")
|
|||
|
|
assert.Error(t, err, "unlock 不存在的鎖應該失敗")
|
|||
|
|
})
|
|||
|
|
}
|