Fixes memstore transaction semantics

This commit is contained in:
Barak Michener 2015-09-02 17:36:00 -04:00
parent b8b3e1b45a
commit 3e2b490063
2 changed files with 51 additions and 2 deletions

View file

@ -106,6 +106,26 @@ func newQuadStore() *QuadStore {
}
func (qs *QuadStore) ApplyDeltas(deltas []graph.Delta, ignoreOpts graph.IgnoreOpts) error {
// Precheck the whole transaction
for _, d := range deltas {
switch d.Action {
case graph.Add:
if !ignoreOpts.IgnoreDup {
if _, exists := qs.indexOf(d.Quad); exists {
return graph.ErrQuadExists
}
}
case graph.Delete:
if !ignoreOpts.IgnoreMissing {
if _, exists := qs.indexOf(d.Quad); !exists {
return graph.ErrQuadNotExist
}
}
default:
return errors.New("memstore: invalid action")
}
}
for _, d := range deltas {
var err error
switch d.Action {
@ -120,7 +140,7 @@ func (qs *QuadStore) ApplyDeltas(deltas []graph.Delta, ignoreOpts graph.IgnoreOp
err = nil
}
default:
err = errors.New("memstore: invalid action")
panic("memstore: unexpected invalid action")
}
if err != nil {
return err

View file

@ -180,13 +180,17 @@ func TestLinksToOptimization(t *testing.T) {
func TestRemoveQuad(t *testing.T) {
qs, w, _ := makeTestStore(simpleGraph)
w.RemoveQuad(quad.Quad{
err := w.RemoveQuad(quad.Quad{
Subject: "E",
Predicate: "follows",
Object: "F",
Label: "",
})
if err != nil {
t.Error("Couldn't remove quad", err)
}
fixed := qs.FixedIterator()
fixed.Add(qs.ValueOf("E"))
@ -204,3 +208,28 @@ func TestRemoveQuad(t *testing.T) {
t.Error("E should not have any followers.")
}
}
func TestTransaction(t *testing.T) {
qs, w, _ := makeTestStore(simpleGraph)
size := qs.Size()
tx := graph.NewTransaction()
tx.AddQuad(quad.Quad{
Subject: "E",
Predicate: "follows",
Object: "G",
Label: ""})
tx.RemoveQuad(quad.Quad{
Subject: "Non",
Predicate: "existent",
Object: "quad",
Label: ""})
err := w.ApplyTransaction(tx)
if err == nil {
t.Error("Able to remove a non-existent quad")
}
if size != qs.Size() {
t.Error("Appended a new quad in a failed transaction")
}
}