SharePoint 2010 の古い友人 - "このページのセキュリティの検証は正しくありません" - に対する新たなひと工夫

原文の記事の投稿日: 2011 年 9 月 15 日 (木曜日)

数え切れないほど多くの読者が、私の古い友人 (といっても例外のことですが) を目にしたことがあるに違いありません。その例外とは、"このページのセキュリティの検証は正しくありません。お使いの Web ブラウザーにある [戻る] ボタンをクリックし、ページを最新の状態に更新してから、操作をやり直してください。" というものです。まるで "Jelly of the Month Club" (今月のゼリー クラブ) の贈り物のように、この例外はとどまることなくやってきます。一般にこの問題は、リストにアイテムを追加しようとしているときに、たいていは RunWithElevatedPrivileges デリゲートの内部で発生します。今や多くの人々が、次のような一般的な問題と回避策を見つけています。

  • 一般的な問題 - RunWithElevatedPrivileges を使用し、ただし前から存在する SPSite または SPWeb コンテキストを使用している場合。既存の SPSite または SPWeb コンテキストには、それ以降に呼び出される RunWithElevatedPrivileges の権限が適用されないために、処理がうまくいきません。
  • 一般的な回避策 - SPWeb の AllowUnsafeUpdates プロパティを true に設定し、リストにアイテムを追加した後で、プロパティを false に戻します。たしかにこの方法は有効なのですが、たいていは 7 月のゼリー (例の... "Jelly of the Month Club" からの :-) の甘さを堪能しすぎたような気分にさせられます。この意味がおわかりいただけるでしょうか。

私がかなり変わった回避策を見つけたときも、同じような状況にありました。私は _layouts ディレクトリ用のカスタム ページを使用していて、分離コードでリスト アイテムを追加していました。この問題には以前に (それこそ FormDigest コントロールが追加された SharePoint 2003 のころから) 何度もお目にかかったことがあるので、間に合わせの方法で 2 分ほどで対処しました。ただしこのときは、もう少し詳しく調べて代わりの方法がないかどうかを確かめたいと思いました。そして実際に調べてみました。

すると、RunWithElevatedPrivileges コードを開始する直前に SPUtility.ValidateFormDigest() を呼び出せばよいことがわかりました。これによってフォームの検証コードがスタックに入り、追加を正常に続行できるようになります。私自身のケースでは、LayoutsPageBase を継承しており、ASPX マークアップは他の _layouts ページと同じように構成されていて、<form> 要素と <FormDigest> コントロール インスタンスを既に含んだマスター ページを使用していました。このどちらかがページまたはマスターにない場合は、それらも追加する必要があります。AllowUnsafeUpdates コードが不要になるので、ページと処理全体がそれだけずっと安全になります。次回同じようなシナリオで作業をしているときは、この方法を検討してみてください。

これはローカライズされたブログ投稿です。原文の記事は、「A New Twist on an Old Friend - "The security validation for this page is invalid" - in SharePoint 2010」をご覧ください。