(t *testing.T)
| 88 | } |
| 89 | |
| 90 | func TestDetectTxnOrderViolation(t *testing.T) { |
| 91 | errOrderViolation := errors.New("DetectedOrderViolation") |
| 92 | |
| 93 | integration2.BeforeTest(t) |
| 94 | clus := integration2.NewCluster(t, &integration2.ClusterConfig{Size: 3, UseBridge: true}) |
| 95 | defer clus.Terminate(t) |
| 96 | |
| 97 | cfg := clientv3.Config{ |
| 98 | Endpoints: []string{ |
| 99 | clus.Members[0].GRPCURL, |
| 100 | clus.Members[1].GRPCURL, |
| 101 | clus.Members[2].GRPCURL, |
| 102 | }, |
| 103 | } |
| 104 | cli, err := integration2.NewClient(t, cfg) |
| 105 | require.NoError(t, err) |
| 106 | defer func() { assert.NoError(t, cli.Close()) }() |
| 107 | ctx := context.TODO() |
| 108 | |
| 109 | _, err = clus.Client(0).Put(ctx, "foo", "bar") |
| 110 | require.NoError(t, err) |
| 111 | // ensure that the second member has the current revision for the key foo |
| 112 | _, err = clus.Client(1).Get(ctx, "foo") |
| 113 | require.NoError(t, err) |
| 114 | |
| 115 | // stop third member in order to force the member to have an outdated revision |
| 116 | clus.Members[2].Stop(t) |
| 117 | time.Sleep(1 * time.Second) // give enough time for operation |
| 118 | _, err = clus.Client(1).Put(ctx, "foo", "buzz") |
| 119 | require.NoError(t, err) |
| 120 | |
| 121 | // perform get request against the first member, in order to |
| 122 | // set up kvOrdering to expect "foo" revisions greater than that of |
| 123 | // the third member. |
| 124 | orderingKv := ordering.NewKV(cli.KV, |
| 125 | func(op clientv3.Op, resp clientv3.OpResponse, prevRev int64) error { |
| 126 | return errOrderViolation |
| 127 | }) |
| 128 | orderingTxn := orderingKv.Txn(ctx) |
| 129 | _, err = orderingTxn.If( |
| 130 | clientv3.Compare(clientv3.Value("b"), ">", "a"), |
| 131 | ).Then( |
| 132 | clientv3.OpGet("foo"), |
| 133 | ).Commit() |
| 134 | require.NoError(t, err) |
| 135 | |
| 136 | // ensure that only the third member is queried during requests |
| 137 | clus.Members[0].Stop(t) |
| 138 | clus.Members[1].Stop(t) |
| 139 | require.NoError(t, clus.Members[2].Restart(t)) |
| 140 | // force OrderingKv to query the third member |
| 141 | cli.SetEndpoints(clus.Members[2].GRPCURL) |
| 142 | time.Sleep(2 * time.Second) // FIXME: Figure out how pause SetEndpoints sufficiently that this is not needed |
| 143 | _, err = orderingKv.Get(ctx, "foo", clientv3.WithSerializable()) |
| 144 | if !errors.Is(err, errOrderViolation) { |
| 145 | t.Fatalf("expected %v, got %v", errOrderViolation, err) |
| 146 | } |
| 147 | orderingTxn = orderingKv.Txn(ctx) |
nothing calls this directly
no test coverage detected
searching dependent graphs…