Cookie の問題から引き出すカスタム モデル バインダー?
-
18-09-2019 - |
質問
私は次のことをしようとしています。
デフォルトのモデル バインダーを使用して、クエリ文字列値からオブジェクトをバインドします。
それが失敗した場合は、Cookie 値からオブジェクトをバインドしようとします。
ただし、このオブジェクトに dataannotations を使用しているため、次の問題が発生しています。
- クエリ文字列パラメーターがない場合、デフォルトのモデル バインダーは必須フィールドの検証エラーも登録しません。プロパティ自体がクエリ文字列コレクションに含まれていない場合、これらのバリデーターは起動されないようです。この動作を変更するにはどうすればよいでしょうか?必須フィールドがクエリ文字列にない場合はエラーになるようにしたいです。
- モデル検証エラーが発生した場合は、Cookie からモデルをロードして、オブジェクトを再検証したいと思います。自分で設定したオブジェクトを検証するためにモデル バインダーを取得する方法がわかりません。
これが私がこれまでに持っているものです。
public class MyCarBinder : DefaultModelBinder
{
public override object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
{
var myCar = base.BindModel(controllerContext, bindingContext);
if (!bindingContext.ModelState.IsValid)
{
myCar = MyCar.LoadFromCookie();
// Not sure what to do to revalidate
}
return myCar;
}
}
これを適切に行う方法についてのアドバイスをいただければ幸いです。
解決
まあ、私はそれを自分で解決しました。ここケースの誰もがコメントを持っているか、それを使用したい場合があります。
ソリューションを投稿 public class MyCarBinder : DefaultModelBinder
{
public override object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
{
var queryStringBindingContext = new ModelBindingContext()
{
FallbackToEmptyPrefix = bindingContext.FallbackToEmptyPrefix,
ModelMetadata = bindingContext.ModelMetadata,
ModelName = bindingContext.ModelName,
PropertyFilter = bindingContext.PropertyFilter,
ValueProvider = new QueryStringValueProvider(controllerContext),
ModelState = new ModelStateDictionary()
};
var myCar = base.BindModel(controllerContext, queryStringBindingContext);
if (queryStringBindingContext.ModelState.IsValid)
return myCar;
// try to bind from cookie if query string is invalid
var cookieHelper = new Helpers.ControllerContextCookieHelper(controllerContext);
NameValueCollection nvc = cookieHelper.GetCookies(Helpers.CookieName.MyCar);
if (nvc == null)
{
bindingContext.ModelState.Merge(queryStringBindingContext.ModelState);
return myCar;
}
var cookieBindingContext = new ModelBindingContext()
{
FallbackToEmptyPrefix = bindingContext.FallbackToEmptyPrefix,
ModelMetadata = bindingContext.ModelMetadata,
ModelName = bindingContext.ModelName,
PropertyFilter = bindingContext.PropertyFilter,
ValueProvider = new NameValueCollectionValueProvider(nvc, CultureInfo.InvariantCulture),
ModelState = new ModelStateDictionary()
};
var myCarFromCookie = base.BindModel(controllerContext, cookieBindingContext);
if (cookieBindingContext.ModelState.IsValid)
{
MyCar temp = myCarFromCookie as MyCar;
if (temp != null)
temp.FromCookie = true;
return myCarFromCookie;
}
else
{
bindingContext.ModelState.Merge(queryStringBindingContext.ModelState);
return myCar;
}
}
}
所属していません StackOverflow