avro-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From bru...@apache.org
Subject svn commit: r1057676 - in /avro/trunk: CHANGES.txt lang/c/src/avro.h lang/c/src/datum.c lang/c/src/datum.h lang/c/src/schema.c lang/c/src/schema.h lang/c/tests/test_avro_data.c lang/c/tests/test_avro_schema.c
Date Tue, 11 Jan 2011 14:56:52 GMT
Author: brucem
Date: Tue Jan 11 14:56:51 2011
New Revision: 1057676

URL: http://svn.apache.org/viewvc?rev=1057676&view=rev
Log:
AVRO-727. This patchs several missing accessor and mutator methods for Avro
schemas and data instances.

For the most part, their definitions are straightforward.  Some notes for the
more interesting cases:

  - You can create the appropriate avro_datum_t instance for an
    arbitrary schema with the new avro_datum_from_schema() function.
    For records, this includes creating a datum instance for each of the
    record's fields.  Arrays and maps are initially created empty, while
    a union is created with none of its branches initially selected.
    This prevents the function from going into an endless loop for
    recursive schemas.

  - The active branch of a union can now be changed.  If the desired
    branch is already active, this has no result.  Otherwise, a new
    avro_datum_t is created for the new branch.

  - Map values can now be accessed by index as well as by key.  The
    index of a map entry is based on the order that it was added to the
    map.

  - Enum values can be retrieved or set either by integer value or by
    symbol name.

A couple of the new functions need access to the schema of a datum in
order to work.  These functions take in the schema instance as an extra
parameter.  A better solution might be to include a reference to a
schema object in each avro_datum_t instance.

Modified:
    avro/trunk/CHANGES.txt
    avro/trunk/lang/c/src/avro.h
    avro/trunk/lang/c/src/datum.c
    avro/trunk/lang/c/src/datum.h
    avro/trunk/lang/c/src/schema.c
    avro/trunk/lang/c/src/schema.h
    avro/trunk/lang/c/tests/test_avro_data.c
    avro/trunk/lang/c/tests/test_avro_schema.c

Modified: avro/trunk/CHANGES.txt
URL: http://svn.apache.org/viewvc/avro/trunk/CHANGES.txt?rev=1057676&r1=1057675&r2=1057676&view=diff
==============================================================================
--- avro/trunk/CHANGES.txt (original)
+++ avro/trunk/CHANGES.txt Tue Jan 11 14:56:51 2011
@@ -94,6 +94,9 @@ Avro 1.5.0 (unreleased)
     AVRO-630. C: Add size accessors for map and list data. (Douglas Creager
     via brucem)
 
+    AVRO-727. C: Add many new accessor and mutator functions. (Douglas Creager
+    via brucem)
+
   BUG FIXES
 
     AVRO-675. C: Bytes and fixed setters don't update datum size.

Modified: avro/trunk/lang/c/src/avro.h
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/src/avro.h?rev=1057676&r1=1057675&r2=1057676&view=diff
==============================================================================
--- avro/trunk/lang/c/src/avro.h (original)
+++ avro/trunk/lang/c/src/avro.h Tue Jan 11 14:56:51 2011
@@ -110,21 +110,38 @@ avro_schema_t avro_schema_null(void);
 avro_schema_t avro_schema_record(const char *name, const char *space);
 avro_schema_t avro_schema_record_field_get(const avro_schema_t
 					   record, const char *field_name);
+const char *avro_schema_record_field_name(const avro_schema_t schema, int index);
+avro_schema_t avro_schema_record_field_get_by_index
+(const avro_schema_t record, int index);
 int avro_schema_record_field_append(const avro_schema_t record,
 				    const char *field_name,
 				    const avro_schema_t type);
+size_t avro_schema_record_size(const avro_schema_t record);
 
 avro_schema_t avro_schema_enum(const char *name);
+const char *avro_schema_enum_get(const avro_schema_t enump,
+				 int index);
+int avro_schema_enum_get_by_name(const avro_schema_t enump,
+				 const char *symbol_name);
 int avro_schema_enum_symbol_append(const avro_schema_t
 				   enump, const char *symbol);
 
 avro_schema_t avro_schema_fixed(const char *name, const int64_t len);
+int64_t avro_schema_fixed_size(const avro_schema_t fixed);
+
 avro_schema_t avro_schema_map(const avro_schema_t values);
+avro_schema_t avro_schema_map_values(avro_schema_t map);
+
 avro_schema_t avro_schema_array(const avro_schema_t items);
+avro_schema_t avro_schema_array_items(avro_schema_t array);
 
 avro_schema_t avro_schema_union(void);
 int avro_schema_union_append(const avro_schema_t
 			     union_schema, const avro_schema_t schema);
+avro_schema_t avro_schema_union_branch(avro_schema_t union_schema,
+				       int branch_index);
+avro_schema_t avro_schema_union_branch_by_name
+(avro_schema_t union_schema, int *branch_index, const char *name);
 
 avro_schema_t avro_schema_link(avro_schema_t schema);
 
@@ -198,6 +215,13 @@ avro_datum_t avro_map(void);
 avro_datum_t avro_array(void);
 avro_datum_t avro_union(int64_t discriminant, const avro_datum_t datum);
 
+/*
+ * Constructs a new avro_datum_t instance that's appropriate for holding
+ * values of the given schema.
+ */
+
+avro_datum_t avro_datum_from_schema(const avro_schema_t schema);
+
 /* getters */
 int avro_string_get(avro_datum_t datum, char **p);
 int avro_bytes_get(avro_datum_t datum, char **bytes, int64_t * size);
@@ -207,15 +231,34 @@ int avro_float_get(avro_datum_t datum, f
 int avro_double_get(avro_datum_t datum, double *d);
 int avro_boolean_get(avro_datum_t datum, int8_t * i);
 
+int avro_enum_get(const avro_datum_t datum);
+const char *avro_enum_get_name(const avro_datum_t datum,
+			       const avro_schema_t schema);
 int avro_fixed_get(avro_datum_t datum, char **bytes, int64_t * size);
 int avro_record_get(const avro_datum_t record, const char *field_name,
 		    avro_datum_t * value);
 int avro_map_get(const avro_datum_t datum, const char *key,
 		 avro_datum_t * value);
+/*
+ * For maps, the "index" for each entry is based on the order that they
+ * were added to the map.
+ */
+int avro_map_get_key(const avro_datum_t datum, int index,
+		     const char **key);
 size_t avro_map_size(const avro_datum_t datum);
 int avro_array_get(const avro_datum_t datum, int64_t index, avro_datum_t * value);
 size_t avro_array_size(const avro_datum_t datum);
 
+/*
+ * These accessors allow you to query the current branch of a union
+ * value, returning either the branch's discriminant value or the
+ * avro_datum_t of the branch.  A union value can be uninitialized, in
+ * which case the discriminant will be -1 and the datum NULL.
+ */
+
+int64_t avro_union_discriminant(const avro_datum_t datum);
+avro_datum_t avro_union_current_branch(avro_datum_t datum);
+
 /* setters */
 int avro_string_set(avro_datum_t datum, const char *p);
 int avro_givestring_set(avro_datum_t datum, const char *p);
@@ -233,18 +276,37 @@ int avro_float_set(avro_datum_t datum, c
 int avro_double_set(avro_datum_t datum, const double d);
 int avro_boolean_set(avro_datum_t datum, const int8_t i);
 
+int avro_enum_set(avro_datum_t datum, const int symbol_value);
+int avro_enum_set_name(avro_datum_t datum, avro_schema_t schema,
+		       const char *symbol_name);
 int avro_fixed_set(avro_datum_t datum, const char *bytes, const int64_t size);
 int avro_givefixed_set(avro_datum_t datum, const char *bytes,
 		       const int64_t size);
 int avro_wrapfixed_set(avro_datum_t datum, const char *bytes,
 		       const int64_t size);
 
-int avro_record_set(const avro_datum_t record, const char *field_name,
-		    const avro_datum_t value);
-int avro_map_set(const avro_datum_t map, const char *key,
-		 const avro_datum_t value);
-int avro_array_append_datum(const avro_datum_t array_datum,
-			    const avro_datum_t datum);
+int avro_record_set(avro_datum_t record, const char *field_name,
+		    avro_datum_t value);
+int avro_map_set(avro_datum_t map, const char *key,
+		 avro_datum_t value);
+int avro_array_append_datum(avro_datum_t array_datum,
+			    avro_datum_t datum);
+
+/*
+ * This function selects the active branch of a union value, and can be
+ * safely called on an existing union to change the current branch.  If
+ * the branch changes, we'll automatically construct a new avro_datum_t
+ * for the new branch's schema type.  If the desired branch is already
+ * the active branch of the union, we'll leave the existing datum
+ * instance as-is.  The branch datum will be placed into the "branch"
+ * parameter, regardless of whether we have to create a new datum
+ * instance or not.
+ */
+
+int avro_union_set_discriminant(avro_datum_t unionp,
+				avro_schema_t schema,
+				int discriminant,
+				avro_datum_t *branch);
 
 /* reference counting */
 avro_datum_t avro_datum_incref(avro_datum_t value);

Modified: avro/trunk/lang/c/src/datum.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/src/datum.c?rev=1057676&r1=1057675&r2=1057676&view=diff
==============================================================================
--- avro/trunk/lang/c/src/datum.c (original)
+++ avro/trunk/lang/c/src/datum.c Tue Jan 11 14:56:51 2011
@@ -398,6 +398,59 @@ avro_datum_t avro_union(int64_t discrimi
 	return &datum->obj;
 }
 
+int64_t avro_union_discriminant(const avro_datum_t datum)
+{
+	return avro_datum_to_union(datum)->discriminant;
+}
+
+avro_datum_t avro_union_current_branch(avro_datum_t datum)
+{
+	return avro_datum_to_union(datum)->value;
+}
+
+int avro_union_set_discriminant(avro_datum_t datum,
+				avro_schema_t schema,
+				int discriminant,
+				avro_datum_t *branch)
+{
+	if (!is_avro_union(datum) || !is_avro_union(schema)) {
+		return EINVAL;
+	}
+
+	struct avro_union_datum_t  *unionp =
+	    avro_datum_to_union(datum);
+
+	avro_schema_t  branch_schema =
+	    avro_schema_union_branch(schema, discriminant);
+
+	if (branch_schema == NULL) {
+		// That branch doesn't exist!
+		return EINVAL;
+	}
+
+	if (unionp->discriminant != discriminant) {
+		// If we're changing the branch, throw away any old
+		// branch value.
+		if (unionp->value != NULL) {
+			avro_datum_decref(unionp->value);
+			unionp->value = NULL;
+		}
+
+		unionp->discriminant = discriminant;
+	}
+
+	// Create a new branch value, if there isn't one already.
+	if (unionp->value == NULL) {
+		unionp->value = avro_datum_from_schema(branch_schema);
+	}
+
+	if (branch != NULL) {
+		*branch = unionp->value;
+	}
+
+	return 0;
+}
+
 avro_datum_t avro_record(const char *name, const char *space)
 {
 	struct avro_record_datum_t *datum =
@@ -460,7 +513,7 @@ avro_record_get(const avro_datum_t datum
 }
 
 int
-avro_record_set(const avro_datum_t datum, const char *field_name,
+avro_record_set(avro_datum_t datum, const char *field_name,
 		const avro_datum_t field_value)
 {
 	char *key = (char *)field_name;
@@ -504,6 +557,42 @@ avro_datum_t avro_enum(const char *name,
 	return &datum->obj;
 }
 
+int avro_enum_get(const avro_datum_t datum)
+{
+	return avro_datum_to_enum(datum)->value;
+}
+
+const char *avro_enum_get_name(const avro_datum_t datum,
+			       const avro_schema_t schema)
+{
+	int  value = avro_enum_get(datum);
+	return avro_schema_enum_get(schema, value);
+}
+
+int avro_enum_set(avro_datum_t datum, const int symbol_value)
+{
+	if (!is_avro_enum(datum)) {
+		return EINVAL;
+	}
+
+	avro_datum_to_enum(datum)->value = symbol_value;
+	return 0;
+}
+
+int avro_enum_set_name(avro_datum_t datum, avro_schema_t schema,
+		       const char *symbol_name)
+{
+	if (!is_avro_enum(datum) || !is_avro_enum(schema)) {
+		return EINVAL;
+	}
+	int  symbol_value = avro_schema_enum_get_by_name(schema, symbol_name);
+	if (symbol_value == -1) {
+		return EINVAL;
+	}
+	avro_datum_to_enum(datum)->value = symbol_value;
+	return 0;
+}
+
 static avro_datum_t avro_fixed_private(const char *name, const char *bytes,
 				       const int64_t size,
 				       void (*fixed_free) (void *ptr))
@@ -616,6 +705,12 @@ avro_datum_t avro_map(void)
 		free(datum);
 		return NULL;
 	}
+	datum->keys_by_index = st_init_numtable_with_size(DEFAULT_TABLE_SIZE);
+	if (!datum->keys_by_index) {
+		st_free_table(datum->map);
+		free(datum);
+		return NULL;
+	}
 
 	avro_datum_init(&datum->obj, AVRO_MAP);
 	return &datum->obj;
@@ -649,8 +744,30 @@ avro_map_get(const avro_datum_t datum, c
 	return EINVAL;
 }
 
+int avro_map_get_key(const avro_datum_t datum, int index,
+		     const char **key)
+{
+	if (!(is_avro_datum(datum) && is_avro_map(datum) &&
+	      index >= 0 && key)) {
+		return EINVAL;
+	}
+
+	union {
+		st_data_t data;
+		char *key;
+	} val;
+	struct avro_map_datum_t *map = avro_datum_to_map(datum);
+
+	if (st_lookup(map->keys_by_index, (st_data_t) index, &val.data)) {
+		*key = val.key;
+		return 0;
+	}
+
+	return EINVAL;
+}
+
 int
-avro_map_set(const avro_datum_t datum, const char *key,
+avro_map_set(avro_datum_t datum, const char *key,
 	     const avro_datum_t value)
 {
 	char *save_key = (char *)key;
@@ -661,6 +778,8 @@ avro_map_set(const avro_datum_t datum, c
 		return EINVAL;
 	}
 
+	struct avro_map_datum_t  *map = avro_datum_to_map(datum);
+
 	if (avro_map_get(datum, key, &old_datum) == 0) {
 		/* Overwriting an old value */
 		avro_datum_decref(old_datum);
@@ -670,10 +789,12 @@ avro_map_set(const avro_datum_t datum, c
 		if (!save_key) {
 			return ENOMEM;
 		}
+		int  new_index = map->map->num_entries;
+		st_insert(map->keys_by_index, (st_data_t) new_index,
+			  (st_data_t) save_key);
 	}
 	avro_datum_incref(value);
-	st_insert(avro_datum_to_map(datum)->map, (st_data_t) save_key,
-		  (st_data_t) value);
+	st_insert(map->map, (st_data_t) save_key, (st_data_t) value);
 	return 0;
 }
 
@@ -719,7 +840,7 @@ avro_array_size(const avro_datum_t datum
 }
 
 int
-avro_array_append_datum(const avro_datum_t array_datum,
+avro_array_append_datum(avro_datum_t array_datum,
 			const avro_datum_t datum)
 {
 	struct avro_array_datum_t *array;
@@ -844,6 +965,7 @@ static void avro_datum_free(avro_datum_t
 				st_foreach(map->map, char_datum_free_foreach,
 					   0);
 				st_free_table(map->map);
+				st_free_table(map->keys_by_index);
 				free(map);
 			}
 			break;

Modified: avro/trunk/lang/c/src/datum.h
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/src/datum.h?rev=1057676&r1=1057675&r2=1057676&view=diff
==============================================================================
--- avro/trunk/lang/c/src/datum.h (original)
+++ avro/trunk/lang/c/src/datum.h Tue Jan 11 14:56:51 2011
@@ -70,6 +70,7 @@ struct avro_fixed_datum_t {
 struct avro_map_datum_t {
 	struct avro_obj_t obj;
 	st_table *map;
+	st_table *keys_by_index;
 };
 
 struct avro_record_datum_t {

Modified: avro/trunk/lang/c/src/schema.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/src/schema.c?rev=1057676&r1=1057675&r2=1057676&view=diff
==============================================================================
--- avro/trunk/lang/c/src/schema.c (original)
+++ avro/trunk/lang/c/src/schema.c Tue Jan 11 14:56:51 2011
@@ -163,6 +163,7 @@ static void avro_schema_free(avro_schema
 				st_foreach(unionp->branches, union_free_foreach,
 					   0);
 				st_free_table(unionp->branches);
+				st_free_table(unionp->branches_byname);
 				free(unionp);
 			}
 			break;
@@ -290,6 +291,11 @@ avro_schema_t avro_schema_fixed(const ch
 	return &fixed->obj;
 }
 
+int64_t avro_schema_fixed_size(const avro_schema_t fixed)
+{
+	return avro_schema_to_fixed(fixed)->size;
+}
+
 avro_schema_t avro_schema_union(void)
 {
 	struct avro_union_schema_t *schema =
@@ -302,6 +308,13 @@ avro_schema_t avro_schema_union(void)
 		free(schema);
 		return NULL;
 	}
+	schema->branches_byname =
+	    st_init_strtable_with_size(DEFAULT_TABLE_SIZE);
+	if (!schema->branches_byname) {
+		st_free_table(schema->branches);
+		free(schema);
+		return NULL;
+	}
 
 	avro_schema_init(&schema->obj, AVRO_UNION);
 	return &schema->obj;
@@ -316,12 +329,46 @@ avro_schema_union_append(const avro_sche
 		return EINVAL;
 	}
 	unionp = avro_schema_to_union(union_schema);
-	st_insert(unionp->branches, unionp->branches->num_entries,
-		  (st_data_t) schema);
+	int  new_index = unionp->branches->num_entries;
+	st_insert(unionp->branches, new_index, (st_data_t) schema);
+	const char *name = avro_schema_type_name(schema);
+	st_insert(unionp->branches_byname, (st_data_t) name,
+		  (st_data_t) new_index);
 	avro_schema_incref(schema);
 	return 0;
 }
 
+avro_schema_t avro_schema_union_branch(avro_schema_t unionp,
+				       int branch_index)
+{
+	union {
+		st_data_t data;
+		avro_schema_t schema;
+	} val;
+	st_lookup(avro_schema_to_union(unionp)->branches,
+		  branch_index, &val.data);
+	return val.schema;
+}
+
+avro_schema_t avro_schema_union_branch_by_name
+(avro_schema_t unionp, int *branch_index, const char *name)
+{
+	union {
+		st_data_t data;
+		int  branch_index;
+	} val;
+
+	if (!st_lookup(avro_schema_to_union(unionp)->branches_byname,
+		       (st_data_t) name, &val.data)) {
+		return NULL;
+	}
+
+	if (branch_index != NULL) {
+		*branch_index = val.branch_index;
+	}
+	return avro_schema_union_branch(unionp, val.branch_index);
+}
+
 avro_schema_t avro_schema_array(const avro_schema_t items)
 {
 	struct avro_array_schema_t *array =
@@ -334,6 +381,11 @@ avro_schema_t avro_schema_array(const av
 	return &array->obj;
 }
 
+avro_schema_t avro_schema_array_items(avro_schema_t array)
+{
+	return avro_schema_to_array(array)->items;
+}
+
 avro_schema_t avro_schema_map(const avro_schema_t values)
 {
 	struct avro_map_schema_t *map =
@@ -346,6 +398,11 @@ avro_schema_t avro_schema_map(const avro
 	return &map->obj;
 }
 
+avro_schema_t avro_schema_map_values(avro_schema_t map)
+{
+	return avro_schema_to_map(map)->values;
+}
+
 avro_schema_t avro_schema_enum(const char *name)
 {
 	struct avro_enum_schema_t *enump;
@@ -379,6 +436,32 @@ avro_schema_t avro_schema_enum(const cha
 	return &enump->obj;
 }
 
+const char *avro_schema_enum_get(const avro_schema_t enump,
+				 int index)
+{
+	union {
+		st_data_t data;
+		char *sym;
+	} val;
+	st_lookup(avro_schema_to_enum(enump)->symbols, index, &val.data);
+	return val.sym;
+}
+
+int avro_schema_enum_get_by_name(const avro_schema_t enump,
+				 const char *symbol_name)
+{
+	union {
+		st_data_t data;
+		long idx;
+	} val;
+
+	return
+	    (st_lookup(avro_schema_to_enum(enump)->symbols_byname,
+		       (st_data_t) symbol_name, &val.data))?
+	    val.idx:
+	    -1;
+}
+
 int
 avro_schema_enum_symbol_append(const avro_schema_t enum_schema,
 			       const char *symbol)
@@ -468,6 +551,44 @@ avro_schema_t avro_schema_record(const c
 	return &record->obj;
 }
 
+size_t avro_schema_record_size(const avro_schema_t record)
+{
+	return avro_schema_to_record(record)->fields->num_entries;
+}
+
+avro_schema_t avro_schema_record_field_get(const avro_schema_t
+					   record, const char *field_name)
+{
+	union {
+		st_data_t data;
+		struct avro_record_field_t *field;
+	} val;
+	st_lookup(avro_schema_to_record(record)->fields_byname,
+		  (st_data_t) field_name, &val.data);
+	return val.field->type;
+}
+
+const char *avro_schema_record_field_name(const avro_schema_t schema, int index)
+{
+	union {
+		st_data_t data;
+		struct avro_record_field_t *field;
+	} val;
+	st_lookup(avro_schema_to_record(schema)->fields, index, &val.data);
+	return val.field->name;
+}
+
+avro_schema_t avro_schema_record_field_get_by_index
+(const avro_schema_t record, int index)
+{
+	union {
+		st_data_t data;
+		struct avro_record_field_t *field;
+	} val;
+	st_lookup(avro_schema_to_record(record)->fields, index, &val.data);
+	return val.field->type;
+}
+
 static int
 save_named_schemas(const char *name, avro_schema_t schema,
 		   avro_schema_error_t * error)
@@ -1129,6 +1250,98 @@ const char *avro_schema_type_name(const 
  return NULL;
 }
 
+avro_datum_t avro_datum_from_schema(const avro_schema_t schema)
+{
+	if (!is_avro_schema(schema)) {
+		return NULL;
+	}
+
+	switch (avro_typeof(schema)) {
+		case AVRO_STRING:
+			return avro_wrapstring("");
+
+		case AVRO_BYTES:
+			return avro_wrapbytes("", 0);
+
+		case AVRO_INT32:
+			return avro_int32(0);
+
+		case AVRO_INT64:
+			return avro_int64(0);
+
+		case AVRO_FLOAT:
+			return avro_float(0);
+
+		case AVRO_DOUBLE:
+			return avro_double(0);
+
+		case AVRO_BOOLEAN:
+			return avro_boolean(0);
+
+		case AVRO_NULL:
+			return avro_null();
+
+		case AVRO_RECORD:
+			{
+				const struct avro_record_schema_t *record_schema =
+				    avro_schema_to_record(schema);
+
+				avro_datum_t  rec =
+				    avro_record(record_schema->name,
+						record_schema->space);
+
+				int  i;
+				for (i = 0; i < record_schema->fields->num_entries; i++) {
+					union {
+						st_data_t data;
+						struct avro_record_field_t *field;
+					} val;
+					st_lookup(record_schema->fields, i, &val.data);
+
+					avro_datum_t  field =
+					    avro_datum_from_schema(val.field->type);
+					avro_record_set(rec, val.field->name, field);
+					avro_datum_decref(field);
+				}
+
+				return rec;
+			}
+
+		case AVRO_ENUM:
+			{
+				const struct avro_enum_schema_t *enum_schema =
+				    avro_schema_to_enum(schema);
+				return avro_enum(enum_schema->name, 0);
+			}
+
+		case AVRO_FIXED:
+			{
+				const struct avro_fixed_schema_t *fixed_schema =
+				    avro_schema_to_fixed(schema);
+				return avro_wrapfixed(fixed_schema->name, "", 0);
+			}
+
+		case AVRO_MAP:
+			return avro_map();
+
+		case AVRO_ARRAY:
+			return avro_array();
+
+		case AVRO_UNION:
+			return avro_union(-1, NULL);
+
+		case AVRO_LINK:
+			{
+				const struct avro_link_schema_t *link_schema =
+				    avro_schema_to_link(schema);
+				return avro_datum_from_schema(link_schema->to);
+			}
+
+		default:
+			return NULL;
+	}
+}
+
 /* simple helper for writing strings */
 static int avro_write_str(avro_writer_t out, const char *str)
 {

Modified: avro/trunk/lang/c/src/schema.h
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/src/schema.h?rev=1057676&r1=1057675&r2=1057676&view=diff
==============================================================================
--- avro/trunk/lang/c/src/schema.h (original)
+++ avro/trunk/lang/c/src/schema.h Tue Jan 11 14:56:51 2011
@@ -57,6 +57,7 @@ struct avro_map_schema_t {
 struct avro_union_schema_t {
 	struct avro_obj_t obj;
 	st_table *branches;
+	st_table *branches_byname;
 };
 
 struct avro_fixed_schema_t {

Modified: avro/trunk/lang/c/tests/test_avro_data.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/tests/test_avro_data.c?rev=1057676&r1=1057675&r2=1057676&view=diff
==============================================================================
--- avro/trunk/lang/c/tests/test_avro_data.c (original)
+++ avro/trunk/lang/c/tests/test_avro_data.c Tue Jan 11 14:56:51 2011
@@ -258,7 +258,34 @@ static int test_enum(void)
 	avro_schema_enum_symbol_append(schema, "Ruby");
 	avro_schema_enum_symbol_append(schema, "Java");
 
+	if (avro_enum_get(datum) != AVRO_C) {
+		fprintf(stderr, "Unexpected enum value AVRO_C\n");
+		exit(EXIT_FAILURE);
+	}
+
+	if (strcmp(avro_enum_get_name(datum, schema), "C") != 0) {
+		fprintf(stderr, "Unexpected enum value name C\n");
+		exit(EXIT_FAILURE);
+	}
+
+	write_read_check(schema, NULL, datum, "enum");
+
+	avro_enum_set(datum, AVRO_CPP);
+	if (strcmp(avro_enum_get_name(datum, schema), "C++") != 0) {
+		fprintf(stderr, "Unexpected enum value name C++\n");
+		exit(EXIT_FAILURE);
+	}
+
+	write_read_check(schema, NULL, datum, "enum");
+
+	avro_enum_set_name(datum, schema, "Python");
+	if (avro_enum_get(datum) != AVRO_PYTHON) {
+		fprintf(stderr, "Unexpected enum value AVRO_PYTHON\n");
+		exit(EXIT_FAILURE);
+	}
+
 	write_read_check(schema, NULL, datum, "enum");
+
 	avro_datum_decref(datum);
 	avro_schema_decref(schema);
 	return 0;
@@ -305,7 +332,19 @@ static int test_map(void)
 	}
 
 	if (avro_array_size(datum) != 7) {
-		fprintf(stderr, "Unexpected array size");
+		fprintf(stderr, "Unexpected map size\n");
+		exit(EXIT_FAILURE);
+	}
+
+	avro_datum_t value;
+	const char  *key;
+	avro_map_get_key(datum, 2, &key);
+	avro_map_get(datum, key, &value);
+	int64_t  val;
+	avro_int64_get(value, &val);
+
+	if (val != 2) {
+		fprintf(stderr, "Unexpected map value 2\n");
 		exit(EXIT_FAILURE);
 	}
 
@@ -320,6 +359,8 @@ static int test_union(void)
 	avro_schema_t schema = avro_schema_union();
 	avro_datum_t union_datum;
 	avro_datum_t datum;
+	avro_datum_t union_datum1;
+	avro_datum_t datum1;
 
 	avro_schema_union_append(schema, avro_schema_string());
 	avro_schema_union_append(schema, avro_schema_int());
@@ -328,9 +369,29 @@ static int test_union(void)
 	datum = avro_wrapstring("Follow your bliss.");
 	union_datum = avro_union(0, datum);
 
+	if (avro_union_discriminant(union_datum) != 0) {
+		fprintf(stderr, "Unexpected union discriminant\n");
+		exit(EXIT_FAILURE);
+	}
+
+	if (avro_union_current_branch(union_datum) != datum) {
+		fprintf(stderr, "Unexpected union branch datum\n");
+		exit(EXIT_FAILURE);
+	}
+
+	union_datum1 = avro_datum_from_schema(schema);
+	avro_union_set_discriminant(union_datum1, schema, 0, &datum1);
+	avro_wrapstring_set(datum1, "Follow your bliss.");
+
+	if (!avro_datum_equal(datum, datum1)) {
+		fprintf(stderr, "Union values should be equal\n");
+		exit(EXIT_FAILURE);
+	}
+
 	write_read_check(schema, NULL, union_datum, "union");
 	avro_datum_decref(union_datum);
 	avro_datum_decref(datum);
+	avro_datum_decref(union_datum1);
 	avro_schema_decref(schema);
 	return 0;
 }

Modified: avro/trunk/lang/c/tests/test_avro_schema.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/tests/test_avro_schema.c?rev=1057676&r1=1057675&r2=1057676&view=diff
==============================================================================
--- avro/trunk/lang/c/tests/test_avro_schema.c (original)
+++ avro/trunk/lang/c/tests/test_avro_schema.c Tue Jan 11 14:56:51 2011
@@ -18,6 +18,7 @@
 #include "avro_private.h"
 #include <stdio.h>
 #include <stdlib.h>
+#include <string.h>
 #include <sys/types.h>
 #include <dirent.h>
 
@@ -97,6 +98,132 @@ static void run_tests(char *dirpath, int
 	while (dent != NULL);
 }
 
+static int test_array(void)
+{
+	avro_schema_t schema = avro_schema_array(avro_schema_int());
+
+	if (!avro_schema_equal
+	    (avro_schema_array_items(schema), avro_schema_int())) {
+		fprintf(stderr, "Unexpected array items schema");
+		exit(EXIT_FAILURE);
+	}
+
+	avro_schema_decref(schema);
+	return 0;
+}
+
+static int test_enum(void)
+{
+	enum avro_languages {
+		AVRO_C,
+		AVRO_CPP,
+		AVRO_PYTHON,
+		AVRO_RUBY,
+		AVRO_JAVA
+	};
+	avro_schema_t schema = avro_schema_enum("language");
+
+	avro_schema_enum_symbol_append(schema, "C");
+	avro_schema_enum_symbol_append(schema, "C++");
+	avro_schema_enum_symbol_append(schema, "Python");
+	avro_schema_enum_symbol_append(schema, "Ruby");
+	avro_schema_enum_symbol_append(schema, "Java");
+
+	const char  *symbol1 = avro_schema_enum_get(schema, 1);
+	if (strcmp(symbol1, "C++") != 0) {
+		fprintf(stderr, "Unexpected enum schema symbol\n");
+		exit(EXIT_FAILURE);
+	}
+
+	if (avro_schema_enum_get_by_name(schema, "C++") != 1) {
+		fprintf(stderr, "Unexpected enum schema index\n");
+		exit(EXIT_FAILURE);
+	}
+
+	if (avro_schema_enum_get_by_name(schema, "Haskell") != -1) {
+		fprintf(stderr, "Unexpected enum schema index\n");
+		exit(EXIT_FAILURE);
+	}
+
+	avro_schema_decref(schema);
+	return 0;
+}
+
+static int test_fixed(void)
+{
+	avro_schema_t schema = avro_schema_fixed("msg", 8);
+	if (avro_schema_fixed_size(schema) != 8) {
+		fprintf(stderr, "Unexpected fixed size\n");
+		exit(EXIT_FAILURE);
+	}
+	return 0;
+}
+
+static int test_map(void)
+{
+	avro_schema_t schema = avro_schema_map(avro_schema_long());
+
+	if (!avro_schema_equal
+	    (avro_schema_map_values(schema), avro_schema_long())) {
+		fprintf(stderr, "Unexpected map values schema");
+		exit(EXIT_FAILURE);
+	}
+
+	avro_schema_decref(schema);
+	return 0;
+}
+
+static int test_record(void)
+{
+	avro_schema_t schema = avro_schema_record("person", NULL);
+
+	avro_schema_record_field_append(schema, "name", avro_schema_string());
+	avro_schema_record_field_append(schema, "age", avro_schema_int());
+
+	avro_schema_t  name_field =
+		avro_schema_record_field_get(schema, "name");
+	if (!avro_schema_equal(name_field, avro_schema_string())) {
+		fprintf(stderr, "Unexpected name field\n");
+		exit(EXIT_FAILURE);
+	}
+
+	avro_schema_t  field1 =
+		avro_schema_record_field_get_by_index(schema, 1);
+	if (!avro_schema_equal(field1, avro_schema_int())) {
+		fprintf(stderr, "Unexpected field 1\n");
+		exit(EXIT_FAILURE);
+	}
+
+	avro_schema_decref(schema);
+	return 0;
+}
+
+static int test_union(void)
+{
+	avro_schema_t schema = avro_schema_union();
+
+	avro_schema_union_append(schema, avro_schema_string());
+	avro_schema_union_append(schema, avro_schema_int());
+	avro_schema_union_append(schema, avro_schema_null());
+
+	if (!avro_schema_equal
+	    (avro_schema_string(),
+	     avro_schema_union_branch(schema, 0))) {
+		fprintf(stderr, "Unexpected union schema branch 0\n");
+		exit(EXIT_FAILURE);
+	}
+
+	if (!avro_schema_equal
+	    (avro_schema_string(),
+	     avro_schema_union_branch_by_name(schema, NULL, "string"))) {
+		fprintf(stderr, "Unexpected union schema branch \"string\"\n");
+		exit(EXIT_FAILURE);
+	}
+
+	avro_schema_decref(schema);
+	return 0;
+}
+
 int main(int argc, char *argv[])
 {
 	char *srcdir = getenv("srcdir");
@@ -121,6 +248,19 @@ int main(int argc, char *argv[])
 	fprintf(stderr, "RUNNING %s\n", path);
 	run_tests(path, 0);
 
+	fprintf(stderr, "*** Running array tests **\n");
+	test_array();
+	fprintf(stderr, "*** Running enum tests **\n");
+	test_enum();
+	fprintf(stderr, "*** Running fixed tests **\n");
+	test_fixed();
+	fprintf(stderr, "*** Running map tests **\n");
+	test_map();
+	fprintf(stderr, "*** Running record tests **\n");
+	test_record();
+	fprintf(stderr, "*** Running union tests **\n");
+	test_union();
+
 	fprintf(stderr, "==================================================\n");
 	fprintf(stderr,
 		"Finished running %d schema test cases successfully \n",



Mime
View raw message