OepnFeatureって何?
OpenFeatureはフィーチャーフラグのベンダーロックインを避けるために策定された標準仕様です。
CNCF incubating projectにも認定されています。
openfeature.dev
アプリケーションからフィーチャーフラグを使うインターフェースはOpenFeatureが提供し、実際にどのような値を返すかを決定するプロバイダーという部分は各ベンダーなどが提供するという仕組みになっています。
つまり、もしフィーチャーフラグを提供するサービスを変えたくなってもアプリケーションの対応はほとんど必要なくなるということです。
詳しくは、OpenFeatureのintroductionを参照してください。
Introduction | OpenFeature
先ほどもあげたように、OpenFeatureにはプロバイダーという概念があります。これは実際にフラグを出し分ける際に参照される具体的な実装と考えればよいです。
どのプロバイダーを使うかに制約はなく自由です。SaaSを使いたいならSaaSベンダーが提供しているProviderを利用すればよいですし、もちろん自分で実装することもできます。
一例として上げると、フィーチャーフラグSaaSの一種である、FlagSmithはOpenFeatureに対応したプロバイダーを提供しています。
OpenFeature | Flagsmith Docs
OpenTelemetryと世界観は似ていますね。
今回は理解のために自分でプロバイダーを作って使ってみようと思います。
Nodejsでプロバイダーを作ってみる
オレオレプロバイダーを作ってみましょう。今回はNodejsを対象としたプロバイダーを作ってみます。
ドキュメントを読むとOpenFeatureが提供するNodeSDKの中にあるProviderインターフェースを満たすクラスを実装すればよいことがわかります。
export class MyFeatureProvider implements Provider {
metadata: ProviderMetadata = { name: 'MyFeatureFlagProvider' };
async resolveBooleanEvaluation(
flagKey: string,
defaultValue: boolean,
context: EvaluationContext,
logger: Logger,
): Promise<ResolutionDetails<boolean>> {
const userId = context['userId'];
const result =
logger.debug('result is ', result);
return {
value: result ?? defaultValue,
};
}
こんな感じです。指定されたインターフェースを満たすようにクラスを作るだけなので難しくはないです。
プロバイダーを使う
まずはどのプロバイダーを使うかを設定する必要があります。とはいっても引数として先ほど作成したプロバイダーを渡すだけ。
OpenFeature.setProvider(new MyFeatureProvider());
これだけ。環境変数を読むなど初期化をする段階で一緒に与えるとよいでしょう。
プロバイダーを登録すれば準備は完了です。
では使ってみましょう。
const featureClient = OpenFeature.getClient();
const client = featureClient.setContext({ userId: '1' });
await client.getBooleanValue("someBoolKey", true);
await client.getStringValue("someStringKey", 'hoge');
実際に触ってみるとキーを渡せる第一引数はstring型になっていることやcontextの型の制約が緩いことに気がつきます。またcontextの値を一律で付与したり渡せる値を制限したくなります。
上の理由からkeyに使える値を型で制約したりコンテキストに渡せる値に制約を掛けたくなって実際には以下のようなラッパーを作ることになると思います。
export const boolFeature = async (
key: 'hoge' | 'fuga',
defaultValue: boolean,
context: { userId: string },
): Promise<boolean> => {
const client = OpenFeature.getClient(context);
return await client.getBooleanValue(key, defaultValue);
};
const flagHoge = await boolFeature("hoge", false, { userId: '1' });
まとめ
OpenFeatureに触れるべく、自分でプロバイダーを実装してみました。
実装するまではフィーチャーフラグを提供するSaaS向けかと思っていました。
しかしSaaSを使わずフィーチャーフラグを自前で実装するという場面でも、OpenFeatureプロバイダーを自分で実装することにより実現することができるということが分かりました。