web-dev-qa-db-ja.com

役割と権限に基づくアクセス制御

アクセス制御(承認)に関しては、ロールと権限の間の固有のトレードオフを理解しようとしています。

与えられたものから始めましょう:私たちのシステムでは、Permissionはきめの細かいアクセス単位( "リソースX "、"ダッシュボードページにアクセス "など)を編集します。 Roleは、1つ以上の権限のコレクションになります。 Userは1つ以上のロールを持つことができます。これらすべての関係(ユーザー、ロール、権限)はすべてデータベースに格納され、必要に応じてオンザフライで変更できます。

私の懸念:

(1)アクセス制御のためにロールをチェックすることの「悪い」とは何ですか?代わりに権限を確認することでどのようなメリットがありますか?つまり、以下の2つのスニペットの違いは何ですか。

if(SecurityUtils.hasRole(user)) {
    // Grant them access to a feature
}

// vs.
if(SecurityUtils.hasPermission(user)) {
    // Grant them access to a feature
}

そして:

(2)このシナリオでは、役割はどのような有用な価値を提供しますか?ユーザーに1つ以上の権限を直接割り当てることはできませんか?ロールは何をconcrete抽象化の価値を提供しますか(誰かが具体的な例を挙げられますか)?

45
smeeb

(1)アクセス制御のためにロールをチェックすることの「悪い」とは何ですか?代わりに権限を確認することでどのようなメリットがありますか?

チェックの時点では、呼び出し側のコードは知っている必要があります"ユーザーXはアクションYを実行する権限を持っていますか?"
呼び出しコードは、役割と権限の間の関係を気にせず、認識してはなりません。

次に、認証レイヤーは、ユーザーにこの権限があるかどうかをチェックします。通常、ユーザーのロールにこの権限があるかどうかをチェックします。これにより、呼び出しコードを更新せずに認証ロジックを変更できます。

呼び出しサイトで役割を直接確認する場合は、暗黙的に役割と許可の関係を形成し、呼び出しロジックに承認ロジックを挿入しているため、懸念の分離に違反しています。

後でロールfooに権限bazを付与しないことを決定した場合、ユーザーがfooかどうかをチェックするすべてのコードを変更する必要があります。

(2)このシナリオでは、役割はどのような有用な価値を提供しますか?ユーザーに1つ以上の権限を直接割り当てることはできませんか?ロールが提供する抽象化の具体的な値は何ですか(誰かが具体的な例を挙げられますか)?

ロールは、概念的には、名前付きの権限のコレクションを表します。

ユーザーが特定の設定を編集できる新しい機能を追加するとします。この機能は、管理者のみが使用できるようにする必要があります。

ユーザーごとに権限を保存している場合、データベース内のすべてのユーザーを管理者であることがわかっていることを確認する必要があります(ユーザーのロール情報を保存していない場合は、どのユーザーが管理者であるかをどのようにして知ることができますか? )、そしてこの許可を許可のリストに追加します。

ロールを使用する場合は、権限をAdministratorロールに追加するだけで済みます。これにより、実行がより簡単になり、スペース効率が向上し、ミスが発生しにくくなります。

66
Rotem

最初の質問への回答として、ユーザーが特定の権限ではなく役割を持っていることを確認する際の最大の問題は、複数の役割が権限を保持できることです。これの例として、開発者は会社のイントラネット上の開発者ポータルを表示するアクセス権を持っている可能性があります。これはおそらくマネージャーによって保持されている許可でもあります。その後、ユーザーが開発者ポータルにアクセスしようとすると、次のようなチェックが行われます。

if(SecurityUtils.hasRole(developer)) {
    // Grant them access to a feature
} else if(SecurityUtils.hasRole(manager)) {
    // Grant them access to a feature
} else if...

(選択した言語でのswitchステートメントの方が優れていますが、それでも特に整然としているわけではありません)

権限が一般的または広く保持されているほど、誰かが特定のシステムにアクセスできることを確認するために確認する必要があるユーザーロールが多くなります。これにより、ロールの権限を変更するたびに、チェックを変更してこれを反映する必要があるという問題も発生します。大規模なシステムでは、これは非常に扱いにくくなります。

たとえば、ユーザーが開発者ポータルへのアクセスを許可する権限を持っていることを単に確認した場合、ユーザーが保持している役割に関係なく、アクセスが許可されます。

2番目の質問に答えるために、役割を持っている理由は、権限の「パッケージ」を簡単に変更および配布できるためです。数百のロールと数千の権限を持つシステムがある場合、新しいユーザー(たとえば、新しいHRマネージャー)を追加するには、他のHRマネージャーが保持するすべての権限を1つずつ付与する必要があります。これは退屈な作業であるだけでなく、手動で行うと間違いが起こりやすくなります。これを、「HRマネージャー」ロールをユーザーのプロファイルに単に追加することと比較してください。これにより、そのロールを持つ他のすべてのユーザーと同じアクセス権が付与されます。

既存のユーザーのクローンを作成するだけでよいと主張することもできます(システムがこれをサポートしている場合)。これにより、その瞬間の正しいアクセス許可がユーザーに付与されますが、将来的にすべてのユーザーのアクセス許可を追加または削除しようとする可能性があります。難しい。このシナリオの例としては、おそらく過去には人事部のスタッフも給与を担当していたが、後で会社が十分に大きくなり、給与を処理するためのスタッフを雇う場合があります。これは、人事部が給与計算システムにアクセスする必要がないため、権限を削除できることを意味します。 HRのメンバーが10人いる場合は、手動で確認し、正しい権限を削除する必要があります。これにより、ユーザーエラーが発生する可能性があります。これに関するもう1つの問題は、単純にスケーリングされないことです。与えられた役割でますます多くのユーザーを獲得すると、役割の変更がはるかに困難になります。これを役割の使用と比較してください。問題の主要な役割を変更するだけで権限を削除できます。これは、その役割を持つすべてのユーザーによって反映されます。

20
Matt Champion