public void ShouldCreateNewRecordIfConcurrentWriterReturnsFalse() { var copyOnWrite = new FunctionsCopyOnWrite(); // FunctionsCopyOnWrite var log = default(IDevice); try { log = Devices.CreateLogDevice(TestContext.CurrentContext.TestDirectory + "\\hlog1.log", deleteOnClose: true); using (var fht = new FasterKV <KeyStruct, ValueStruct, InputStruct, OutputStruct, Empty, FunctionsCopyOnWrite> (128, copyOnWrite, new LogSettings { LogDevice = log, MemorySizeBits = 29 })) { fht.StartSession(); var key = default(KeyStruct); var value = default(ValueStruct); key = new KeyStruct() { kfield1 = 1, kfield2 = 2 }; value = new ValueStruct() { vfield1 = 1000, vfield2 = 2000 }; fht.Upsert(ref key, ref value, Empty.Default, 0); value = new ValueStruct() { vfield1 = 1001, vfield2 = 2002 }; fht.Upsert(ref key, ref value, Empty.Default, 0); var recordCount = 0; using (var iterator = fht.Log.Scan(fht.Log.BeginAddress, fht.Log.TailAddress)) { while (iterator.GetNext(out var info)) { recordCount++; } } Assert.AreEqual(1, copyOnWrite.ConcurrentWriterCallCount, 2); Assert.AreEqual(2, recordCount); fht.StopSession(); } } finally { if (log != null) { log.Close(); } } }
public void ShouldCreateNewRecordIfConcurrentWriterReturnsFalse() { var copyOnWrite = new FunctionsCopyOnWrite(); // FunctionsCopyOnWrite var log = default(IDevice); try { log = Devices.CreateLogDevice(TestUtils.MethodTestDir + "/hlog1.log", deleteOnClose: true); using var fht = new FasterKV <KeyStruct, ValueStruct> (128, new LogSettings { LogDevice = log, MemorySizeBits = 29 }); using var session = fht.NewSession(copyOnWrite); var key = default(KeyStruct); var value = default(ValueStruct); var input = default(InputStruct); var output = default(OutputStruct); key = new KeyStruct() { kfield1 = 1, kfield2 = 2 }; value = new ValueStruct() { vfield1 = 1000, vfield2 = 2000 }; var status = session.Upsert(ref key, ref input, ref value, ref output, out RecordMetadata recordMetadata1); Assert.IsTrue(!status.Found && status.Record.Created, status.ToString()); // ConcurrentWriter returns false, so we create a new record (and leave the old one sealed). value = new ValueStruct() { vfield1 = 1001, vfield2 = 2002 }; status = session.Upsert(ref key, ref input, ref value, ref output, out RecordMetadata recordMetadata2); Assert.IsTrue(!status.Found && status.Record.Created, status.ToString()); Assert.Greater(recordMetadata2.Address, recordMetadata1.Address); var recordCount = 0; using (var iterator = fht.Log.Scan(fht.Log.BeginAddress, fht.Log.TailAddress)) { // We seal before copying and leave it sealed after copying, so we only get one record. while (iterator.GetNext(out var info)) { recordCount++; } } Assert.AreEqual(1, copyOnWrite.ConcurrentWriterCallCount); Assert.AreEqual(1, recordCount); } finally { if (log != null) { log.Dispose(); } } }