2017-08-29 1 views
1

EveでREST APIを構築し、特定のエンドポイントを保護するためにロールを使用していますが、それ以上の場合、特定のフィールドレベルのアクセスルールを適用する必要もあります。Eveでフィールドレベルのセキュリティを実装するにはどうすればよいですか?

users = { 
    'schema': { 
     Schema.NAME: { 
      'type': 'string', 
      'minlength': 1, 
      'maxlength': 32, 
      'required': True, 
      'unique': True 
     }, 
     Schema.PASSWORD: { 
      'type': 'string', 
      'required': True 
     }, 
     Schema.ROLE: { 
      'type': 'string', 
      'allowed': ['end user', 'manager', 'admin'], 
      'required': True 
     } 
    }, 

エンドポイントがパブリックPOSTアクセス権を持っているので、誰でも(すなわち、新しいユーザーが自分のアカウントを作成することができます)ユーザを作成することができます:私は、次のスキーマの基本的なusersエンドポイントを持っています。エンドユーザは自分のパスワードを変更でき、マネージャはエンドユーザのパスワードを変更でき、管理者はエンドユーザの役割を変更できます。

標準のスキーマ定義でこれを行う方法はありませんでした。私はCerberusの検証についても見ていたが、それは複数の文書にわたるロジックをサポートするようには見えなかった(すなわち、クライアントがuserとして認証されたことを確認してエンドユーザのuser文書の変更を検証する)。

は、私は、イベントフックを追加することによって、私が探しています効果を達成:

app.on_insert += all_users_created_equal 
app.on_pre_PATCH_users += restrict_role_updates_to_admins 

... 

def all_users_created_equal(resource, docs): 
    """Ensure that all users are created as end users. 
    Managers and Admins must be granted these roles by an existing 
    manager or admin.""" 
    if resource == 'users': 
     for doc in docs: 
      doc['role'] = 'user' 

def restrict_role_updates_to_admins(request, lookup): 
    if 'role' in request.json: 
     users = app.data.driver.db['users'] 
     user = users.find_one({'name': request.authorization.username}) 
     if user and user['role'] != 'admin': 
      # Non-admins cannot update roles. Break the lookup to fail the request. 
      lookup['_id'] = None 

しかし、それは要求を失敗させるために要求内容をマックするハックです。フィールドレベルのセキュリティを強化するより良い方法はありますか?そうでない場合は、イベントフックを使用してサーバーに要求を失敗させるより良い方法がありますか?フックから例外を発生させると、要求は失敗しましたが、例外はサーバーの上に伝播され、理想的でもありませんでした。

+1

リクエストを失敗させるより良い方法は、フラスコのアボート機能を呼び出すことです。次に、ドキュメントの例を示します(http://flask.pocoo.org/docs/0.12/quickstart/#redirects-and-errors)。 – gcw

答えて

0

フィールドレベルのセキュリティを強化する方法はありますか?

私が知っているように、フィールドレベルのカスタムアクセスコントロールをサポートするメカニズムはありません。あなたはそれがあればそれを見つけるだろう。

可能であれば、デザインを変更することをお勧めします。私は、eveでサポートされているCRUD操作からアクセス制御メカニズムを分離する方がよいと思います。アクセスを制御するだけのサーバーを開発することができます。このアクセス制御サーバーは、ユーザーからのすべての要求を取得し、アーキテクチャーでメディエーターの役割を果たします。次に、リクエストがアクセス制御ルール(あなたの質問で言及したもの)と互換性がある場合、リクエストはCRUDサーバ(eveサーバ)に送信され、データベースに影響を与えることができます。

このアーキテクチャは、ユーザーアクセス制御とCRUD操作を分離し、将来的にさらにアクセス制御規則を追加できるため、拡張性があるので簡単です。

+0

興味深い提案。私は、追加のネットワークトラフィックとその中に埋め込まれたこれらのアクセスコントロールを持たないCRUDサーバーのリスクに対するその分離の価値を測る必要があります。アクセス制御サーバーとCRUDサーバーのセットアップは、基本的にWebサーバーとデータベースのセットアップに似ています。コメントありがとう! – Riaz

関連する問題