2017-02-20 54 views
2

我有一個SQLAlchemy模型,其中一列是一個枚舉。爲了儘可能接近香草SQLAlchemy和Python3 stdlib,我已經定義了enum和stdlib的類,然後使用它的sqlalchemy.Enum類(SQLAlchemy文檔中建議的某處)將其提供給SQLAlchemy。如何在Python/SQLAlchemy中使用「class」作爲枚舉值?

class TaxonRank(enum.Enum): 

    domain = "domain" 
    kingdom = "kingdom" 
    phylum = "phylum" 
    class_ = "class" 
    order = "order" 
    family = "family" 
    genus = "genus" 
    species = "species" 

和模型:

rank = sqlalchemy.Column(sqlalchemy.Enum(TaxonRank), name = "rank", nullable = False) 

這個效果很好,除了強迫我使用class_而不是class的枚舉值(自然的一個,以避免與Python關鍵詞的衝突,這是非法的語法嘗試訪問TaxonRank.class。)

我真的不介意使用class_,但我遇到的問題是class_是最終存儲在數據庫中的值。這反過來又引起了我的CRUD API問題,其中我允許用戶執行諸如「過濾排名以ss排名結尾」。當然,這不匹配任何東西,因爲值實際上以ss_結束!

對於記錄顯示我一直在進行一些hacky的逐案翻譯,以始終向用戶class代替class_。但是,對排序和過濾做類似的處理更爲棘手,因爲我在SQL級別執行了這兩個操作。

所以我的問題:是否有一個很好的解決這個溫和的煩惱?我真的不關心我的Python訪問TaxonRank.class_,但也許有一種方法子類STDLIB的enum.Enum迫使class_屬性的字符串表示(因此實際上被存儲在數據庫中的值)所需class

+0

使用此值是否會在SQLAlchemy或其他庫代碼中導致錯誤?如果它適合你,你可以使用TaxonRank ['class']。 –

+0

'TaxonRank [「class」]'可以;問題出在定義上,特別是'class_ =「class」'。它是屬性名稱('class_')而不是放入數據庫的屬性值('class')。 – snoopy91

+0

嘗試使用此[形式使用的(https://docs.python.org/3.4/library/enum.html#functional-api)。如果將'TaxonClass'定義爲'Enum('TaxonClass',['domain','kingdom','phylum','class'])'',您可以避免使用'class_'屬性名稱。 –

回答

1

感謝Sergey Shubin向我指出了一個定義enum.Enum的替代形式。

TaxonRank = enum.Enum("TaxonRank", [ 
    ("domain", "domain"), 
    ("kingdom", "kingdom"), 
    ("phylum", "phylum"), 
    ("class", "class"), 
    ("order", "order"), 
    ("family", "family"), 
    ("genus", "genus"), 
    ("species", "species") 
])