diff options
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 + " "); |