Ejemplo n.º 1
0
    def update_or_create_from_xml(self, el,
            default_language=settings.LANGUAGE_CODE, base_url='',
            save=True):
        """ Returns a tuple of (CREATED/UPDATED/UNMODIFIED, model_obj)"""

        el_hash = hashlib.md5(etree.tostring(el)).hexdigest()

        el = deepcopy(el)

        jurisdiction_id, obj_id = el.findtext('id').split('/')
        
        if not (jurisdiction_id and obj_id):
            raise ValidationError(u"%s is not a valid Open511 ID" % el.findtext('id'))
        el.remove(el.xpath('id')[0])

        external_jurisdiction = el.xpath('link[@rel="jurisdiction"]')
        if external_jurisdiction:
            el.remove(external_jurisdiction[0])

        try:
            jurisdiction = Jurisdiction.objects.get(id=jurisdiction_id)
        except Jurisdiction.DoesNotExist:
            if not external_jurisdiction:
                raise Exception("No jurisdiction URL provided for %s" % jurisdiction_id)
            jurisdiction = Jurisdiction.objects.get_or_create_from_url(
                urljoin(base_url, external_jurisdiction[0].get('href')))

        try:
            obj = self.get(id=obj_id, jurisdiction=jurisdiction)
            if obj.last_import_hash == el_hash:
                return ('UNMODIFIED', obj)
            created = False
        except ObjectDoesNotExist:
            created = True
            obj = self.model(id=obj_id, jurisdiction=jurisdiction, last_import_hash=el_hash)

        self_link = el.xpath('link[@rel="self"]')
        if self_link:
            obj.external_url = urljoin(base_url, self_link[0].get('href'))
            el.remove(self_link[0])

        # Extract the geometry
        geometry = el.xpath('geography')[0]
        gml = etree.tostring(geometry[0], encoding='unicode')
        ewkt = gml_to_ewkt(gml, force_2D=True)
        obj.geom = geos_geom_from_string(ewkt)

        # And regenerate the GML so it's consistent with the PostGIS representation
        el.remove(geometry)
        el.append(E.geography(geom_to_xml_element(obj.geom)))

        # Push down the default language if necessary
        if not el.get(XML_LANG):
            el.set(XML_LANG, default_language)

        obj.xml_elem = el
        if save:
            obj.save()
        return ('CREATED' if created else 'UPDATED', obj)
Ejemplo n.º 2
0
    def handle(self, filename=sys.stdin, **options):
        root = etree.parse(filename).getroot()
        assert root.tag == 'Open511'

        created = []

        for event in root.xpath('RoadEvent'):
            try:
                jurisdiction, dummy, id = event.get('id').partition(':')
                try:
                    rdev = RoadEvent.objects.get(id=id, jurisdiction=jurisdiction)
                except RoadEvent.DoesNotExist:
                    rdev = RoadEvent(id=id, jurisdiction=jurisdiction)
                logger.info("Importing event %s" % rdev.id)

                # Extract the geometry
                geometry = event.xpath('Geometry')[0]
                gml = etree.tostring(geometry[0])
                ewkt = gml_to_ewkt(gml, force_2D=True)
                rdev.geom = geos_geom_from_string(ewkt)
                event.remove(geometry)

                # Remove the ID from the stored XML (we keep it in the table)
                del event.attrib['id']

                # Push down the default language if necessary
                if not event.get(XML_LANG):
                    event.set(XML_LANG, root.get(XML_LANG))

                rdev.xml_elem = event

                rdev.save()
                created.append(rdev)

            except ValueError as e:
                logger.error("ValueError importing %s: %s" % (e, rdev.compound_id))

        print "%s entries imported." % len(created)
Ejemplo n.º 3
0
    def update(self, key, val):

        if key in ('updated', 'created'):
            raise NotImplementedError
        elif key == 'status':
            self.active = (val.upper() == 'ACTIVE')
            return
        elif key == '!unpublished':
            self.published = (not val) or unicode(val).lower() == 'false'
            return
        elif key.startswith('_'):
            # ignore internal fields
            return

        update_el = self._get_or_create_el(key)

        if val is None:
            update_el.getparent().remove(update_el)
        elif isinstance(val, (str, unicode)):
            update_el.text = val
        elif key == 'geography':
            if 'opengis' in getattr(val, 'tag', ''):
                gml = val
            else:
                gml = geojson_to_gml(val)
            wkt = gml_to_ewkt(etree.tostring(gml, encoding='unicode'))
            self.geom = geos_geom_from_string(wkt)
            update_el.clear()
            update_el.append(gml)
        elif isinstance(val, (dict, list)):
            if not val:
                update_el.getparent().remove(update_el)
            update_el.clear()
            json_struct_to_xml(val, update_el)
        else:
            raise NotImplementedError
Ejemplo n.º 4
0
 def fromstring(cls, input):
     if is_hex(input):
         # Looks like an ID
         return cls.get(input)
     geom = geos_geom_from_string(input)
     return cls(geom, id=None)