Pythonメタクラスを使用してマッピングしている一連の動的データベーステーブル(PostGISを使用したPostgres 9.3)があります:
cls = type(str(tablename), (db.Model,), {'__tablename__':tablename})
ここで、db.Model はフラスコ sqlalchemy による db オブジェクトで、tablename は少しの Unicode です。cls はアプリケーション全体のディクショナリにcurrent_app.class_references
(Flask の current_app を使用して) 追加され、クラスを複数回インスタンス化しようとする試みを回避します。
wkb_geometry
各テーブルには、 Well Known Binaryに格納されたジオメトリ列が含まれています。これらをマップしてgeoalchemy2を使用し、GeoJSON を取得するという最終目標を達成したいと考えています。
テーブルをアプリオリに宣言する場合は、次を使用します。
class GeoPoly():
__tablename__ = 'somename'
wkb_geometry = db.Column(Geometry("POLYGON"))
#more columns...
cls1
これを動的に実行しようとしているので、既知の型でリフレクションをオーバーライドできる必要があります。
試み:
リフレクション オーバーライド構文を使用して、列を明示的に定義します。
cls = type(str(tablename), (db.Model,), {'__tablename__':tablename, 'wkb_geometry':db.Column(Geometry("POLYGON"))})
新たに再起動すると、つまり、クラスはまだインスタンス化されていません: InvalidRequestError: テーブル 'tablename' は、この MetaData インスタンスに対して既に定義されています。'extend_existing=True' を指定して、既存のテーブル オブジェクトのオプションと列を再定義します
上で定義したクラスで mixin を使用します (sans tablename ):
cls = type(str(tablename), (GeoPoly, db.Model), {'__tablename__':tablename})
再びメタデータの問題。
クラスがインスタンス化された後、列定義属性をオーバーライドします。
cls = type(str(tablename), (db.Model,), {'__tablename__':tablename}) current_app.class_references[tablename] = cls cls.wkb_geometry = db.Column(Geometry("POLYGON"))
結果は次のとおりです。
InvalidRequestError: 属性 'wkb_geometry' の下で列 tablename.wkb_geometry を列 tablename.wkb_geometry と暗黙的に組み合わせています。これらの同じ名前の列の 1 つ以上の属性を明示的に構成してください。
メタデータ構造を使用して動的リフレクションをサポートし、*すべてのテーブルで使用できることがわかっている列をオーバーライドすることは可能ですか?