예제 #1
0
    def dispatch(event, table, bind):
        if event == 'before-create':
            for c in table.c:
                # Add spatial indices for the Geometry and Geography columns
                if isinstance(c.type, (Geometry, Geography)) and \
                        c.type.spatial_index is True:
                    idx_name = 'idx_%s_%s' % (table.name, c.name)
                    get_or_create_GIST_Index(table, idx_name, c)

        if event in ('before-create', 'before-drop'):
            # Filter Geometry columns from the table with management=True
            # Note: Geography and PostGIS >= 2.0 don't need this
            gis_cols = [
                c for c in table.c
                if isinstance(c.type, Geometry) and c.type.management is True
            ]

            # Find all other columns that are not managed Geometries
            regular_cols = [x for x in table.c if x not in gis_cols]

            # Save original table column list for later
            table.info["_saved_columns"] = table.c

            # Temporarily patch a set of columns not including the
            # managed Geometry columns
            column_collection = expression.ColumnCollection()
            for col in regular_cols:
                column_collection.add(col)
            table.columns = column_collection

            if event == 'before-drop':
                # Drop the managed Geometry columns with DropGeometryColumn()
                table_schema = table.schema or 'public'
                for c in gis_cols:
                    stmt = select([
                        func.DropGeometryColumn(table_schema, table.name,
                                                c.name)
                    ])
                    stmt = stmt.execution_options(autocommit=True)
                    bind.execute(stmt)

        elif event == 'after-create':
            # Restore original column list including managed Geometry columns
            table.columns = table.info.pop('_saved_columns')

            table_schema = table.schema or 'public'
            for c in table.c:
                # Add the managed Geometry columns with AddGeometryColumn()
                if isinstance(c.type, Geometry) and c.type.management is True:
                    stmt = select([
                        func.AddGeometryColumn(table_schema, table.name,
                                               c.name, c.type.srid,
                                               c.type.geometry_type,
                                               c.type.dimension)
                    ])
                    stmt = stmt.execution_options(autocommit=True)
                    bind.execute(stmt)

                # Add spatial indices for the Raster columns
                #
                # Note the use of ST_ConvexHull since most raster operators are
                # based on the convex hull of the rasters.
                if isinstance(c.type, Raster) and c.type.spatial_index is True:
                    bind.execute(
                        'CREATE INDEX "idx_%s_%s" ON "%s"."%s" '
                        'USING GIST (ST_ConvexHull("%s"))' %
                        (table.name, c.name, table_schema, table.name, c.name))

        elif event == 'after-drop':
            # Restore original column list including managed Geometry columns
            table.columns = table.info.pop('_saved_columns')
예제 #2
0
    def dispatch(event, table, bind):
        if event in ('before-create', 'before-drop'):
            # Filter Geometry columns from the table with management=True
            # Note: Geography and PostGIS >= 2.0 don't need this
            gis_cols = [
                c for c in table.c
                if isinstance(c.type, Geometry) and c.type.management is True
            ]

            # Find all other columns that are not managed Geometries
            regular_cols = [x for x in table.c if x not in gis_cols]

            # Save original table column list for later
            table.info["_saved_columns"] = table.c

            # Temporarily patch a set of columns not including the
            # managed Geometry columns
            column_collection = expression.ColumnCollection()
            for col in regular_cols:
                column_collection.add(col)
            table.columns = column_collection

            if event == 'before-drop':
                # Drop the managed Geometry columns
                for c in gis_cols:
                    if bind.dialect.name == 'sqlite':
                        drop_func = 'DiscardGeometryColumn'
                    elif bind.dialect.name == 'postgresql':
                        drop_func = 'DropGeometryColumn'
                    else:
                        raise ArgumentError(
                            'dialect {} is not supported'.format(
                                bind.dialect.name))
                    args = [table.schema] if table.schema else []
                    args.extend([table.name, c.name])

                    stmt = select([getattr(func, drop_func)(*args)])
                    stmt = stmt.execution_options(autocommit=True)
                    bind.execute(stmt)

        elif event == 'after-create':
            # Restore original column list including managed Geometry columns
            table.columns = table.info.pop('_saved_columns')

            for c in table.c:
                # Add the managed Geometry columns with AddGeometryColumn()
                if isinstance(c.type, Geometry) and c.type.management is True:
                    args = [table.schema] if table.schema else []
                    args.extend([
                        table.name, c.name, c.type.srid, c.type.geometry_type,
                        c.type.dimension
                    ])
                    if c.type.use_typmod is not None:
                        args.append(c.type.use_typmod)

                    stmt = select([func.AddGeometryColumn(*args)])
                    stmt = stmt.execution_options(autocommit=True)
                    bind.execute(stmt)

                # Add spatial indices for the Geometry and Geography columns
                if isinstance(c.type, (Geometry, Geography)) and \
                        c.type.spatial_index is True:
                    if bind.dialect.name == 'sqlite':
                        stmt = select(
                            [func.CreateSpatialIndex(table.name, c.name)])
                        stmt = stmt.execution_options(autocommit=True)
                        bind.execute(stmt)
                    elif bind.dialect.name == 'postgresql':
                        if table.schema:
                            bind.execute(
                                'CREATE INDEX "idx_%s_%s" ON "%s"."%s" '
                                'USING GIST ("%s")' %
                                (table.name, c.name, table.schema, table.name,
                                 c.name))
                        else:
                            bind.execute(
                                'CREATE INDEX "idx_%s_%s" ON "%s" '
                                'USING GIST ("%s")' %
                                (table.name, c.name, table.name, c.name))
                    else:
                        raise ArgumentError(
                            'dialect {} is not supported'.format(
                                bind.dialect.name))

                # Add spatial indices for the Raster columns
                #
                # Note the use of ST_ConvexHull since most raster operators are
                # based on the convex hull of the rasters.
                if isinstance(c.type, Raster) and c.type.spatial_index is True:
                    if table.schema:
                        bind.execute('CREATE INDEX "idx_%s_%s" ON "%s"."%s" '
                                     'USING GIST (ST_ConvexHull("%s"))' %
                                     (table.name, c.name, table.schema,
                                      table.name, c.name))
                    else:
                        bind.execute('CREATE INDEX "idx_%s_%s" ON "%s" '
                                     'USING GIST (ST_ConvexHull("%s"))' %
                                     (table.name, c.name, table.name, c.name))

        elif event == 'after-drop':
            # Restore original column list including managed Geometry columns
            table.columns = table.info.pop('_saved_columns')