TypeScriptでは、配列内のすべての要素が次のように同じ型であることを宣言できます。
const theArray: MyInterface[]
オブジェクトのすべてのプロパティ値が同じ型でなければならないことを宣言することができる同様のものはありますか? (すべてのプロパティ名を指定せずに)
たとえば、私は現在これをやっています:
interface MyInterface {
name:string;
}
const allTheThingsCurrently = {
first: <MyInterface>{name: 'first thing name' },
second: <MyInterface>{name: 'second thing name' },
third: <MyInterface>{name: 'third thing name' },
//...
};
...すべての単一のプロパティに対して<MyInterface>
を指定する方法に注意してください。このためのショートカットはありますか?つまり、私はこのようなものを想像しています...
const allTheThingsWanted:MyInterface{} = {
first: {name: 'first thing name' },
second: {name: 'second thing name' },
third: {name: 'third thing name' },
//...
};
MyInterface{}
は無効なコードの部分です。冗長性を減らし、オプションで他のプロパティが異なる型のオブジェクトに追加されないようにする特別な厳密さを実現する方法を探しています。
ジェネリックを使用して、必要なプロパティタイプを指定します。
type SamePropTypeOnly<T> = {
[P: string]: T;
}
interface MyInterface {
name: string;
}
const newObj: SamePropTypeOnly<MyInterface> = {
first: { name: 'first thing name' },
second: { name: 'second thing name' },
third: { name: 'third thing name' },
// forth: 'Blah' // Type 'string' is not assignable to type `MyInterface`
}
interface Thing {
name: string
}
interface ThingMap {
[thingName: string]: Thing
}
const allTheThings: ThingMap = {
first: { name: "first thing name" },
second: { name: "second thing name" },
third: { name: "third thing name" },
}
ここでの欠点は、allTheThings
以外のプロパティにエラーなしでアクセスできることです。
allTheThings.nonexistent // type is Thing
これは、ThingMap
を[thingName: string]: Thing | void
として定義することでより安全にできますが、そこにあることがわかっているプロパティにアクセスしている場合でも、至る所でnullチェックが必要になります。
const createThings = <M extends ThingMap>(things: M) => things
const allTheThings = createThings({
first: { name: "first thing name" },
second: { name: "second thing name" },
third: { name: "third thing name" },
fourth: { oops: 'lol!' }, // error here
})
allTheThings.first
allTheThings.nonexistent // comment out "fourth" above, error here
createThings
関数には汎用のM
があり、すべての値がM
である限り、Thing
は何でもかまいません。そうするとM
が返されます。オブジェクトを渡すと、オブジェクトはextends
の後の型に対して検証され、渡されたものと同じ形状が返されます。
これは「最もスマートな」ソリューションですが、多少巧妙に見えるハックを使用して実際に機能させます。いずれにしても、TSがこのようなケースをサポートするためのより良いパターンを追加するまでは、これが私の推奨ルートです。