1

申し訳ありませんが、私はまだ Django に慣れていません。質問が場違いでないことを願っています。

テンプレートに次のものが含まれている場合:

<td><a href="/contact/edit/?id{{ item.id }}">{{ item.last_name }}</a></td>

姓をクリックすると、ユーザーはそれを編集するために次のリンクにリダイレクトされます。

http://127.0.0.1:8000/contact/edit/?id=1

しかし、ログインしているユーザーがブラウザに別の ID を挿入して、自分のものではないレコードを編集するのを防ぐにはどうすればよいでしょうか?

アップデート

以下のコメントと回答を読んだときに、私はちょうど考えていました。サードパーティのアプリを使用するのではなく、ユーザーごとに UserProfile を作成し、会社全体で一意の uuid.uuid1() を添付することはできませんでした。ログインしたユーザーが何かを編集しようとするたびに、そのユーザー固有の会社の uuid も追加パラメーターとしてリンクに渡されます。

編集側では、この GUID を収集し、ログインしているユーザーと比較して、一致するかどうかを確認します。それらが一致する場合、彼は編集を続行する権限を与えられます。そうでない場合、彼はリダイレクトされます。

どう思いますか?弱点はありますか?

4

4 に答える 4

2

Django の新しいクラス ベースのビュー(汎用のUpdateViewdispatchなど) を使用する場合は、ハンドラーを拡張できます。

def dispatch(self, request, *args, **kwargs):
    handler = super(MyEditView, self).dispatch(request, *args, **kwargs)
    # Only allow editing if current user is owner
    if self.object.author != request.user:
        return HttpResponseForbidden(u"Can't touch this.")
    return handler

この場合、コードはauthor、残りのリクエストを処理する前に、モデル オブジェクトのフィールドが現在ログインしているユーザーに対応することを確認します。

これの実際の例は、私のプロジェクトで見ることができます。

于 2012-06-27T15:41:41.517 に答える
0

さまざまなユーザーに特定のオブジェクトへのさまざまなアクセスを許可できる「行レベルのアクセス許可」と呼ばれる、必要な処理を実行するサードパーティのアプリがいくつかあります。「行レベル」は、各オブジェクトがデータベース内の行であるSQLに由来します。

私はdjango-guardianを使って仕事をしています

于 2012-06-27T12:14:39.507 に答える
0

データの保存を処理する関数で、編集中のオブジェクトが現在ログインしているユーザーと同じ ID を持っているかどうかを確認します。

たとえば、問題のオブジェクトが EmailPrefs と呼ばれ、user_id というフィールドがある場合:

  1. 編集中のオブジェクトの ID を使用して EmailPrefs オブジェクトをロードします。
  2. user_id が現在のユーザーと一致しない場合、それ以上の処理を停止します
  3. EmailPrefs オブジェクトを変更する
  4. EmailPrefs オブジェクトをデータベースに保存します
于 2012-06-27T12:29:44.857 に答える
0

Django を使用している場合は、 などの他の ID を作成する代わりにauth、常にこのメカニズムに依存してユーザーを識別します(たとえば、 の下の e コマース サイトで追加のセッションが必要な場合を除きます)。sessionuuid1()HTTPS

権限の部分については、主にKoliber Servicesで説明されているように、所有権を直接確認できます。との関係はCompany、パーミッション チェックのロジックにとって重要です。関係をモデル化するには多くの方法があるため、コードは大きく異なります。例えば:UserContact

# a modeling way
User.company -> Company : an user belongs to a company
Contact.contributor -> User : a contact is contributed by an user, would be invalid is user is leaving the company
# could check accessibility by 
can_view = contact.contributor.company_id == current_user.company_id

# another modeling way
User.company -> Company : an user belongs to a company
Contact.company -> Company : a contact info is owned by a company, does not share globally
# could check accessibility by
can_view = contact.company_id == current_user.company_id

の場合、ユーザーcan_viewFalse無許可の試行に対して 403 を取得し、ログに記録する必要があります。

通常、コンテンツ保護には上記の方法で十分です (Django Admin にはまだありません)。ただし、さまざまな種類のパーミッション チェックや行パーミッション チェックがある場合は、統一されたパーミッション API を使用することをお勧めします。

たとえば、Django-guardian を例にとると、会社をグループにマップしassign can_view、ユーザーの会社を表すグループの連絡先を許可するだけです。または、シグナルまたはセロリ タスクを使用して連絡先が作成されたときの、会社内のすべてのユーザーへassignのアクセス許可。can_view

/contact/1/edit/さらに、の代わりに使用できます/contact/edit/?id=1。このようにして、このint(request.GET('id'))部分は のように urlconf に移動されr'^contact/(?P<pk>\d+)/$'、コードが少なくなり、より明確になります。

于 2012-06-28T13:53:38.330 に答える