有効期間の短いアクセス許可用の Momento トークンz
トークンは、ユーザーのセッションなどの一時的な状況で使用されることを目的とした、有効期間が短く、範囲が限定された値です。 ユーザーログインなどのソフトウェアライフサイクルイベントでは、多くの場合、そのセッションの間のみ有効なトークンが発行されます。
Momento トークンは、データプレーン API 操作へのアクセスのみを許可します。 ユーザーは、キャッシュの作成、削除、フラッシュなどの コントロールプレーン 操作を実行できません。
完全な特権トークンを持つユーザーは、次のアクションを実行できます。
- 任意のキャッシュ内のキャッシュ項目を追加/編集/削除
- 任意のキャッシュ内の任意のトピックをパブリッシュおよびサブスクライブ
- 任意のキャッシュのインクリメント API を 介してキャッシュ値をインクリメント
システム要件に基づいてトークンのアクセスを制限するかどうかは、ユーザーの責任です。
トークンの作成
API キー とは異なり、トークンを作成する唯一の方法はコードを使用することです。 Momento コンソールからは作成できません。
以下に、さまざまな権限セットを持つトークンを作成する例をいくつか示します。
- JavaScript
- Python
- Java
- Go
- C#
// Generate a disposable token with read-write access to a specific key in one cache
const oneKeyOneCacheToken = await authClient.generateDisposableToken(
DisposableTokenScopes.cacheKeyReadWrite('squirrels', 'mo'),
ExpiresIn.minutes(30)
);
switch (oneKeyOneCacheToken.type) {
case GenerateDisposableTokenResponse.Success:
console.log('Generated a disposable API key with access to the "mo" key in the "squirrels" cache!');
// logging only a substring of the tokens, because logging security credentials is not advisable :)
console.log(`API key starts with: ${oneKeyOneCacheToken.authToken.substring(0, 10)}`);
console.log(`Expires At: ${oneKeyOneCacheToken.expiresAt.epoch()}`);
break;
case GenerateDisposableTokenResponse.Error:
throw new Error(
`An error occurred while attempting to call generateApiKey with disposable token scope: ${oneKeyOneCacheToken.errorCode()}: ${oneKeyOneCacheToken.toString()}`
);
}
// Generate a disposable token with read-write access to a specific key prefix in all caches
const keyPrefixAllCachesToken = await authClient.generateDisposableToken(
DisposableTokenScopes.cacheKeyPrefixReadWrite(AllCaches, 'squirrel'),
ExpiresIn.minutes(30)
);
switch (keyPrefixAllCachesToken.type) {
case GenerateDisposableTokenResponse.Success:
console.log('Generated a disposable API key with access to keys prefixed with "squirrel" in all caches!');
// logging only a substring of the tokens, because logging security credentials is not advisable :)
console.log(`API key starts with: ${keyPrefixAllCachesToken.authToken.substring(0, 10)}`);
console.log(`Expires At: ${keyPrefixAllCachesToken.expiresAt.epoch()}`);
break;
case GenerateDisposableTokenResponse.Error:
throw new Error(
`An error occurred while attempting to call generateApiKey with disposable token scope: ${keyPrefixAllCachesToken.errorCode()}: ${keyPrefixAllCachesToken.toString()}`
);
}
// Generate a disposable token with read-only access to all topics in one cache
const allTopicsOneCacheToken = await authClient.generateDisposableToken(
TokenScopes.topicSubscribeOnly('squirrel', AllTopics),
ExpiresIn.minutes(30)
);
switch (allTopicsOneCacheToken.type) {
case GenerateDisposableTokenResponse.Success:
console.log('Generated a disposable API key with access to all topics in the "squirrel" cache!');
// logging only a substring of the tokens, because logging security credentials is not advisable :)
console.log(`API key starts with: ${allTopicsOneCacheToken.authToken.substring(0, 10)}`);
console.log(`Expires At: ${allTopicsOneCacheToken.expiresAt.epoch()}`);
break;
case GenerateDisposableTokenResponse.Error:
throw new Error(
`An error occurred while attempting to call generateApiKey with disposable token scope: ${allTopicsOneCacheToken.errorCode()}: ${allTopicsOneCacheToken.toString()}`
);
}
// Generate a disposable token with write-only access to a single topic in all caches
const oneTopicAllCachesToken = await authClient.generateDisposableToken(
TokenScopes.topicPublishOnly(AllCaches, 'acorn'),
ExpiresIn.minutes(30)
);
switch (oneTopicAllCachesToken.type) {
case GenerateDisposableTokenResponse.Success:
console.log('Generated a disposable API key with access to all topics in the "squirrel" cache!');
// logging only a substring of the tokens, because logging security credentials is not advisable :)
console.log(`API key starts with: ${oneTopicAllCachesToken.authToken.substring(0, 10)}`);
console.log(`Expires At: ${oneTopicAllCachesToken.expiresAt.epoch()}`);
break;
case GenerateDisposableTokenResponse.Error:
throw new Error(
`An error occurred while attempting to call generateApiKey with disposable token scope: ${oneTopicAllCachesToken.errorCode()}: ${oneTopicAllCachesToken.toString()}`
);
}
response = await auth_client.generate_disposable_token(
DisposableTokenScopes.topic_publish_subscribe("a-cache", "a-topic"),
ExpiresIn.minutes(5),
DisposableTokenProps(token_id="a-token-id"),
)
match response:
case GenerateDisposableToken.Success():
print("Successfully generated a disposable token")
case GenerateDisposableToken.Error() as error:
print(f"Error generating a disposable token: {error.message}")
final GenerateDisposableTokenResponse response =
authClient
.generateDisposableTokenAsync(
DisposableTokenScopes.cacheKeyReadWrite("squirrel", "mo"), ExpiresIn.minutes(30))
.join();
if (response instanceof GenerateDisposableTokenResponse.Success success) {
System.out.println("Successfully generated the disposable token: " + success.authToken());
} else if (response instanceof GenerateDisposableTokenResponse.Error error) {
throw new RuntimeException(
"An error occurred while attempting to generate disposable token: "
+ error.getErrorCode(),
error);
}
tokenId := "a token id"
resp, err := authClient.GenerateDisposableToken(ctx, &momento.GenerateDisposableTokenRequest{
ExpiresIn: utils.ExpiresInSeconds(10),
Scope: momento.TopicSubscribeOnly(
momento.CacheName{Name: "a cache"},
momento.TopicName{Name: "a topic"},
),
Props: momento.DisposableTokenProps{
TokenId: &tokenId,
},
})
if err != nil {
panic(err)
}
switch r := resp.(type) {
case *auth_resp.GenerateDisposableTokenSuccess:
log.Printf("Successfully generated a disposable token for endpoint=%s with tokenId=%s\n", r.Endpoint, tokenId)
}
// Generate a disposable token with read-write access to a specific key in one cache
var oneKeyOneCacheToken = await authClient.GenerateDisposableTokenAsync(
DisposableTokenScopes.CacheKeyReadWrite("squirrels", "mo"),
ExpiresIn.Minutes(30)
);
if (oneKeyOneCacheToken is GenerateDisposableTokenResponse.Success token1)
{
// logging only a substring of the tokens, because logging security credentials is not advisable :)
Console.WriteLine("The generated disposable token starts with: " + token1.AuthToken.Substring(0, 10));
Console.WriteLine("The token expires at (epoch timestamp): " + token1.ExpiresAt.Epoch());
}
else if (oneKeyOneCacheToken is GenerateDisposableTokenResponse.Error err)
{
Console.WriteLine("Error generating disposable token: " + err.Message);
}
// Generate a disposable token with read-write access to a specific key prefix in all caches
var keyPrefixAllCachesToken = await authClient.GenerateDisposableTokenAsync(
DisposableTokenScopes.CacheKeyPrefixReadWrite(CacheSelector.AllCaches, "squirrel"),
ExpiresIn.Minutes(30)
);
if (keyPrefixAllCachesToken is GenerateDisposableTokenResponse.Success token2)
{
// logging only a substring of the tokens, because logging security credentials is not advisable :)
Console.WriteLine("The generated disposable token starts with: " + token2.AuthToken.Substring(0, 10));
Console.WriteLine("The token expires at (epoch timestamp): " + token2.ExpiresAt.Epoch());
}
else if (keyPrefixAllCachesToken is GenerateDisposableTokenResponse.Error err)
{
Console.WriteLine("Error generating disposable token: " + err.Message);
}
// Generate a disposable token with read-only access to all topics in one cache
var allTopicsOneCacheToken = await authClient.GenerateDisposableTokenAsync(
DisposableTokenScopes.TopicSubscribeOnly("squirrel", TopicSelector.AllTopics),
ExpiresIn.Minutes(30)
);
if (allTopicsOneCacheToken is GenerateDisposableTokenResponse.Success token3)
{
// logging only a substring of the tokens, because logging security credentials is not advisable :)
Console.WriteLine("The generated disposable token starts with: " + token3.AuthToken.Substring(0, 10));
Console.WriteLine("The token expires at (epoch timestamp): " + token3.ExpiresAt.Epoch());
}
else if (allTopicsOneCacheToken is GenerateDisposableTokenResponse.Error err)
{
Console.WriteLine("Error generating disposable token: " + err.Message);
}
// Generate a disposable token with write-only access to a single topic in all caches
var oneTopicAllCachesToken = await authClient.GenerateDisposableTokenAsync(
DisposableTokenScopes.TopicPublishOnly(CacheSelector.AllCaches, "acorn"),
ExpiresIn.Minutes(30)
);
if (oneTopicAllCachesToken is GenerateDisposableTokenResponse.Success token4)
{
// logging only a substring of the tokens, because logging security credentials is not advisable :)
Console.WriteLine("The generated disposable token starts with: " + token4.AuthToken.Substring(0, 10));
Console.WriteLine("The token expires at (epoch timestamp): " + token4.ExpiresAt.Epoch());
}
else if (oneTopicAllCachesToken is GenerateDisposableTokenResponse.Error err)
{
Console.WriteLine("Error generating disposable token: " + err.Message);
}
トークン作成の詳細については、APIリファレンスページを参照してください。
有効期限
Momento トークンには有効期限が必要です。 トークンの最大有効期限は 1 時間です。 トークンの有効期限が経過すると、新しいトークンを作成する必要があります。
期限切れのトークンを使用して呼び出しを行おうとすると、提供された資格情報がサービスに接続できなかったことを示す「AUTHENTICATION_ERROR」応答が返されます。
トークンは更新できません。 したがって、期限が切れると永久に失われます。 セッションが継続する場合は、新しいセッションを作成して発行する必要があります。
ユースケース
これらのトークンは、次の使用例に最適です。
- フロントエンド開発に Momento を使用
- IoT デバイスとの通信
- 特定のリソースへの一時的なアクセスの発行
- ログイン時にユーザーに資格情報を提供する
データ制限
トークンの一般的な使用例は、アクセスをリソースの小さなサブセットのみに制限することです。 トークンに 読み取り専用 アクセスを提供するなど、機能を制限できるだけでなく、個々のキャッシュ アイテムやトピックにスコープ を設定することもできます。
データ制限で何ができるかを完全に理解するには、権限ページ を確認してください。