avro_schema_t avro_schema_copy_root()

in lang/c/src/schema.c [1288:1444]


avro_schema_t avro_schema_copy_root(avro_schema_t schema, st_table *named_schemas)
{
	long i;
	avro_schema_t new_schema = NULL;
	if (!schema) {
		return NULL;
	}
	switch (avro_typeof(schema)) {
	case AVRO_STRING:
	case AVRO_BYTES:
	case AVRO_INT32:
	case AVRO_INT64:
	case AVRO_FLOAT:
	case AVRO_DOUBLE:
	case AVRO_BOOLEAN:
	case AVRO_NULL:
		/*
		 * No need to copy primitives since they're static
		 */
		new_schema = schema;
		break;

	case AVRO_RECORD:
		{
			struct avro_record_schema_t *record_schema =
			    avro_schema_to_record(schema);
			new_schema =
			    avro_schema_record(record_schema->name,
					       record_schema->space);
		    if (save_named_schemas(new_schema, named_schemas)) {
   				avro_set_error("Cannot save enum schema");
   				return NULL;
   			}
			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_schema_t type_copy =
				    avro_schema_copy_root(val.field->type, named_schemas);
				avro_schema_record_field_append(new_schema,
								val.field->name,
								type_copy);
				avro_schema_decref(type_copy);
			}
		}
		break;

	case AVRO_ENUM:
		{
			struct avro_enum_schema_t *enum_schema =
			    avro_schema_to_enum(schema);
			new_schema = avro_schema_enum_ns(enum_schema->name,
					enum_schema->space);
			if (save_named_schemas(new_schema, named_schemas)) {
				avro_set_error("Cannot save enum schema");
				return NULL;
			}
			for (i = 0; i < enum_schema->symbols->num_entries; i++) {
				union {
					st_data_t data;
					char *sym;
				} val;
				st_lookup(enum_schema->symbols, i, &val.data);
				avro_schema_enum_symbol_append(new_schema,
							       val.sym);
			}
		}
		break;

	case AVRO_FIXED:
		{
			struct avro_fixed_schema_t *fixed_schema =
			    avro_schema_to_fixed(schema);
			new_schema =
			    avro_schema_fixed_ns(fixed_schema->name,
					         fixed_schema->space,
					         fixed_schema->size);
 			if (save_named_schemas(new_schema, named_schemas)) {
 				avro_set_error("Cannot save fixed schema");
 				return NULL;
 			}
		}
		break;

	case AVRO_MAP:
		{
			struct avro_map_schema_t *map_schema =
			    avro_schema_to_map(schema);
			avro_schema_t values_copy =
			    avro_schema_copy_root(map_schema->values, named_schemas);
			if (!values_copy) {
				return NULL;
			}
			new_schema = avro_schema_map(values_copy);
			avro_schema_decref(values_copy);
		}
		break;

	case AVRO_ARRAY:
		{
			struct avro_array_schema_t *array_schema =
			    avro_schema_to_array(schema);
			avro_schema_t items_copy =
			    avro_schema_copy_root(array_schema->items, named_schemas);
			if (!items_copy) {
				return NULL;
			}
			new_schema = avro_schema_array(items_copy);
			avro_schema_decref(items_copy);
		}
		break;

	case AVRO_UNION:
		{
			struct avro_union_schema_t *union_schema =
			    avro_schema_to_union(schema);

			new_schema = avro_schema_union();
			for (i = 0; i < union_schema->branches->num_entries;
			     i++) {
				avro_schema_t schema_copy;
				union {
					st_data_t data;
					avro_schema_t schema;
				} val;
				st_lookup(union_schema->branches, i, &val.data);
				schema_copy = avro_schema_copy_root(val.schema, named_schemas);
				if (avro_schema_union_append
				    (new_schema, schema_copy)) {
					avro_schema_decref(new_schema);
					return NULL;
				}
				avro_schema_decref(schema_copy);
			}
		}
		break;

	case AVRO_LINK:
		{
			struct avro_link_schema_t *link_schema =
			    avro_schema_to_link(schema);
			avro_schema_t to;

			to = find_named_schemas(avro_schema_name(link_schema->to),
									avro_schema_namespace(link_schema->to),
									named_schemas);
			new_schema = avro_schema_link(to);
		}
		break;

	default:
		return NULL;
	}
	return new_schema;
}