2017-06-02 14 views
0

我正在尋找最佳的解決方案,以將字符串的用法分隔爲已翻譯消息和文本文本值的標識符。原型的FlowType標稱打字

,所以我可能有一個對象場稱爲title,在這種情況下指的是一種形式的稱號,它的值將SIGNUP_FORM_TITLEMAIL_FORM_TITLE所以它會參考一個本地化的字符串,將被傳遞給像函數format(id)它返回當前語言環境的實際本地化文本。

但是,那麼我可能也有一個對象字段name它是指一個人的名字,並沒有本地化,所以它可能有價值John Doe

我如何確保當我將名稱傳遞給格式(id)時出現類型錯誤,反之亦然,當我將title傳遞給期望普通(文本)字符串的API時。

我不能(當然)只是說type LocalizationIdentifierType = string,因爲這只是一個別名。

也許我可以做一個字符串class LocalizationIdentifier extends String的子類,但這仍然會允許LocalizationIdentifier傳遞給一個基於字符串的API(或者至少我認爲是這種情況)。

有沒有人有一個更好的想法,名義上鍵入一個字符串? 或者,也許我完全在錯誤的軌道上? (「奧夫DEM的Holzweg」我們在德國說)


有一個related questionproposal加入類似的功能,以打字稿。 當然,選擇typecript over flowtype當然不是一種選擇。

回答

1

我想你可能會尋找有流量的opaque type aliases

你可以做一個不透明的類型別名: opaque type LocalizationIdentifierType = string

這將在文件內表現爲字符串,但作爲文件外部的名義類型。

你提到你想類似的東西LocalizationIdentifierType extends String - 您可以通過添加子類型約束到您的不透明類型別名實現這一目標:

opaque type LocalizationIdentifierType: string = string

這意味着LocalizationIdentifierType是一個字符串,但不所有字符串都是LocalizationIdentifierType

+0

是的。我已經在使用這個,但是當我問這個問題時,它不可用:) –

1

字面類型幾乎工作。您可以指定format的簽名

function format(id: "SIGNUP_FORM_TITLE" | "MAIL_FORM_TITLE" | ...): string { 
    ... 
} 

不幸的是,這個分崩離析您的其他情況下(本地化的文本錯誤地傳遞到純文本API)。對象文本類型似乎是阻力最小的JavaScript的路徑:

type LocalizedString = { 
    +field: "SIGNUP_FORM_TITLE" | "MAIL_FORM_TITLE" 
}; 
type PlainText = string; 

const signupFormTitle: LocalizedString = { field: "SIGNUP_FORM_TITLE" }; 
const mailFormTitle: LocalizedString = { field: "MAIL_FORM_TITLE" }; 

如果您需要在LocalizedString引進的變化,在對象的附加標記字段工作得很好,例如:

type LocalizedString = { 
    +variant: "variant1", 
    +field: "SIGNUP_FORM_TITLE" | "MAIL_FORM_TITLE" 
}; 
+0

感謝您的解決方法,不幸的是這並不完全符合我的想法。我真的很高興,那種不透明的類型現在成爲了☺️ –