summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorHenning Baldersheim <balder@yahoo-inc.com>2020-01-15 15:17:07 +0000
committerHenning Baldersheim <balder@yahoo-inc.com>2020-01-16 15:41:23 +0000
commitd3cf455cba32ef3f5280634470858e80761d8450 (patch)
tree7d4dd978a349cd305fff48ee5967acbe0ad4458b
parent6abc05684fc3fe46da2b159b8944fae9adb086a4 (diff)
Unify towards nbostream
-rw-r--r--document/src/tests/arrayfieldvaluetest.cpp24
-rw-r--r--document/src/tests/documenttestcase.cpp264
-rw-r--r--document/src/tests/primitivefieldvaluetest.cpp25
-rw-r--r--document/src/tests/structfieldvaluetest.cpp23
-rw-r--r--document/src/tests/weightedsetfieldvaluetest.cpp16
-rw-r--r--document/src/vespa/document/fieldvalue/document.cpp149
-rw-r--r--document/src/vespa/document/fieldvalue/document.h32
-rw-r--r--document/src/vespa/document/fieldvalue/fieldvalue.cpp14
-rw-r--r--document/src/vespa/document/fieldvalue/fieldvalue.h2
-rw-r--r--document/src/vespa/document/fieldvalue/serializablearray.h1
-rw-r--r--document/src/vespa/document/fieldvalue/structfieldvalue.cpp39
-rw-r--r--documentapi/src/vespa/documentapi/messagebus/messages/visitor.cpp37
-rw-r--r--documentapi/src/vespa/documentapi/messagebus/routablefactories60.cpp8
-rw-r--r--persistence/src/vespa/persistence/conformancetest/conformancetest.cpp2
-rw-r--r--storage/src/tests/visiting/visitormanagertest.cpp2
-rw-r--r--storage/src/vespa/storage/persistence/mergehandler.cpp24
-rw-r--r--storage/src/vespa/storage/visiting/recoveryvisitor.cpp4
-rw-r--r--storageapi/src/vespa/storageapi/mbusprot/protocolserialization7.cpp2
-rw-r--r--storageapi/src/vespa/storageapi/mbusprot/serializationhelper.h4
-rw-r--r--storageapi/src/vespa/storageapi/message/bucket.cpp3
-rw-r--r--storageapi/src/vespa/storageapi/message/persistence.cpp2
21 files changed, 197 insertions, 480 deletions
diff --git a/document/src/tests/arrayfieldvaluetest.cpp b/document/src/tests/arrayfieldvaluetest.cpp
index 014884e44cd..0bdf51194fb 100644
--- a/document/src/tests/arrayfieldvaluetest.cpp
+++ b/document/src/tests/arrayfieldvaluetest.cpp
@@ -15,9 +15,8 @@ namespace document {
namespace {
template <typename T>
-void deserialize(const ByteBuffer &buffer, T &value) {
+void deserialize(nbostream & stream, T &value) {
uint16_t version = Document::getNewestSerializationVersion();
- nbostream stream(buffer.getBufferAtPos(), buffer.getRemaining());
DocumentTypeRepo repo;
VespaDocumentDeserializer deserializer(repo, stream, version);
deserializer.read(value);
@@ -53,40 +52,39 @@ TEST(ArrayFieldValueTest, testArray)
EXPECT_EQ(IntFieldValue(3), (IntFieldValue&) value[2]);
// Serialize & equality
- std::unique_ptr<ByteBuffer> buffer(value.serialize());
- buffer->flip();
+ nbostream stream(value.serialize());
ArrayFieldValue value2(type);
EXPECT_TRUE(value != value2);
- deserialize(*buffer, value2);
+ deserialize(stream, value2);
EXPECT_EQ(value, value2);
// Various ways of removing
{
// By index
- buffer->setPos(0);
- deserialize(*buffer, value2);
+ stream.rp(0);
+ deserialize(stream, value2);
value2.remove(1);
EXPECT_TRUE(!value2.contains(IntFieldValue(2)));
EXPECT_EQ(size_t(2), value2.size());
// By value
- buffer->setPos(0);
- deserialize(*buffer, value2);
+ stream.rp(0);
+ deserialize(stream, value2);
EXPECT_TRUE(value2.remove(IntFieldValue(1)));
EXPECT_TRUE(!value2.contains(IntFieldValue(1)));
EXPECT_EQ(size_t(2), value2.size());
// By value with multiple present
- buffer->setPos(0);
- deserialize(*buffer, value2);
+ stream.rp(0);
+ deserialize(stream, value2);
value2.add(IntFieldValue(1));
EXPECT_TRUE(value2.remove(IntFieldValue(1)));
EXPECT_TRUE(!value2.contains(IntFieldValue(1)));
EXPECT_EQ(size_t(2), value2.size());
// Clearing all
- buffer->setPos(0);
- deserialize(*buffer, value2);
+ stream.rp(0);
+ deserialize(stream, value2);
value2.clear();
EXPECT_TRUE(!value2.contains(IntFieldValue(1)));
EXPECT_EQ(size_t(0), value2.size());
diff --git a/document/src/tests/documenttestcase.cpp b/document/src/tests/documenttestcase.cpp
index 60f2a1ae861..93bcd61ddb0 100644
--- a/document/src/tests/documenttestcase.cpp
+++ b/document/src/tests/documenttestcase.cpp
@@ -386,13 +386,13 @@ TEST(DocumentTest, testSimpleUsage)
EXPECT_EQ(1, value.getValue(intF)->getAsInt());
EXPECT_EQ(2, value.getValue(longF)->getAsInt());
- // Serialize & equality
- std::unique_ptr<ByteBuffer> buffer(value.serialize());
- buffer->flip();
+ // Serialize & equality
+ nbostream buffer;
+ value.serialize(buffer);
Document value2(*repo.getDocumentType("test"),
DocumentId("id::test:n=3:foo"));
EXPECT_TRUE(value != value2);
- value2.deserialize(repo, *buffer);
+ value2.deserialize(repo, buffer);
EXPECT_TRUE(value2.hasValue(intF));
EXPECT_EQ(value, value2);
EXPECT_EQ(DocumentId("id:ns:test::1"), value2.getId());
@@ -400,15 +400,15 @@ TEST(DocumentTest, testSimpleUsage)
// Various ways of removing
{
// By value
- buffer->setPos(0);
- value2.deserialize(repo, *buffer);
+ buffer.rp(0);
+ value2.deserialize(repo, buffer);
value2.remove(intF);
EXPECT_TRUE(!value2.hasValue(intF));
EXPECT_EQ(size_t(1), value2.getSetFieldCount());
// Clearing all
- buffer->setPos(0);
- value2.deserialize(repo, *buffer);
+ buffer.rp(0);
+ value2.deserialize(repo, buffer);
value2.clear();
EXPECT_TRUE(!value2.hasValue(intF));
EXPECT_EQ(size_t(0), value2.getSetFieldCount());
@@ -568,22 +568,24 @@ TEST(DocumentTest, testReadSerializedFile)
}
close(fd);
- Document doc(repo, buf);
+ nbostream stream(buf.getBufferAtPos(), len);
+ Document doc(repo, stream);
verifyJavaDocument(doc);
- std::unique_ptr<ByteBuffer> buf2 = doc.serialize();
- buf2->flip();
+ nbostream buf2 = doc.serialize();
- Document doc2(repo, *buf2);
+ Document doc2(repo, buf2);
verifyJavaDocument(doc2);
- EXPECT_EQ(len, buf2->getPos());
- EXPECT_TRUE(memcmp(buf2->getBuffer(), buf.getBuffer(), buf2->getPos()) == 0);
+ EXPECT_TRUE(buf2.empty());
+ buf2.rp(0);
+ EXPECT_EQ(len, buf2.size());
+ EXPECT_TRUE(memcmp(buf2.peek(), buf.getBuffer(), buf2.size()) == 0);
doc2.setValue("stringfield", StringFieldValue("hei"));
- std::unique_ptr<ByteBuffer> buf3 = doc2.serialize();
- EXPECT_TRUE(len != buf3->getPos());
+ nbostream buf3 = doc2.serialize();
+ EXPECT_TRUE(len != buf3.size());
}
TEST(DocumentTest, testReadSerializedFileCompressed)
@@ -602,7 +604,8 @@ TEST(DocumentTest, testReadSerializedFileCompressed)
}
close(fd);
- Document doc(repo, buf);
+ nbostream stream(buf.getBufferAtPos(), len);
+ Document doc(repo, stream);
verifyJavaDocument(doc);
}
@@ -706,26 +709,25 @@ TEST(DocumentTest,testReadSerializedAllVersions)
// you can copy this current to new test for new version)
{
//doc.setCompression(CompressionConfig(CompressionConfig::NONE, 0, 0));
- std::unique_ptr<ByteBuffer> buf = doc.serialize();
- EXPECT_EQ(buf->getLength(), buf->getPos());
+ nbostream buf = doc.serialize();
int fd = open(TEST_PATH("data/document-cpp-currentversion-uncompressed.dat").c_str(),
O_WRONLY | O_CREAT | O_TRUNC, 0644);
EXPECT_TRUE(fd > 0);
- size_t len = write(fd, buf->getBuffer(), buf->getPos());
- EXPECT_EQ(buf->getPos(), len);
+ size_t len = write(fd, buf.peek(), buf.size());
+ EXPECT_EQ(buf.size(), len);
close(fd);
}
{
CompressionConfig oldCfg(doc.getType().getFieldsType().getCompressionConfig());
CompressionConfig newCfg(CompressionConfig::LZ4, 9, 95);
const_cast<StructDataType &>(doc.getType().getFieldsType()).setCompressionConfig(newCfg);
- std::unique_ptr<ByteBuffer> buf = doc.serialize();
- EXPECT_TRUE(buf->getPos() <= buf->getLength());
+ nbostream buf = doc.serialize();
+ EXPECT_TRUE(buf.size() <= buf.capacity());
int fd = open(TEST_PATH("data/document-cpp-currentversion-lz4-9.dat").c_str(),
O_WRONLY | O_CREAT | O_TRUNC, 0644);
EXPECT_TRUE(fd > 0);
- size_t len = write(fd, buf->getBuffer(), buf->getPos());
- EXPECT_EQ(buf->getPos(), len);
+ size_t len = write(fd, buf.peek(), buf.size());
+ EXPECT_EQ(buf.size(), len);
close(fd);
const_cast<StructDataType &>(doc.getType().getFieldsType()).setCompressionConfig(oldCfg);
}
@@ -752,7 +754,8 @@ TEST(DocumentTest,testReadSerializedAllVersions)
}
close(fd);
- Document doc(repo, buf);
+ nbostream stream(buf.getBufferAtPos(), len);
+ Document doc(repo, stream);
IntFieldValue intVal;
EXPECT_TRUE(doc.getValue(doc.getField("intfield"), intVal));
@@ -805,27 +808,14 @@ TEST(DocumentTest,testReadSerializedAllVersions)
EXPECT_EQ(199, wset.get(StringFieldValue("Weighted 1")));
// Check that serialization doesn't cause any problems.
- std::unique_ptr<ByteBuffer> buf2 = doc.serialize();
- buf2->flip();
+ nbostream buf2 = doc.serialize();
- Document doc2(repo, *buf2);
+ Document doc2(repo, buf2);
}
}
size_t getSerializedSize(const Document &doc) {
- return doc.serialize()->getLength();
-}
-
-size_t getSerializedSizeHeader(const Document &doc) {
- nbostream stream;
- doc.serializeHeader(stream);
- return stream.size();
-}
-
-size_t getSerializedSizeBody(const Document &doc) {
- nbostream stream;
- doc.serializeBody(stream);
- return stream.size();
+ return doc.serialize().size();
}
TEST(DocumentTest, testGenerateSerializedFile)
@@ -864,30 +854,30 @@ TEST(DocumentTest, testGenerateSerializedFile)
map.put(StringFieldValue("foo2"), StringFieldValue("bar2"));
doc.setValue("mapfield", map);
- std::unique_ptr<ByteBuffer> buf = doc.serialize();
+ nbostream buf = doc.serialize();
const std::string serializedDir = TEST_PATH("../test/document/");
int fd = open((serializedDir + "/serializecpp.dat").c_str(),
O_WRONLY | O_TRUNC | O_CREAT, 0644);
- if (write(fd, buf->getBuffer(), buf->getPos()) != (ssize_t)buf->getPos()) {
+ if (write(fd, buf.peek(), buf.size()) != (ssize_t)buf.size()) {
throw vespalib::Exception("write failed");
}
close(fd);
- ByteBuffer hBuf(getSerializedSizeHeader(doc));
+ vespalib::nbostream hBuf;
doc.serializeHeader(hBuf);
fd = open((serializedDir + "/serializecppsplit_header.dat").c_str(),
O_WRONLY | O_TRUNC | O_CREAT, 0644);
- if (write(fd, hBuf.getBuffer(), hBuf.getPos()) != (ssize_t)hBuf.getPos()) {
+ if (write(fd, hBuf.peek(), hBuf.size()) != (ssize_t)hBuf.size()) {
throw vespalib::Exception("write failed");
}
close(fd);
- ByteBuffer bBuf(getSerializedSizeBody(doc));
+ vespalib::nbostream bBuf;
doc.serializeBody(bBuf);
fd = open((serializedDir+ "/serializecppsplit_body.dat").c_str(),
O_WRONLY | O_TRUNC | O_CREAT, 0644);
- if (write(fd, bBuf.getBuffer(), bBuf.getPos()) != (ssize_t)bBuf.getPos()) {
+ if (write(fd, bBuf.peek(), bBuf.size()) != (ssize_t)bBuf.size()) {
throw vespalib::Exception("write failed");
}
close(fd);
@@ -908,49 +898,20 @@ TEST(DocumentTest, testGenerateSerializedFile)
close(fd);
}
-TEST(DocumentTest, testGetURIFromSerialized)
-{
- TestDocRepo test_repo;
- Document doc(*test_repo.getDocumentType("testdoctype1"), DocumentId("id:ns:testdoctype1::1"));
-
- {
- std::unique_ptr<ByteBuffer> serialized = doc.serialize();
- serialized->flip();
-
- EXPECT_EQ(
- vespalib::string("id:ns:testdoctype1::1"),
- Document::getIdFromSerialized(*serialized).toString());
-
- EXPECT_EQ(vespalib::string("testdoctype1"),
- Document::getDocTypeFromSerialized(
- test_repo.getTypeRepo(),
- *serialized)->getName());
- }
-
- {
- std::unique_ptr<ByteBuffer> serialized = doc.serialize();
- serialized->flip();
-
- Document doc2(test_repo.getTypeRepo(), *serialized);
- EXPECT_EQ(vespalib::string("id:ns:testdoctype1::1"), doc2.getId().toString());
- EXPECT_EQ(vespalib::string("testdoctype1"), doc2.getType().getName());
- }
-}
-
TEST(DocumentTest, testBogusserialize)
{
TestDocRepo test_repo;
try {
- auto buf = std::make_unique<ByteBuffer>("aoifjweprjwoejr203r+2+4r823++!",100);
- Document doc(test_repo.getTypeRepo(), *buf);
+ nbostream stream("aoifjweprjwoejr203r+2+4r823++!",100);
+ Document doc(test_repo.getTypeRepo(), stream);
FAIL() << "Failed to throw exception deserializing bogus data";
} catch (DeserializeException& e) {
EXPECT_THAT(e.what(), HasSubstr("Unrecognized serialization version"));
}
try {
- auto buf = std::make_unique<ByteBuffer>("",0);
- Document doc(test_repo.getTypeRepo(), *buf);
+ nbostream stream("",0);
+ Document doc(test_repo.getTypeRepo(), stream);
FAIL() << "Failed to throw exception deserializing empty buffer";
} catch (DeserializeException& e) {
EXPECT_THAT(e.what(), HasSubstr("Buffer out of bounds"));
@@ -967,24 +928,23 @@ TEST(DocumentTest, testCRC32)
uint32_t crc = doc.calculateChecksum();
EXPECT_EQ(3987392271u, crc);
- std::unique_ptr<ByteBuffer> buf = doc.serialize();
- buf->flip();
+ nbostream buf = doc.serialize();
int pos = 30;
// Corrupt serialization.
- buf->getBuffer()[pos] ^= 72;
+ const_cast<char *>(buf.peek())[pos] ^= 72;
// Create document. Byte corrupted above is in data area and
// shouldn't fail deserialization.
try {
- Document doc2(test_repo.getTypeRepo(), *buf);
- buf->setPos(0);
+ Document doc2(test_repo.getTypeRepo(), buf);
+ buf.rp(0);
EXPECT_TRUE(crc != doc2.calculateChecksum());
} catch (document::DeserializeException& e) {
EXPECT_TRUE(false);
}
// Return original value and retry
- buf->getBuffer()[pos] ^= 72;
+ const_cast<char *>(buf.peek())[pos] ^= 72;
/// \todo TODO (was warning): Cannot test for in memory representation altered, as there is no syntax for getting internal refs to data from document. Add test when this is added.
}
@@ -1001,13 +961,12 @@ TEST(DocumentTest, testHasChanged)
// Still changed after setting a value of course.
EXPECT_TRUE(doc.hasChanged());
- std::unique_ptr<ByteBuffer> buf = doc.serialize();
- buf->flip();
-
+ nbostream buf;
+ doc.serialize(buf);
// Setting a value in doc tags us changed.
{
- buf->setPos(0);
- Document doc2(test_repo.getTypeRepo(), *buf);
+ buf.rp(0);
+ Document doc2(test_repo.getTypeRepo(), buf);
EXPECT_TRUE(!doc2.hasChanged());
doc2.set("headerval", 13);
@@ -1015,16 +974,16 @@ TEST(DocumentTest, testHasChanged)
}
// Overwriting a value in doc tags us changed.
{
- buf->setPos(0);
- Document doc2(test_repo.getTypeRepo(), *buf);
+ buf.rp(0);
+ Document doc2(test_repo.getTypeRepo(), buf);
doc2.set("hstringval", "bla bla bla bla bla");
EXPECT_TRUE(doc2.hasChanged());
}
// Clearing value tags us changed.
{
- buf->setPos(0);
- Document doc2(test_repo.getTypeRepo(), *buf);
+ buf.rp(0);
+ Document doc2(test_repo.getTypeRepo(), buf);
doc2.clear();
EXPECT_TRUE(doc2.hasChanged());
@@ -1032,36 +991,6 @@ TEST(DocumentTest, testHasChanged)
// Add more tests here when we allow non-const refs to internals
}
-TEST(DocumentTest, testSplitSerialization)
-{
- TestDocMan testDocMan;
- Document::UP doc = testDocMan.createDocument();
- doc->set("headerval", 50);
-
- ByteBuffer buf(getSerializedSizeHeader(*doc));
- doc->serializeHeader(buf);
- buf.flip();
-
- ByteBuffer buf2(getSerializedSizeBody(*doc));
- doc->serializeBody(buf2);
- buf2.flip();
-
- EXPECT_EQ(size_t(65), buf.getLength());
- EXPECT_EQ(size_t(73), buf2.getLength());
-
- Document headerDoc(testDocMan.getTypeRepo(), buf);
- EXPECT_TRUE(headerDoc.hasValue("headerval"));
- EXPECT_TRUE(!headerDoc.hasValue("content"));
-
- buf.setPos(0);
- Document fullDoc;
- fullDoc.deserialize(testDocMan.getTypeRepo(), buf, buf2);
- EXPECT_TRUE(fullDoc.hasValue("headerval"));
- EXPECT_TRUE(fullDoc.hasValue("content"));
-
- EXPECT_EQ(*doc, fullDoc);
-}
-
TEST(DocumentTest, testSliceSerialize)
{
// Test that document doesn't need its own bytebuffer, such that we
@@ -1077,17 +1006,15 @@ TEST(DocumentTest, testSliceSerialize)
val.add(RawFieldValue("hei der", 7));
doc2->setValue(doc2->getField("rawarray"), val);
- ByteBuffer buf(getSerializedSize(*doc) + getSerializedSize(*doc2));
- doc->serialize(buf);
- EXPECT_EQ(getSerializedSize(*doc), buf.getPos());
+ nbostream buf = doc->serialize();
+ EXPECT_EQ(getSerializedSize(*doc), buf.size());
doc2->serialize(buf);
- EXPECT_EQ(getSerializedSize(*doc) + getSerializedSize(*doc2), buf.getPos());
- buf.flip();
+ EXPECT_EQ(getSerializedSize(*doc) + getSerializedSize(*doc2), buf.size());
Document doc3(testDocMan.getTypeRepo(), buf);
- EXPECT_EQ(getSerializedSize(*doc), buf.getPos());
+ EXPECT_EQ(getSerializedSize(*doc), buf.rp());
Document doc4(testDocMan.getTypeRepo(), buf);
- EXPECT_EQ(getSerializedSize(*doc) + getSerializedSize(*doc2), buf.getPos());
+ EXPECT_EQ(getSerializedSize(*doc) + getSerializedSize(*doc2), buf.rp());
EXPECT_EQ(*doc, doc3);
EXPECT_EQ(*doc2, doc4);
@@ -1103,21 +1030,19 @@ TEST(DocumentTest, testCompression)
doc->setValue("hstringval", StringFieldValue(bigString));
- std::unique_ptr<ByteBuffer> buf_uncompressed = doc->serialize();
- buf_uncompressed->flip();
+ nbostream buf_uncompressed = doc->serialize();
CompressionConfig oldCfg(doc->getType().getFieldsType().getCompressionConfig());
CompressionConfig newCfg(CompressionConfig::LZ4, 9, 95);
const_cast<StructDataType &>(doc->getType().getFieldsType()).setCompressionConfig(newCfg);
- std::unique_ptr<ByteBuffer> buf_lz4 = doc->serialize();
- buf_lz4->flip();
+ nbostream buf_lz4 = doc->serialize();
const_cast<StructDataType &>(doc->getType().getFieldsType()).setCompressionConfig(oldCfg);
- EXPECT_TRUE(buf_lz4->getRemaining() < buf_uncompressed->getRemaining());
+ EXPECT_TRUE(buf_lz4.size() < buf_uncompressed.size());
- Document doc_lz4(testDocMan.getTypeRepo(), *buf_lz4);
+ Document doc_lz4(testDocMan.getTypeRepo(), buf_lz4);
EXPECT_EQ(*doc, doc_lz4);
}
@@ -1137,10 +1062,10 @@ TEST(DocumentTest, testCompressionConfigured)
for (int i = 0; i < 8; ++i) { bigString += bigString; }
doc_uncompressed.setValue("stringfield", StringFieldValue(bigString));
- std::unique_ptr<ByteBuffer> buf_uncompressed = doc_uncompressed.serialize();
- buf_uncompressed->flip();
+ nbostream buf_uncompressed;
+ doc_uncompressed.serialize(buf_uncompressed);
- size_t uncompressedSize = buf_uncompressed->getRemaining();
+ size_t uncompressedSize = buf_uncompressed.size();
DocumenttypesConfigBuilderHelper builder2;
builder2.document(43, "serializetest",
@@ -1152,22 +1077,22 @@ TEST(DocumentTest, testCompressionConfigured)
9, 99, 0));
DocumentTypeRepo repo2(builder2.config());
- Document doc(repo2, *buf_uncompressed);
+ Document doc(repo2, buf_uncompressed);
- std::unique_ptr<ByteBuffer> buf_compressed = doc.serialize();
- buf_compressed->flip();
- size_t compressedSize = buf_compressed->getRemaining();
+ nbostream buf_compressed;
+ doc.serialize(buf_compressed);
+ size_t compressedSize = buf_compressed.size();
EXPECT_TRUE(compressedSize < uncompressedSize);
- Document doc2(repo2, *buf_compressed);
+ Document doc2(repo2, buf_compressed);
- std::unique_ptr<ByteBuffer> buf_compressed2 = doc2.serialize();
- buf_compressed2->flip();
+ nbostream buf_compressed2;
+ doc2.serialize(buf_compressed2);
- EXPECT_EQ(compressedSize, buf_compressed2->getRemaining());
+ EXPECT_EQ(compressedSize, buf_compressed2.size());
- Document doc3(repo2, *buf_compressed2);
+ Document doc3(repo2, buf_compressed2);
EXPECT_EQ(doc2, doc_uncompressed);
EXPECT_EQ(doc2, doc3);
@@ -1199,59 +1124,31 @@ TEST(DocumentTest, testUnknownEntries)
doc1.setValue(field3, IntFieldValue(3));
doc1.setValue(field4, IntFieldValue(4));
- uint32_t headerLen = getSerializedSizeHeader(doc1);
- document::ByteBuffer header(headerLen);
- doc1.serializeHeader(header);
- header.flip();
-
- uint32_t bodyLen = getSerializedSizeBody(doc1);
- document::ByteBuffer body(bodyLen);
- doc1.serializeBody(body);
- body.flip();
-
- uint32_t totalLen = getSerializedSize(doc1);
- document::ByteBuffer total(totalLen);
- doc1.serialize(total);
- total.flip();
+ vespalib::nbostream os;
+ doc1.serialize(os);
Document doc2;
- doc2.deserialize(repo, total);
-
- Document doc3;
- doc3.deserializeHeader(repo, header);
- doc3.deserializeBody(repo, body);
+ doc2.deserialize(repo, os);
EXPECT_EQ(std::string(
"<document documenttype=\"test\" documentid=\"id:ns:test::1\">\n"
"<int3>3</int3>\n"
"<int4>4</int4>\n"
"</document>"), doc2.toXml());
- EXPECT_EQ(std::string(
- "<document documenttype=\"test\" documentid=\"id:ns:test::1\">\n"
- "<int3>3</int3>\n"
- "<int4>4</int4>\n"
- "</document>"), doc3.toXml());
EXPECT_EQ(3, doc2.getValue(field3)->getAsInt());
EXPECT_EQ(4, doc2.getValue(field4)->getAsInt());
- EXPECT_EQ(3, doc3.getValue(field3)->getAsInt());
- EXPECT_EQ(4, doc3.getValue(field4)->getAsInt());
// The fields are actually accessible as long as you ask with field of
// correct type.
EXPECT_TRUE(doc2.hasValue(field1));
EXPECT_TRUE(doc2.hasValue(field2));
- EXPECT_TRUE(doc3.hasValue(field1));
- EXPECT_TRUE(doc3.hasValue(field2));
EXPECT_EQ(1, doc2.getValue(field1)->getAsInt());
EXPECT_EQ(2, doc2.getValue(field2)->getAsInt());
- EXPECT_EQ(1, doc3.getValue(field1)->getAsInt());
- EXPECT_EQ(2, doc3.getValue(field2)->getAsInt());
EXPECT_EQ(size_t(2), doc2.getSetFieldCount());
- EXPECT_EQ(size_t(2), doc3.getSetFieldCount());
}
TEST(DocumentTest, testAnnotationDeserialization)
@@ -1288,7 +1185,8 @@ TEST(DocumentTest, testAnnotationDeserialization)
}
close(fd);
- Document doc(repo, buf);
+ nbostream stream1(buf.getBufferAtPos(), len);
+ Document doc(repo, stream1);
StringFieldValue strVal;
EXPECT_TRUE(doc.getValue(doc.getField("story"), strVal));
diff --git a/document/src/tests/primitivefieldvaluetest.cpp b/document/src/tests/primitivefieldvaluetest.cpp
index 58592e50cfe..8a5daf05f05 100644
--- a/document/src/tests/primitivefieldvaluetest.cpp
+++ b/document/src/tests/primitivefieldvaluetest.cpp
@@ -14,9 +14,8 @@ namespace document {
namespace {
template <typename T>
-void deserialize(const ByteBuffer &buffer, T &value) {
+void deserialize(nbostream & stream, T &value) {
uint16_t version = Document::getNewestSerializationVersion();
- nbostream stream(buffer.getBufferAtPos(), buffer.getRemaining());
DocumentTypeRepo repo;
VespaDocumentDeserializer deserializer(repo, stream, version);
deserializer.read(value);
@@ -89,20 +88,17 @@ void deserialize(const ByteBuffer &buffer, T &value) {
// Serialization
Type t;
- std::unique_ptr<ByteBuffer> buf(smallest.serialize());
- buf->flip();
- deserialize(*buf, t);
+ nbostream buf(smallest.serialize());
+ deserialize(buf, t);
EXPECT_EQ(smallest, t);
buf = medium1.serialize();
- buf->flip();
- deserialize(*buf, t);
+ deserialize(buf, t);
EXPECT_EQ(medium1, t);
EXPECT_EQ(medium2, t);
buf = largest.serialize();
- buf->flip();
- deserialize(*buf, t);
+ deserialize(buf, t);
EXPECT_EQ(largest, t);
// Assignment
@@ -160,20 +156,17 @@ void deserialize(const ByteBuffer &buffer, T &value) {
// Test that a just deserialized value can be serialized again
// (literals have lazy deserialization so behaves diff then
value = "foo";
- std::unique_ptr<ByteBuffer> buf(value.serialize());
- buf->flip();
+ nbostream buf(value.serialize());
Literal value2("Other");
- deserialize(*buf, value2);
+ deserialize(buf, value2);
buf = value2.serialize();
- buf->flip();
- deserialize(*buf, value2);
+ deserialize(buf, value2);
EXPECT_EQ(value, value2);
// Verify that get value ref gives us ref within original bytebuffer
// (operator== use above should not modify this)
buf = value.serialize();
- buf->flip();
- deserialize(*buf, value2);
+ deserialize(buf, value2);
EXPECT_EQ(size_t(3), value2.getValueRef().size());
// Zero termination
diff --git a/document/src/tests/structfieldvaluetest.cpp b/document/src/tests/structfieldvaluetest.cpp
index 76cf065a36a..9cf4b38be91 100644
--- a/document/src/tests/structfieldvaluetest.cpp
+++ b/document/src/tests/structfieldvaluetest.cpp
@@ -28,10 +28,9 @@ protected:
namespace {
template <typename T>
-void deserialize(const ByteBuffer &buffer, T &value, const FixedTypeRepo &repo)
+void deserialize(nbostream & stream, T &value, const FixedTypeRepo &repo)
{
uint16_t version = Document::getNewestSerializationVersion();
- nbostream stream(buffer.getBufferAtPos(), buffer.getRemaining());
VespaDocumentDeserializer deserializer(repo, stream, version);
deserializer.read(value);
}
@@ -61,13 +60,11 @@ TEST_F(StructFieldValueTest, testEmptyStruct)
StructFieldValue value(type);
// Serialize & equality
- std::unique_ptr<ByteBuffer> buffer(value.serialize());
- buffer->flip();
+ nbostream buffer(value.serialize());
- EXPECT_EQ(buffer->getLength(), buffer->getLimit());
StructFieldValue value2(type);
- deserialize(*buffer, value2, repo);
+ deserialize(buffer, value2, repo);
EXPECT_TRUE(value == value2);
}
@@ -101,14 +98,12 @@ TEST_F(StructFieldValueTest, testStruct)
EXPECT_EQ(2, value.getValue(longF)->getAsInt());
// Serialize & equality
- std::unique_ptr<ByteBuffer> buffer(value.serialize());
- buffer->flip();
+ nbostream buffer(value.serialize());
- EXPECT_EQ(buffer->getLength(), buffer->getLimit());
StructFieldValue value2(type);
EXPECT_TRUE(value != value2);
- deserialize(*buffer, value2, repo);
+ deserialize(buffer, value2, repo);
EXPECT_TRUE(value2.hasValue(intF));
EXPECT_EQ(value, value2);
@@ -116,15 +111,15 @@ TEST_F(StructFieldValueTest, testStruct)
// Various ways of removing
{
// By value
- buffer->setPos(0);
- deserialize(*buffer, value2, repo);
+ buffer.rp(0);
+ deserialize(buffer, value2, repo);
value2.remove(intF);
EXPECT_TRUE(!value2.hasValue(intF));
EXPECT_EQ(size_t(1), value2.getSetFieldCount());
// Clearing all
- buffer->setPos(0);
- deserialize(*buffer, value2, repo);
+ buffer.rp(0);
+ deserialize(buffer, value2, repo);
value2.clear();
EXPECT_TRUE(!value2.hasValue(intF));
EXPECT_EQ(size_t(0), value2.getSetFieldCount());
diff --git a/document/src/tests/weightedsetfieldvaluetest.cpp b/document/src/tests/weightedsetfieldvaluetest.cpp
index 1ec52791a4a..71dc9f1d1a9 100644
--- a/document/src/tests/weightedsetfieldvaluetest.cpp
+++ b/document/src/tests/weightedsetfieldvaluetest.cpp
@@ -16,9 +16,8 @@ namespace document {
namespace {
template <typename T>
-void deserialize(const ByteBuffer &buffer, T &value) {
+void deserialize(nbostream & stream, T &value) {
uint16_t version = Document::getNewestSerializationVersion();
- nbostream stream(buffer.getBufferAtPos(), buffer.getRemaining());
DocumentTypeRepo repo;
VespaDocumentDeserializer deserializer(repo, stream, version);
deserializer.read(value);
@@ -94,26 +93,25 @@ TEST(WeightedSetFieldValueTest, testWeightedSet)
EXPECT_EQ(6, value.get(IntFieldValue(3)));
// Serialize & equality
- std::unique_ptr<ByteBuffer> buffer(value.serialize());
- buffer->flip();
+ nbostream buffer(value.serialize());
WeightedSetFieldValue value2(type);
EXPECT_TRUE(value != value2);
- deserialize(*buffer, value2);
+ deserialize(buffer, value2);
EXPECT_EQ(value, value2);
// Various ways of removing
{
// By value
- buffer->setPos(0);
- deserialize(*buffer, value2);
+ buffer.rp(0);
+ deserialize(buffer, value2);
EXPECT_EQ(size_t(3), value2.size());
EXPECT_TRUE(value2.remove(IntFieldValue(1)));
EXPECT_TRUE(!value2.contains(IntFieldValue(1)));
EXPECT_EQ(size_t(2), value2.size());
// Clearing all
- buffer->setPos(0);
- deserialize(*buffer, value2);
+ buffer.rp(0);
+ deserialize(buffer, value2);
value2.clear();
EXPECT_TRUE(!value2.contains(IntFieldValue(1)));
EXPECT_EQ(size_t(0), value2.size());
diff --git a/document/src/vespa/document/fieldvalue/document.cpp b/document/src/vespa/document/fieldvalue/document.cpp
index 5b7314f0323..b137f4bac2e 100644
--- a/document/src/vespa/document/fieldvalue/document.cpp
+++ b/document/src/vespa/document/fieldvalue/document.cpp
@@ -8,12 +8,10 @@
#include <vespa/document/serialization/vespadocumentserializer.h>
#include <vespa/vespalib/objects/nbostream.h>
#include <vespa/document/util/serializableexceptions.h>
-#include <vespa/document/base/exceptions.h>
#include <vespa/document/fieldset/fieldsets.h>
#include <vespa/document/util/bytebuffer.h>
#include <vespa/vespalib/util/xmlstream.h>
#include <sstream>
-#include <limits>
using vespalib::nbostream;
using vespalib::make_string;
@@ -24,10 +22,6 @@ using namespace vespalib::xml;
namespace document {
namespace {
-bool isLegalVersion(uint16_t version) {
- return (6 <= version) && (version <= 8);
-}
-
void documentTypeError(vespalib::stringref name) __attribute__((noinline));
void throwTypeMismatch(vespalib::stringref type, vespalib::stringref docidType) __attribute__((noinline));
@@ -93,15 +87,6 @@ Document::Document(const DataType &type, DocumentId documentId)
}
}
-Document::Document(const DocumentTypeRepo& repo, ByteBuffer& buffer)
- : StructuredFieldValue(*DataType::DOCUMENT),
- _id(),
- _fields(static_cast<const DocumentType &>(getType()).getFieldsType()),
- _lastModified(0)
-{
- deserialize(repo, buffer);
-}
-
void Document::setRepo(const DocumentTypeRepo& repo)
{
_fields.setRepo(repo);
@@ -143,30 +128,6 @@ Document::hasChanged() const
return _fields.hasChanged();
}
-DocumentId
-Document::getIdFromSerialized(ByteBuffer& buf)
-{
- int position = buf.getPos();
- DocumentId retVal;
-
- deserializeDocHeader(buf, retVal);
- buf.setPos(position);
-
- return retVal;
-}
-
-const DocumentType *
-Document::getDocTypeFromSerialized(const DocumentTypeRepo& repo, ByteBuffer& buf)
-{
- int position = buf.getPos();
- DocumentId retVal;
-
- const DocumentType *docType(deserializeDocHeaderAndType(repo, buf, retVal));
- buf.setPos(position);
-
- return docType;
-}
-
FieldValue&
Document::assign(const FieldValue& value)
{
@@ -247,97 +208,11 @@ Document::calculateChecksum() const
return calculator.checksum() ^ _fields.calculateChecksum();
}
-const DocumentType *
-Document::deserializeDocHeaderAndType(const DocumentTypeRepo& repo, ByteBuffer& buffer, DocumentId& id)
-{
- deserializeDocHeader(buffer, id);
-
- vespalib::stringref docTypeName(buffer.getBufferAtPos());
- buffer.incPos(docTypeName.size() + 1); // Skip 0-byte too
- {
- int16_t docTypeVersion; // version not supported anymore
- buffer.getShortNetwork(docTypeVersion);
- }
- const DocumentType *docTypeNew = nullptr;
-
- docTypeNew = repo.getDocumentType(docTypeName);
- if (!docTypeNew) {
- throw DocumentTypeNotFoundException(docTypeName, VESPA_STRLOC);
- }
- return docTypeNew;
-}
-
-namespace {
-[[noreturn]] void versionError(uint16_t version) __attribute__((noinline));
-[[noreturn]] void mainDocumentError(int64_t len) __attribute__((noinline));
-[[noreturn]] void notEnoughDocumentError(int32_t len, int64_t remaining) __attribute__((noinline));
-
-void versionError(uint16_t version) {
- throw DeserializeException(make_string( "Unrecognized serialization version %d", version), VESPA_STRLOC);
-}
-
-void mainDocumentError(int64_t len) {
- throw DeserializeException(make_string(
- "Document lengths past %i is not supported. Corrupt data said length is %" PRId64 " bytes",
- std::numeric_limits<int>::max(), len), VESPA_STRLOC);
-}
-
-void notEnoughDocumentError(int32_t len, int64_t remaining) {
- throw DeserializeException(make_string( "Buffer said document length is %d bytes, but only %" PRId64 " bytes remain in buffer", len, remaining));
-}
-
-}
-
-void
-Document::deserializeDocHeader(ByteBuffer& buffer, DocumentId& id) {
- int16_t version;
- int32_t len;
- buffer.getShortNetwork(version);
-
- if ( ! isLegalVersion(version) ) {
- versionError(version);
- } else if (version < 7) {
- int64_t tmpLen = 0;
- buffer.getInt2_4_8Bytes(tmpLen);
- if (tmpLen > std::numeric_limits<int>::max()) {
- mainDocumentError(tmpLen);
- } else {
- len = static_cast<int32_t>(tmpLen)
- - ByteBuffer::getSerializedSize2_4_8Bytes(tmpLen)
- - sizeof(uint16_t);
- }
- } else {
- buffer.getIntNetwork(len);
- }
-
- if (len > (long)buffer.getRemaining()) {
- notEnoughDocumentError(len, buffer.getRemaining());
- } else {
- nbostream stream(buffer.getBufferAtPos(), buffer.getRemaining());
- id = DocumentId(stream);
- buffer.incPos(stream.rp());
- unsigned char contentByte;
- buffer.getByte(contentByte);
- }
-}
-
-void Document::serializeHeader(ByteBuffer& buffer) const {
- nbostream stream;
- serializeHeader(stream);
- buffer.putBytes(stream.peek(), stream.size());
-}
-
void Document::serializeHeader(nbostream& stream) const {
VespaDocumentSerializer serializer(stream);
serializer.write(*this, WITHOUT_BODY);
}
-void Document::serializeBody(ByteBuffer& buffer) const {
- nbostream stream;
- serializeBody(stream);
- buffer.putBytes(stream.peek(), stream.size());
-}
-
bool Document::hasBodyField() const {
for (document::StructuredFieldValue::const_iterator it(getFields().begin()), mt(getFields().end());
it != mt;
@@ -366,38 +241,26 @@ void Document::deserialize(const DocumentTypeRepo& repo, vespalib::nbostream & o
}
}
-void Document::deserialize(const DocumentTypeRepo& repo, ByteBuffer& data) {
- nbostream stream(data.getBufferAtPos(), data.getRemaining());
- deserialize(repo, stream);
- data.incPos(data.getRemaining() - stream.size());
-}
-
-void Document::deserialize(const DocumentTypeRepo& repo, ByteBuffer& header, ByteBuffer& body) {
+void Document::deserialize(const DocumentTypeRepo& repo, vespalib::nbostream & header, vespalib::nbostream & body) {
deserializeHeader(repo, header);
deserializeBody(repo, body);
}
-void Document::deserializeHeader(const DocumentTypeRepo& repo,
- ByteBuffer& header) {
- nbostream stream(header.getBufferAtPos(), header.getRemaining());
+void Document::deserializeHeader(const DocumentTypeRepo& repo, vespalib::nbostream & stream) {
VespaDocumentDeserializer deserializer(repo, stream, 0);
deserializer.read(*this);
- header.incPos(header.getRemaining() - stream.size());
}
-void Document::deserializeBody(const DocumentTypeRepo& repo, ByteBuffer& body) {
- nbostream body_stream(body.getBufferAtPos(), body.getRemaining());
- VespaDocumentDeserializer
- body_deserializer(repo, body_stream, getFields().getVersion());
- body_deserializer.readStructNoReset(getFields());
- body.incPos(body.getRemaining() - body_stream.size());
+void Document::deserializeBody(const DocumentTypeRepo& repo, vespalib::nbostream & stream) {
+ VespaDocumentDeserializer deserializer(repo, stream, getFields().getVersion());
+ deserializer.readStructNoReset(getFields());
}
size_t
Document::getSerializedSize() const
{
// Temporary non-optimal (but guaranteed correct) implementation.
- return serialize()->getLength();
+ return serialize().size();
}
StructuredFieldValue::StructuredIterator::UP
diff --git a/document/src/vespa/document/fieldvalue/document.h b/document/src/vespa/document/fieldvalue/document.h
index f0f86f75c4a..23b97a2a56d 100644
--- a/document/src/vespa/document/fieldvalue/document.h
+++ b/document/src/vespa/document/fieldvalue/document.h
@@ -44,7 +44,6 @@ public:
Document(const Document&);
Document(const DataType &, DocumentId id);
Document(const DocumentTypeRepo& repo, vespalib::nbostream& stream);
- Document(const DocumentTypeRepo& repo, ByteBuffer& buffer);
~Document() override;
void setRepo(const DocumentTypeRepo & repo);
@@ -82,21 +81,6 @@ public:
bool hasChanged() const override;
- /**
- * Returns a pointer to the Id of a serialized document, without performing
- * the deserialization. buffer must point to the start position of the
- * serialization. If the buffer doesn't have enough data remaining to have
- * a legal Id in it, method returns NULL.
- */
- static DocumentId getIdFromSerialized(ByteBuffer&);
-
- /**
- * Returns a pointer to the document type of a serialized header, without
- * performing the deserialization. Buffer must point to the start position
- * of the serialization.
- */
- static const DocumentType *getDocTypeFromSerialized(const DocumentTypeRepo&, ByteBuffer&);
-
// FieldValue implementation.
FieldValue& assign(const FieldValue&) override;
int compare(const FieldValue& other) const override;
@@ -104,20 +88,13 @@ public:
void printXml(XmlOutputStream& out) const override;
void print(std::ostream& out, bool verbose, const std::string& indent) const override;
- // Specialized serialization functions
- void serializeHeader(ByteBuffer& buffer) const;
+ // Specialized serialization functions, Only used for testing legacy stuff
void serializeHeader(vespalib::nbostream& stream) const;
-
- void serializeBody(ByteBuffer& buffer) const;
void serializeBody(vespalib::nbostream& stream) const;
- /** Deserialize document contained in given bytebuffer. */
- void deserialize(const DocumentTypeRepo& repo, ByteBuffer& data);
void deserialize(const DocumentTypeRepo& repo, vespalib::nbostream & os);
/** Deserialize document contained in given bytebuffers. */
- void deserialize(const DocumentTypeRepo& repo, ByteBuffer& body, ByteBuffer& header);
- void deserializeHeader(const DocumentTypeRepo& repo, ByteBuffer& header);
- void deserializeBody(const DocumentTypeRepo& repo, ByteBuffer& body);
+ void deserialize(const DocumentTypeRepo& repo, vespalib::nbostream & body, vespalib::nbostream & header);
size_t getSerializedSize() const;
@@ -133,6 +110,8 @@ public:
void setFieldValue(const Field& field, FieldValue::UP data) override;
private:
+ void deserializeHeader(const DocumentTypeRepo& repo, vespalib::nbostream & header);
+ void deserializeBody(const DocumentTypeRepo& repo, vespalib::nbostream & body);
bool hasBodyField() const;
bool hasFieldValue(const Field& field) const override { return _fields.hasValue(field); }
void removeFieldValue(const Field& field) override { _fields.remove(field); }
@@ -140,9 +119,6 @@ private:
bool getFieldValue(const Field& field, FieldValue& value) const override { return _fields.getValue(field, value); }
StructuredIterator::UP getIterator(const Field* first) const override;
-
- static void deserializeDocHeader(ByteBuffer& buffer, DocumentId& id);
- static const DocumentType *deserializeDocHeaderAndType(const DocumentTypeRepo& repo, ByteBuffer& buffer, DocumentId& id);
};
} // document
diff --git a/document/src/vespa/document/fieldvalue/fieldvalue.cpp b/document/src/vespa/document/fieldvalue/fieldvalue.cpp
index 999747688eb..c41f6cbb616 100644
--- a/document/src/vespa/document/fieldvalue/fieldvalue.cpp
+++ b/document/src/vespa/document/fieldvalue/fieldvalue.cpp
@@ -36,21 +36,15 @@ void FieldValue::serialize(nbostream &stream) const {
}
void FieldValue::serialize(ByteBuffer& buffer) const {
- nbostream stream;
- serialize(stream);
+ nbostream stream = serialize();
buffer.putBytes(stream.peek(), stream.size());
}
-std::unique_ptr<ByteBuffer> FieldValue::serialize() const {
+nbostream
+FieldValue::serialize() const {
nbostream stream;
serialize(stream);
-
- nbostream::Buffer buf;
- stream.swap(buf);
- size_t sz = buf.size();
- auto bb = std::make_unique<ByteBuffer>(nbostream::Buffer::stealAlloc(std::move(buf)), sz);
- bb->setPos(sz);
- return bb;
+ return stream;
}
size_t
diff --git a/document/src/vespa/document/fieldvalue/fieldvalue.h b/document/src/vespa/document/fieldvalue/fieldvalue.h
index a152f74cc09..4b754f09cd6 100644
--- a/document/src/vespa/document/fieldvalue/fieldvalue.h
+++ b/document/src/vespa/document/fieldvalue/fieldvalue.h
@@ -74,7 +74,7 @@ public:
void serialize(vespalib::nbostream &stream) const;
void serialize(ByteBuffer& buffer) const;
- std::unique_ptr<ByteBuffer> serialize() const;
+ vespalib::nbostream serialize() const;
/**
* Compares this fieldvalue with another fieldvalue.
diff --git a/document/src/vespa/document/fieldvalue/serializablearray.h b/document/src/vespa/document/fieldvalue/serializablearray.h
index 2f7d65938aa..1e2bf5706bf 100644
--- a/document/src/vespa/document/fieldvalue/serializablearray.h
+++ b/document/src/vespa/document/fieldvalue/serializablearray.h
@@ -26,7 +26,6 @@
namespace document {
-class SerializableArrayIterator;
class ByteBuffer;
namespace serializablearray {
diff --git a/document/src/vespa/document/fieldvalue/structfieldvalue.cpp b/document/src/vespa/document/fieldvalue/structfieldvalue.cpp
index 87c8d09648c..a011f9d8949 100644
--- a/document/src/vespa/document/fieldvalue/structfieldvalue.cpp
+++ b/document/src/vespa/document/fieldvalue/structfieldvalue.cpp
@@ -183,7 +183,7 @@ StructFieldValue::getFieldValue(const Field& field) const
if (buf.size() != 0) {
nbostream stream(buf.c_str(), buf.size());
FieldValue::UP value(field.getDataType().createFieldValue());
- if ((_repo == NULL) && (_doc_type != NULL)) {
+ if ((_repo == nullptr) && (_doc_type != nullptr)) {
std::unique_ptr<const DocumentTypeRepo> tmpRepo(new DocumentTypeRepo(*_doc_type));
createFV(*value, *tmpRepo, stream, *_doc_type, _version);
} else {
@@ -216,7 +216,7 @@ StructFieldValue::getFieldValue(const Field& field, FieldValue& value) const
vespalib::ConstBufferRef buf = getRawField(fieldId);
if (buf.size() > 0) {
nbostream_longlivedbuf stream(buf.c_str(), buf.size());
- if ((_repo == NULL) && (_doc_type != NULL)) {
+ if ((_repo == nullptr) && (_doc_type != nullptr)) {
std::unique_ptr<const DocumentTypeRepo> tmpRepo(new DocumentTypeRepo(*_doc_type));
createFV(value, *tmpRepo, stream, *_doc_type, _version);
} else {
@@ -239,14 +239,29 @@ StructFieldValue::hasFieldValue(const Field& field) const
return false;
}
+namespace {
+
+std::unique_ptr<ByteBuffer>
+serializeDoc(const FieldValue & fv) {
+ nbostream stream = fv.serialize();
+ nbostream::Buffer buf;
+ stream.swap(buf);
+ size_t sz = buf.size();
+ auto bb = std::make_unique<ByteBuffer>(nbostream::Buffer::stealAlloc(std::move(buf)), sz);
+ bb->setPos(sz);
+ return bb;
+}
+
+}
void
StructFieldValue::setFieldValue(const Field& field, FieldValue::UP value)
{
int fieldId = field.getId();
- std::unique_ptr<ByteBuffer> serialized(value->serialize());
+
+ std::unique_ptr<ByteBuffer> serialized = serializeDoc(*value);
serialized->flip();
if (_chunks.empty()) {
- _chunks.push_back(SerializableArray::UP(new SerializableArray()));
+ _chunks.push_back(std::make_unique<SerializableArray>());
}
_chunks.back().set(fieldId, std::move(serialized));
@@ -274,7 +289,7 @@ StructFieldValue::clear()
FieldValue&
StructFieldValue::assign(const FieldValue& value)
{
- const StructFieldValue& other(dynamic_cast<const StructFieldValue&>(value));
+ const auto & other(dynamic_cast<const StructFieldValue&>(value));
return operator=(other);
}
@@ -285,7 +300,7 @@ StructFieldValue::compare(const FieldValue& otherOrg) const
if (comp != 0) {
return comp;
}
- const StructFieldValue& other = static_cast<const StructFieldValue&>(otherOrg);
+ const auto & other = static_cast<const StructFieldValue&>(otherOrg);
std::vector<int> a;
getRawFieldIds(a);
@@ -315,9 +330,9 @@ StructFieldValue::compare(const FieldValue& otherOrg) const
uint32_t
StructFieldValue::calculateChecksum() const
{
- ByteBuffer::UP buffer(serialize());
+ nbostream buffer(serialize());
vespalib::crc_32_type calculator;
- calculator.process_bytes(buffer->getBuffer(), buffer->getPos());
+ calculator.process_bytes(buffer.peek(), buffer.size());
return calculator.checksum();
}
@@ -386,7 +401,7 @@ struct StructFieldValue::FieldIterator : public StructuredIterator {
std::vector<int> _ids;
std::vector<int>::iterator _cur;
- FieldIterator(const StructFieldValue& s)
+ explicit FieldIterator(const StructFieldValue& s)
: _struct(s),
_ids(),
_cur(_ids.begin())
@@ -412,7 +427,7 @@ struct StructFieldValue::FieldIterator : public StructuredIterator {
LOG(debug, "struct data type: %s", _struct.getType().toString(true).c_str());
}
}
- return 0;
+ return nullptr;
}
};
@@ -421,10 +436,10 @@ StructFieldValue::getIterator(const Field* toFind) const
{
StructuredIterator::UP ret;
- FieldIterator *fi = new FieldIterator(*this);
+ auto *fi = new FieldIterator(*this);
ret.reset(fi);
- if (toFind != NULL) {
+ if (toFind != nullptr) {
fi->skipTo(toFind->getId());
}
return ret;
diff --git a/documentapi/src/vespa/documentapi/messagebus/messages/visitor.cpp b/documentapi/src/vespa/documentapi/messagebus/messages/visitor.cpp
index 43ad30ea24f..c891d9a316d 100644
--- a/documentapi/src/vespa/documentapi/messagebus/messages/visitor.cpp
+++ b/documentapi/src/vespa/documentapi/messagebus/messages/visitor.cpp
@@ -3,6 +3,7 @@
#include "visitor.h"
#include <climits>
#include <vespa/document/bucket/fixed_bucket_spaces.h>
+#include <vespa/vespalib/objects/nbostream.h>
using document::FixedBucketSpaces;
@@ -56,7 +57,7 @@ CreateVisitorMessage::~CreateVisitorMessage() = default;
DocumentReply::UP
CreateVisitorMessage::doCreateReply() const
{
- return DocumentReply::UP(new CreateVisitorReply(DocumentProtocol::REPLY_CREATEVISITOR));
+ return std::make_unique<CreateVisitorReply>(DocumentProtocol::REPLY_CREATEVISITOR);
}
uint32_t
@@ -65,11 +66,7 @@ CreateVisitorMessage::getType() const
return DocumentProtocol::MESSAGE_CREATEVISITOR;
}
-DestroyVisitorMessage::DestroyVisitorMessage() :
- DocumentMessage(),
- _instanceId()
-{
-}
+DestroyVisitorMessage::DestroyVisitorMessage() = default;
DestroyVisitorMessage::DestroyVisitorMessage(const string& instanceId) :
DocumentMessage(),
@@ -77,8 +74,7 @@ DestroyVisitorMessage::DestroyVisitorMessage(const string& instanceId) :
{
}
-DestroyVisitorMessage::~DestroyVisitorMessage() {
-}
+DestroyVisitorMessage::~DestroyVisitorMessage() = default;
DocumentReply::UP
DestroyVisitorMessage::doCreateReply() const
@@ -104,20 +100,13 @@ CreateVisitorReply::CreateVisitorReply(uint32_t type) :
{
}
-VisitorInfoMessage::VisitorInfoMessage() :
- VisitorMessage(),
- _finishedBuckets(),
- _errorMessage()
-{
-}
-
-VisitorInfoMessage::~VisitorInfoMessage() {
-}
+VisitorInfoMessage::VisitorInfoMessage() = default;
+VisitorInfoMessage::~VisitorInfoMessage() = default;
DocumentReply::UP
VisitorInfoMessage::doCreateReply() const
{
- return DocumentReply::UP(new VisitorReply(DocumentProtocol::REPLY_VISITORINFO));
+ return std::make_unique<VisitorReply>(DocumentProtocol::REPLY_VISITORINFO);
}
uint32_t
@@ -141,7 +130,7 @@ MapVisitorMessage::getApproxSize() const
DocumentReply::UP
MapVisitorMessage::doCreateReply() const
{
- return DocumentReply::UP(new VisitorReply(DocumentProtocol::REPLY_MAPVISITOR));
+ return std::make_unique<VisitorReply>(DocumentProtocol::REPLY_MAPVISITOR);
}
uint32_t MapVisitorMessage::getType() const
@@ -158,7 +147,7 @@ DocumentListMessage::Entry::Entry(int64_t timestamp,
document::Document::SP doc,
bool removeEntry) :
_timestamp(timestamp),
- _document(doc),
+ _document(std::move(doc)),
_removeEntry(removeEntry)
{
// empty
@@ -176,7 +165,9 @@ DocumentListMessage::Entry::Entry(const document::DocumentTypeRepo &repo,
document::ByteBuffer& buf)
{
buf.getLongNetwork(_timestamp);
- _document.reset(new document::Document(repo, buf));
+ vespalib::nbostream stream(buf.getBufferAtPos(), buf.getRemaining());
+ _document = std::make_unique<document::Document>(repo, stream);
+ buf.incPos(buf.getRemaining() - stream.size());
uint8_t b;
buf.getByte(b);
_removeEntry = b>0;
@@ -194,7 +185,7 @@ uint32_t
DocumentListMessage::Entry::getSerializedSize() const
{
return sizeof(int64_t) + sizeof(uint8_t)
- + _document->serialize()->getLength();
+ + _document->getSerializedSize();
}
DocumentListMessage::DocumentListMessage() :
@@ -214,7 +205,7 @@ DocumentListMessage::DocumentListMessage(document::BucketId bid) :
DocumentReply::UP
DocumentListMessage::doCreateReply() const
{
- return DocumentReply::UP(new VisitorReply(DocumentProtocol::REPLY_DOCUMENTLIST));
+ return std::make_unique<VisitorReply>(DocumentProtocol::REPLY_DOCUMENTLIST);
}
uint32_t
diff --git a/documentapi/src/vespa/documentapi/messagebus/routablefactories60.cpp b/documentapi/src/vespa/documentapi/messagebus/routablefactories60.cpp
index 797f55120fc..1f950ae166c 100644
--- a/documentapi/src/vespa/documentapi/messagebus/routablefactories60.cpp
+++ b/documentapi/src/vespa/documentapi/messagebus/routablefactories60.cpp
@@ -476,7 +476,9 @@ RoutableFactories60::GetDocumentReplyFactory::doDecode(document::ByteBuffer &buf
bool hasDocument = decodeBoolean(buf);
document::Document * document = nullptr;
if (hasDocument) {
- auto doc = std::make_shared<document::Document>(_repo, buf);
+ vespalib::nbostream stream(buf.getBufferAtPos(), buf.getRemaining());
+ auto doc = std::make_shared<document::Document>(_repo, stream);
+ buf.incPos(buf.getRemaining() - stream.size());
document = doc.get();
reply->setDocument(std::move(doc));
}
@@ -540,7 +542,9 @@ RoutableFactories60::MapVisitorReplyFactory::doEncode(const DocumentReply &, ves
void
RoutableFactories60::PutDocumentMessageFactory::decodeInto(PutDocumentMessage & msg, document::ByteBuffer & buf) const {
- msg.setDocument(make_shared<document::Document>(_repo, buf));
+ vespalib::nbostream stream(buf.getBufferAtPos(), buf.getRemaining());
+ msg.setDocument(make_shared<document::Document>(_repo, stream));
+ buf.incPos(buf.getRemaining() - stream.size());
msg.setTimestamp(static_cast<uint64_t>(decodeLong(buf)));
decodeTasCondition(msg, buf);
}
diff --git a/persistence/src/vespa/persistence/conformancetest/conformancetest.cpp b/persistence/src/vespa/persistence/conformancetest/conformancetest.cpp
index 937431fb7dd..10f03b8f8e4 100644
--- a/persistence/src/vespa/persistence/conformancetest/conformancetest.cpp
+++ b/persistence/src/vespa/persistence/conformancetest/conformancetest.cpp
@@ -260,7 +260,7 @@ verifyDocs(const std::vector<DocAndTimestamp>& wanted,
<< entry.getDocument()->toString(true);
}
EXPECT_EQ(wanted[wantedIdx].timestamp, entry.getTimestamp());
- size_t serSize = wanted[wantedIdx].doc->serialize()->getLength();
+ size_t serSize = wanted[wantedIdx].doc->getSerializedSize();
EXPECT_EQ(serSize + sizeof(DocEntry), size_t(entry.getSize()));
EXPECT_EQ(serSize, size_t(entry.getDocumentSize()));
++wantedIdx;
diff --git a/storage/src/tests/visiting/visitormanagertest.cpp b/storage/src/tests/visiting/visitormanagertest.cpp
index b7eb7fee3ec..3f111bb53f7 100644
--- a/storage/src/tests/visiting/visitormanagertest.cpp
+++ b/storage/src/tests/visiting/visitormanagertest.cpp
@@ -337,7 +337,7 @@ int getTotalSerializedSize(const std::vector<document::Document::SP>& docs)
{
int total = 0;
for (size_t i = 0; i < docs.size(); ++i) {
- total += int(docs[i]->serialize()->getLength());
+ total += int(docs[i]->getSerializedSize());
}
return total;
}
diff --git a/storage/src/vespa/storage/persistence/mergehandler.cpp b/storage/src/vespa/storage/persistence/mergehandler.cpp
index 37e1d818bb8..1ef26a969ed 100644
--- a/storage/src/vespa/storage/persistence/mergehandler.cpp
+++ b/storage/src/vespa/storage/persistence/mergehandler.cpp
@@ -506,18 +506,11 @@ MergeHandler::fetchLocalData(
assert(doc != 0);
assertContainedInBucket(doc->getId(), bucket, idFactory);
e._docName = doc->getId().toString();
- {
- vespalib::nbostream stream;
- doc->serializeHeader(stream);
- e._headerBlob.resize(stream.size());
- memcpy(&e._headerBlob[0], stream.peek(), stream.size());
- }
- {
- vespalib::nbostream stream;
- doc->serializeBody(stream);
- e._bodyBlob.resize(stream.size());
- memcpy(&e._bodyBlob[0], stream.peek(), stream.size());
- }
+ vespalib::nbostream stream;
+ doc->serialize(stream);
+ e._headerBlob.resize(stream.size());
+ memcpy(&e._headerBlob[0], stream.peek(), stream.size());
+ e._bodyBlob.clear();
} else {
const DocumentId* docId = docEntry.getDocumentId();
assert(docId != 0);
@@ -556,11 +549,10 @@ MergeHandler::deserializeDiffDocument(
const api::ApplyBucketDiffCommand::Entry& e,
const document::DocumentTypeRepo& repo) const
{
- Document::UP doc(new Document);
- using document::ByteBuffer;
- ByteBuffer hbuf(&e._headerBlob[0], e._headerBlob.size());
+ auto doc = std::make_unique<Document>();
+ vespalib::nbostream hbuf(&e._headerBlob[0], e._headerBlob.size());
if (e._bodyBlob.size() > 0) {
- ByteBuffer bbuf(&e._bodyBlob[0], e._bodyBlob.size());
+ vespalib::nbostream bbuf(&e._bodyBlob[0], e._bodyBlob.size());
doc->deserialize(repo, hbuf, bbuf);
} else {
doc->deserialize(repo, hbuf);
diff --git a/storage/src/vespa/storage/visiting/recoveryvisitor.cpp b/storage/src/vespa/storage/visiting/recoveryvisitor.cpp
index 7c69a232af0..f9e0fa17d66 100644
--- a/storage/src/vespa/storage/visiting/recoveryvisitor.cpp
+++ b/storage/src/vespa/storage/visiting/recoveryvisitor.cpp
@@ -39,7 +39,7 @@ RecoveryVisitor::handleDocuments(const document::BucketId& bid,
LOG(debug, "Visitor %s handling block of %zu documents.",
_id.c_str(), entries.size());
- documentapi::DocumentListMessage* cmd = NULL;
+ documentapi::DocumentListMessage* cmd = nullptr;
{
CommandMap::iterator iter = _activeCommands.find(bid);
@@ -71,7 +71,7 @@ RecoveryVisitor::handleDocuments(const document::BucketId& bid,
}
}
- hitCounter.addHit(doc->getId(), doc->serialize()->getLength());
+ hitCounter.addHit(doc->getId(), doc->getSerializedSize());
int64_t timestamp = doc->getLastModified();
cmd->getDocuments().push_back(documentapi::DocumentListMessage::Entry(
diff --git a/storageapi/src/vespa/storageapi/mbusprot/protocolserialization7.cpp b/storageapi/src/vespa/storageapi/mbusprot/protocolserialization7.cpp
index bf56dd56db6..27b91836fd2 100644
--- a/storageapi/src/vespa/storageapi/mbusprot/protocolserialization7.cpp
+++ b/storageapi/src/vespa/storageapi/mbusprot/protocolserialization7.cpp
@@ -85,7 +85,7 @@ std::shared_ptr<document::Document> get_document(const protobuf::Document& src_d
const document::DocumentTypeRepo& type_repo)
{
if (!src_doc.payload().empty()) {
- document::ByteBuffer doc_buf(src_doc.payload().data(), src_doc.payload().size());
+ vespalib::nbostream doc_buf(src_doc.payload().data(), src_doc.payload().size());
return std::make_shared<document::Document>(type_repo, doc_buf);
}
return std::shared_ptr<document::Document>();
diff --git a/storageapi/src/vespa/storageapi/mbusprot/serializationhelper.h b/storageapi/src/vespa/storageapi/mbusprot/serializationhelper.h
index 08cec601cce..24cc3e4371d 100644
--- a/storageapi/src/vespa/storageapi/mbusprot/serializationhelper.h
+++ b/storageapi/src/vespa/storageapi/mbusprot/serializationhelper.h
@@ -87,9 +87,9 @@ public:
if (size == 0) {
return document::Document::UP();
} else {
- document::ByteBuffer bbuf(buf.getBufferAtPos(), size);
+ vespalib::nbostream stream(buf.getBufferAtPos(), size);
buf.incPos(size);
- return document::Document::UP(new document::Document(repo, bbuf));
+ return std::make_unique<document::Document>(repo, stream);
}
}
diff --git a/storageapi/src/vespa/storageapi/message/bucket.cpp b/storageapi/src/vespa/storageapi/message/bucket.cpp
index ee8aff31914..de47a52ca9d 100644
--- a/storageapi/src/vespa/storageapi/message/bucket.cpp
+++ b/storageapi/src/vespa/storageapi/message/bucket.cpp
@@ -3,6 +3,7 @@
#include "bucket.h"
#include <vespa/document/fieldvalue/document.h>
#include <vespa/vespalib/stllike/asciistream.h>
+#include <vespa/vespalib/objects/nbostream.h>
#include <vespa/vespalib/util/array.hpp>
#include <ostream>
#include <iterator>
@@ -319,7 +320,7 @@ ApplyBucketDiffCommand::Entry::print(
<< "), headerBlob(" << _headerBlob.size()
<< "), bodyBlob(" << _bodyBlob.size() << ")";
if (_headerBlob.size() > 0) {
- document::ByteBuffer buf(&_headerBlob[0],
+ vespalib::nbostream buf(&_headerBlob[0],
_headerBlob.size());
if (_repo) {
document::Document doc(*_repo, buf);
diff --git a/storageapi/src/vespa/storageapi/message/persistence.cpp b/storageapi/src/vespa/storageapi/message/persistence.cpp
index 54df92546a5..8b8dedda231 100644
--- a/storageapi/src/vespa/storageapi/message/persistence.cpp
+++ b/storageapi/src/vespa/storageapi/message/persistence.cpp
@@ -60,7 +60,7 @@ PutCommand::print(std::ostream& out, bool verbose, const std::string& indent) co
{
out << "Put(" << getBucketId() << ", " << _doc->getId()
<< ", timestamp " << _timestamp << ", size "
- << _doc->serialize()->getLength() << ")";
+ << _doc->getSerializedSize() << ")";
if (verbose) {
out << " {\n" << indent << " ";
_doc->print(out, verbose, indent + " ");