'Parse and validate the specification.'

def parse_specification(self, specification):

    parsed = {}
    for (model_id, items) in specification.items():
        metadata = self.model_metadata[model_id]
        natural_key_spec = metadata['natural_key']
        relations = metadata.get('relations', {})
        filters = metadata.get('filters', {})
        assert apps.get_model(model_id)
        parsed.setdefault(model_id, [])
        for (item_num, item) in enumerate(items):
            key = []
            for name in natural_key_spec:
                relation = relations.get(name, {})
                try:
                    value = item.pop(name)
                except KeyError:
                    raise ValueError(('%s    %d:    Needs    key    "%s"' % (model_id, item_num, name)))
                else:
                    if relation:
                        assert (relation['link'] == 'to_one')
                        key.append(tuple(value))
                    else:
                        key.append(value)
            data = {'key': tuple(key), 'fields': {}, 'relations': {}}
            for (name, value) in item.items():
                relation = relations.get(name, {})
                if relation:
                    if (relation['link'] == 'to_one'):
                        data['relations'][name] = tuple(value)
                    else:
                        assert (relation['link'] == 'to_many')
                        data['relations'][name] = [tuple(val) for val in value]
                elif (name in filters):
                    value_filter = getattr(self, filters[name])
                    data['fields'][name] = value_filter(value)
                else:
                    data['fields'][name] = value
            parsed[model_id].append(data)
    return parsed
