You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@avro.apache.org by th...@apache.org on 2013/12/15 17:50:01 UTC

svn commit: r1551029 - in /avro/trunk: CHANGES.txt lang/c++/api/Generic.hh lang/c++/impl/FileStream.cc lang/c++/impl/parsing/ResolvingDecoder.cc lang/c++/test/DataFileTests.cc

Author: thiru
Date: Sun Dec 15 16:50:00 2013
New Revision: 1551029

URL: http://svn.apache.org/r1551029
Log:
AVRO-1406 Avro C++ GenericRecord (GenericDatum, etc.) doesn't support getters and setters with field name argument

Modified:
    avro/trunk/CHANGES.txt
    avro/trunk/lang/c++/api/Generic.hh
    avro/trunk/lang/c++/impl/FileStream.cc
    avro/trunk/lang/c++/impl/parsing/ResolvingDecoder.cc
    avro/trunk/lang/c++/test/DataFileTests.cc

Modified: avro/trunk/CHANGES.txt
URL: http://svn.apache.org/viewvc/avro/trunk/CHANGES.txt?rev=1551029&r1=1551028&r2=1551029&view=diff
==============================================================================
--- avro/trunk/CHANGES.txt (original)
+++ avro/trunk/CHANGES.txt Sun Dec 15 16:50:00 2013
@@ -44,6 +44,8 @@ Trunk (not yet released)
     AVRO-1344. Java: Expose sync interval configuration in mapreduce API.
     (Rob Turner via cutting)
 
+    AVRO-1406. C++. GenericRecord (GenericDatum, etc.) doesn't support getters and setters with field name argument. (Iaroslav Zeigerman via thiru)
+
   BUG FIXES
 
     AVRO-1368. Fix SpecificDatumWriter to, when writing a string

Modified: avro/trunk/lang/c++/api/Generic.hh
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c%2B%2B/api/Generic.hh?rev=1551029&r1=1551028&r2=1551029&view=diff
==============================================================================
--- avro/trunk/lang/c++/api/Generic.hh (original)
+++ avro/trunk/lang/c++/api/Generic.hh Sun Dec 15 16:50:00 2013
@@ -249,6 +249,41 @@ public:
     }
 
     /**
+     * Returns index of the field with the given name \p name
+     */
+    size_t fieldIndex(const std::string& name) const { 
+        size_t index = 0;
+        if (!schema()->nameIndex(name, index)) {
+            throw Exception("Invalid field name: " + name);
+        }
+        return index;
+    }
+
+    /**
+     * Returns true if a field with the given name \p name is located in this record, 
+     * false otherwise
+     */
+    bool hasField(const std::string& name) const {
+        size_t index = 0;
+        return schema()->nameIndex(name, index);
+    }
+
+    /**
+     * Returns the field with the given name \p name.
+     */
+    const GenericDatum& field(const std::string& name) const {
+        return fieldAt(fieldIndex(name));
+    }
+
+    /**
+     * Returns the reference to the field with the given name \p name,
+     * which can be used to change the contents.
+     */
+    GenericDatum& field(const std::string& name) {
+        return fieldAt(fieldIndex(name));
+    }
+
+    /**
      * Returns the field at the given position \p pos.
      */
     const GenericDatum& fieldAt(size_t pos) const {
@@ -264,6 +299,14 @@ public:
     }
 
     /**
+     * Replaces the field with the given name \p name with \p v.
+     */
+    void setField(const std::string& name, const GenericDatum& v) {
+        // assertSameType(v, schema()->leafAt(pos)); 
+        return setFieldAt(fieldIndex(name), v);
+    }
+
+    /**
      * Replaces the field at the given position \p pos with \p v.
      */
     void setFieldAt(size_t pos, const GenericDatum& v) {

Modified: avro/trunk/lang/c++/impl/FileStream.cc
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c%2B%2B/impl/FileStream.cc?rev=1551029&r1=1551028&r2=1551029&view=diff
==============================================================================
--- avro/trunk/lang/c++/impl/FileStream.cc (original)
+++ avro/trunk/lang/c++/impl/FileStream.cc Sun Dec 15 16:50:00 2013
@@ -16,6 +16,7 @@
  * limitations under the License.
  */
 
+#include <fstream>
 #include "Stream.hh"
 #ifndef _WIN32
 #include "unistd.h"

Modified: avro/trunk/lang/c++/impl/parsing/ResolvingDecoder.cc
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c%2B%2B/impl/parsing/ResolvingDecoder.cc?rev=1551029&r1=1551028&r2=1551029&view=diff
==============================================================================
--- avro/trunk/lang/c++/impl/parsing/ResolvingDecoder.cc (original)
+++ avro/trunk/lang/c++/impl/parsing/ResolvingDecoder.cc Sun Dec 15 16:50:00 2013
@@ -60,7 +60,7 @@ using std::make_pair;
 typedef pair<NodePtr, NodePtr> NodePair;
 
 class ResolvingGrammarGenerator : public ValidatingGrammarGenerator {
-    Production doGenerate(const NodePtr& writer, const NodePtr& reader,
+    Production doGenerate2(const NodePtr& writer, const NodePtr& reader,
         map<NodePair, shared_ptr<Production> > &m,
         const map<NodePtr, shared_ptr<Production> > &m2);
     Production resolveRecords(const NodePtr& writer, const NodePtr& reader,
@@ -99,7 +99,7 @@ Symbol ResolvingGrammarGenerator::genera
     fixup(backup, m2);
 
     map<NodePair, shared_ptr<Production> > m;
-    Production main = doGenerate(rr, rw, m, m2);
+    Production main = doGenerate2(rr, rw, m, m2);
     fixup(main, m);
     return Symbol::rootSymbol(main, backup);
 }
@@ -183,7 +183,7 @@ Production ResolvingGrammarGenerator::re
             find_if(rf.begin(), rf.end(),
                 equalsFirst<string, size_t>(it->first));
         if (it2 != rf.end()) {
-            Production p = doGenerate(writer->leafAt(it->second),
+            Production p = doGenerate2(writer->leafAt(it->second),
                 reader->leafAt(it2->second), m, m2);
             copy(p.rbegin(), p.rend(), back_inserter(result));
             fieldOrder.push_back(it2->second);
@@ -219,7 +219,7 @@ Production ResolvingGrammarGenerator::re
     size_t c = writer->leaves();
     v.reserve(c);
     for (size_t i = 0; i < c; ++i) {
-        Production p = doGenerate(writer->leafAt(i), reader, m, m2);
+        Production p = doGenerate2(writer->leafAt(i), reader, m, m2);
         v.push_back(p);
     }
     Symbol r[] = {
@@ -229,7 +229,7 @@ Production ResolvingGrammarGenerator::re
     return Production(r, r + 2);
 }
 
-Production ResolvingGrammarGenerator::doGenerate(
+Production ResolvingGrammarGenerator::doGenerate2(
     const NodePtr& writer, const NodePtr& reader,
     map<NodePair, shared_ptr<Production> > &m,
     const map<NodePtr, shared_ptr<Production> > &m2)
@@ -298,14 +298,14 @@ Production ResolvingGrammarGenerator::do
                 Symbol r[] = {
                     Symbol::arrayEndSymbol(),
                     Symbol::repeater(
-                        doGenerate(writer->leafAt(0), reader->leafAt(0), m, m2),
+                        doGenerate2(writer->leafAt(0), reader->leafAt(0), m, m2),
                         p, true),
                     Symbol::arrayStartSymbol() };
                 return Production(r, r + 3);
             }
         case AVRO_MAP:
             {
-                Production v = doGenerate(writer->leafAt(1),
+                Production v = doGenerate2(writer->leafAt(1),
                     reader->leafAt(1), m, m2);
                 v.push_back(Symbol::stringSymbol());
 
@@ -369,7 +369,7 @@ Production ResolvingGrammarGenerator::do
             {
                 int j = bestBranch(writer, reader);
                 if (j >= 0) {
-                    Production p = doGenerate(writer, reader->leafAt(j), m, m2);
+                    Production p = doGenerate2(writer, reader->leafAt(j), m, m2);
                     Symbol r[] = {
                         Symbol::unionAdjustSymbol(j, p),
                         Symbol::unionSymbol()

Modified: avro/trunk/lang/c++/test/DataFileTests.cc
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c%2B%2B/test/DataFileTests.cc?rev=1551029&r1=1551028&r2=1551029&view=diff
==============================================================================
--- avro/trunk/lang/c++/test/DataFileTests.cc (original)
+++ avro/trunk/lang/c++/test/DataFileTests.cc Sun Dec 15 16:50:00 2013
@@ -177,6 +177,24 @@ public:
         df.close();
     }
 
+    void testWriteGenericByName() {
+        avro::DataFileWriter<Pair> df(filename, writerSchema, 100);
+        int64_t re = 3;
+        int64_t im = 5;
+        Pair p(writerSchema, GenericDatum());
+
+        GenericDatum& c = p.second;
+        c = GenericDatum(writerSchema.root());
+        GenericRecord& r = c.value<GenericRecord>();
+
+        for (int i = 0; i < count; ++i, re *= im, im += 3) {
+            r.field("re") = re;
+            r.field("im") = im;
+            df.write(p);
+        }
+        df.close();
+    }
+
     void testWriteDouble() {
         avro::DataFileWriter<ComplexDouble> df(filename, writerSchema, 100);
         double re = 3.0;
@@ -257,6 +275,33 @@ public:
         BOOST_CHECK_EQUAL(i, count);
     }
 
+    void testReaderGenericByName() {
+        avro::DataFileReader<Pair> df(filename, writerSchema);
+        int i = 0;
+        Pair p(writerSchema, GenericDatum());
+        int64_t re = 3;
+        int64_t im = 5;
+        
+        const GenericDatum& ci = p.second;
+        while (df.read(p)) {
+            BOOST_REQUIRE_EQUAL(ci.type(), avro::AVRO_RECORD);
+            const GenericRecord& r = ci.value<GenericRecord>();
+            const size_t n = 2;
+            BOOST_REQUIRE_EQUAL(r.fieldCount(), n);
+            const GenericDatum& f0 = r.field("re");
+            BOOST_REQUIRE_EQUAL(f0.type(), avro::AVRO_LONG);
+            BOOST_CHECK_EQUAL(f0.value<int64_t>(), re);
+
+            const GenericDatum& f1 = r.field("im");
+            BOOST_REQUIRE_EQUAL(f1.type(), avro::AVRO_LONG);
+            BOOST_CHECK_EQUAL(f1.value<int64_t>(), im);
+            re *= im;
+            im += 3;
+            ++i;
+        }
+        BOOST_CHECK_EQUAL(i, count);
+    }
+
     void testReaderGenericProjection() {
         avro::DataFileReader<Pair> df(filename, readerSchema);
         int i = 0;
@@ -350,6 +395,7 @@ void addReaderTests(test_suite* ts, cons
     ts->add(BOOST_CLASS_TEST_CASE(&DataFileTest::testReadFull, t));
     ts->add(BOOST_CLASS_TEST_CASE(&DataFileTest::testReadProjection, t));
     ts->add(BOOST_CLASS_TEST_CASE(&DataFileTest::testReaderGeneric, t));
+    ts->add(BOOST_CLASS_TEST_CASE(&DataFileTest::testReaderGenericByName, t));
     ts->add(BOOST_CLASS_TEST_CASE(&DataFileTest::testReaderGenericProjection,
         t));
     ts->add(BOOST_CLASS_TEST_CASE(&DataFileTest::testCleanup, t));
@@ -380,5 +426,9 @@ init_unit_test_suite( int argc, char* ar
     ts->add(BOOST_CLASS_TEST_CASE(&DataFileTest::testTruncate, t4));
     ts->add(BOOST_CLASS_TEST_CASE(&DataFileTest::testCleanup, t4));
 
+    shared_ptr<DataFileTest> t5(new DataFileTest("test5.df", sch, isch));
+    ts->add(BOOST_CLASS_TEST_CASE(&DataFileTest::testWriteGenericByName, t5));
+    addReaderTests(ts, t5);
+
     return ts;
 }