Add ETag operation to statestore conformance test (#716)
* Add ETag operation to statestore conformance test ETags are used to enable concurrency guarantees and are part of the statestore specification. Not all stores need to use them, however if the store chooses to, it should be part of the certification process. This commit adds a simple ETag test scenario that verifies the basic behaviors of ETags. https://github.com/dapr/components-contrib/issues/711 * Update tests.yml * Error on mongodb when etag does not match on delete. Co-authored-by: Artur Souza <artursouza.ms@outlook.com>
This commit is contained in:
parent
3ebe447759
commit
cb3c881d39
|
@ -209,11 +209,15 @@ func (m *MongoDB) deleteInternal(ctx context.Context, req *state.DeleteRequest)
|
|||
if req.ETag != nil {
|
||||
filter[etag] = *req.ETag
|
||||
}
|
||||
_, err := m.collection.DeleteOne(ctx, filter)
|
||||
result, err := m.collection.DeleteOne(ctx, filter)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if result.DeletedCount == 0 && req.ETag != nil {
|
||||
return errors.New("key or etag not found")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
|
|
|
@ -382,4 +382,75 @@ func ConformanceTests(t *testing.T, props map[string]string, statestore state.St
|
|||
}
|
||||
})
|
||||
}
|
||||
|
||||
// Supporting etags requires support for get, set, and delete so they are not checked individually
|
||||
if config.HasOperation("etag") {
|
||||
t.Run("etag", func(t *testing.T) {
|
||||
testKey := "etagTest"
|
||||
firstValue := []byte("testValue1")
|
||||
secondValue := []byte("testValue2")
|
||||
fakeEtag := "not-an-etag"
|
||||
|
||||
// Delete any potential object, it's important to start from a clean slate.
|
||||
err := statestore.Delete(&state.DeleteRequest{
|
||||
Key: testKey,
|
||||
})
|
||||
assert.Nil(t, err)
|
||||
|
||||
// Set an object.
|
||||
err = statestore.Set(&state.SetRequest{
|
||||
Key: testKey,
|
||||
Value: firstValue,
|
||||
})
|
||||
assert.Nil(t, err)
|
||||
|
||||
// Validate the set.
|
||||
res, err := statestore.Get(&state.GetRequest{
|
||||
Key: testKey,
|
||||
})
|
||||
|
||||
assert.Nil(t, err)
|
||||
assert.Equal(t, firstValue, res.Data)
|
||||
etag := res.ETag
|
||||
|
||||
// Try and update with wrong ETag, expect failure.
|
||||
err = statestore.Set(&state.SetRequest{
|
||||
Key: testKey,
|
||||
Value: secondValue,
|
||||
ETag: &fakeEtag,
|
||||
})
|
||||
assert.NotNil(t, err)
|
||||
|
||||
// Try and update with corect ETag, expect success.
|
||||
err = statestore.Set(&state.SetRequest{
|
||||
Key: testKey,
|
||||
Value: secondValue,
|
||||
ETag: &etag,
|
||||
})
|
||||
assert.Nil(t, err)
|
||||
|
||||
// Validate the set.
|
||||
res, err = statestore.Get(&state.GetRequest{
|
||||
Key: testKey,
|
||||
})
|
||||
assert.Nil(t, err)
|
||||
assert.Equal(t, secondValue, res.Data)
|
||||
assert.NotEqual(t, etag, res.ETag)
|
||||
etag = res.ETag
|
||||
|
||||
// Try and delete with wrong ETag, expect failure.
|
||||
err = statestore.Delete(&state.DeleteRequest{
|
||||
Key: testKey,
|
||||
ETag: &fakeEtag,
|
||||
})
|
||||
assert.NotNil(t, err)
|
||||
|
||||
// Try and delete with correct ETag, expect success.
|
||||
err = statestore.Delete(&state.DeleteRequest{
|
||||
Key: testKey,
|
||||
ETag: &etag,
|
||||
})
|
||||
assert.Nil(t, err)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue