3

私はMVCにかなり慣れていないので、何か欠けている場合はご容赦ください。

コントローラーの 1 つで、何らかの処理を行い、次のような文字列を出力するクラスを開始します。

[HttpPost]
public ActionResult Check(string reg)
{
    string sCarmodel;
    GetRegInfo gri = new GetRegInfo(reg, out sCarmodel);
    Session["test"] = sCarmodel;

    return View("Check");
}

ここまでは順調で、sCarmodel の出力はセッションに正しく保存され、後でビューでアクセスできます。ただし、クラスを完了するのに時間がかかるため、クラスを別のスレッドに配置する必要があり、View aschyncronosly を返す必要があります。だから私はこれを試しました:

[HttpPost]
public ActionResult Check(string reg)
{
    var getreginfoThread = new Thread(
        () =>
        {
            string sCarmodel;
            GetRegInfo gri = new GetRegInfo(reg, out sCarmodel);
            Session["test"] = sCarmodel;
        }
        );

    getreginfoThread.Start();

    return View("Check");
}

「sCarmodel」の値をクラス自体からデータベースに格納できることはわかっていますが、データベースの使用をスキップする方法を探していました。nullスレッドを使用すると、sCarmodel の値が Session に格納されず、後で取得しようとするとSession が格納されます。

スレッド内でクラスから値にアクセスする方法について誰かアドバイスをいただけますか?

ありがとう!

編集: 問題は解決しました。提案してくれたみんなに感謝します!

4

7 に答える 7

3

リクエストの処理中にカスタム オブジェクトを Session に配置します。

このカスタム オブジェクトへの参照をバックグラウンド スレッドに渡します。

バックグラウンド スレッドでカスタム オブジェクトのプロパティを設定します。

必要な同期を必ず行ってください。

于 2013-08-03T12:23:59.030 に答える
0

スレッドセーフではないため、スレッドで Session オブジェクトを使用しないことをお勧めします。ASP.NET では、各要求に独自のスレッドと独自のセッションがあります。

(残念ながら)実際の問題について説明したことはないので、何を解決しようとしているのかはよくわかりませんが、新しいスレッドを手動でスピンアップしてセッションにデータを入れることは解決策ではありません。

バックグラウンドで何かを実行している間に Web サーバーが他のクライアントにサービスを提供できるようにするために非同期で実行したい場合は、おそらく非同期コントローラーを見てください: http://www.asp.net/mvc/tutorials/mvc-4/using-asynchronous -aspnet-mvc-4 のメソッド

繰り返しになりますが、適切な解決策を提案するために何を達成しようとしているのかを知ることは非常に役立ちます.

于 2013-08-03T13:25:57.673 に答える
0

クラスのインスタンスを TempData に格納することで問題を解決しました。また、Thread の代わりに、はるかに優れた Task を使用します。これが私の解決策です:

[HttpPost]
        public ActionResult GetRegInfo(string reg)
        {
            var gri = new GetRegInfo(reg);
            TempData["GetRegInfo"] = gri;

            Action<object> action = (object obj) => gri.Start();
            var t1 = new Task(action, "GetRegInfo");   
            t1.Start();

            return View("bilforsakring");
        }

後で、Ajax で JavaScript タイマーを使用して、次のような値を取得します。

[OutputCache(NoStore = true, Duration = 0)]
        public ActionResult GetRegInfoAjax()
        {
            if (TempData["GetRegInfo"] != null)
            {
                var g = (GetRegInfo)TempData["GetRegInfo"];  
                return Content(g.sCarmodel);
            }
            else
            {
                return Content("null");
            }
        }
于 2013-08-03T13:38:06.193 に答える
0

ただし、クラスを完了するのに時間がかかるため、クラスを別のスレッドに配置する必要があり、View aschyncronosly を返す必要があります。

違う。これは、この問題を解決するための完全に間違った方法です。ASP.NET アプリケーションでは、永続的なストレージにその作業を保存していない限り、実行すべき作業がさらにある場合は決して戻ってはなりません。

作業をメモリに保持する (つまり、スレッドまたはタスクを使用する) ことは、正しくない解決策です。

正しい解決策は、永続ストレージ (Azure Queue、MSMQ、WebSphere MQ など) を使用して実行する作業を保存し、そのキューを読み取って適切なアクションを実行し、結果を別の永続ストレージに格納する別のサービスを用意することです。データ構造。次に、クライアントに "結果" データ構造をポーリング (HTTP 要求など) させたり、結果が保存されたときにクライアント (SignalR など) に通知させたりすることができます。

私のブログで詳細を説明します。また、安全でないルートを確実に使用したい場合に使用するサンプル コードもいくつかあります。

于 2013-08-03T15:31:24.633 に答える