DanBlog

Il blog di Daniele Armanasco
posts - 48, comments - 73, trackbacks - 10

Thread asincrono e pagine asp.net

Contesto: devo lanciare un'operazione che può durare molto tempo eseguita da un metodo sincrono che non torna eventi (legacy). Devo fornire un feedback all'utente (una sorta di pagina clessidra) e, a lavoro terminato, mostrare il risultato.
Soluzione adottata: creo una pagina per iniziare l'operazione e configurarne i parametri (pagina Start), una autorefreshante per comunicare che il
lavoro è in corso (pagina Wait) e una pagina per mostrare i risultati (pagina Results).
La pagina Start:
- mette in sessione un flag per indicare che il calcolo è in corso
- istanzia un delegate per richiamare il metodo sincrono con un nuovo thread;
- lancia il nuovo thread passando eventuali parametri del metodo, un riferimento al metodo di callback e un riferimento al caller stesso
- carica la pagina Wait
Il caller del MetodoLungo:
- a lavoro completato richiama il metodo di callback sulla pagina Start
Il metodo di callback (su Start):
- riaggancia il chiamante
- recupera il risultato del calcolo usando EndInvoke sul chiamante
- mette il risultato in sessione
- setta il flag in sessione per indicare che il calcolo è terminato
La pagina Wait:
- ha un tag meta (magari inserito da codice) per fare il refresh automatico
- verifica il flag in sessione per sapere quando passare alla pagina dei risultati
La pagina Results:
- recupera il risultato dalla sessione e lo mostra

Codice:
pagina Start:
   public delegate TipoRisultatoCalcoloLungo MetodoLungoAsyncCaller(TipoParametro1MetodoLungo par1,   TipoParametro2MetodoLungo par2);

    public partial class StartPage
    {
     ...
     void Toolbar1_ButtonClick(object sender, ToolbarEventArgs ea)
        {
             
Session[SessionConstants.SCAN_IN_PROGRESS] = true;

                        // Create the delegate.
                        MetodoLungoAsyncCaller caller = new MetodoLungoAsyncCaller(MetodoLungo);

                        // Initiate the asychronous call.  Include an AsyncCallback
                        // delegate representing the callback method, and the data
                        // needed to call EndInvoke.
                        IAsyncResult result = caller.BeginInvoke(valorePar1, valorePar2,
                            new AsyncCallback(CallbackMethod),
                            caller);

                        // goto to "hourglass" page
                        Response.Redirect(WebFormsConstants.WAIT_ASPX);
        }
        ...
        // Callback method
        public void CallbackMethod(IAsyncResult ar)
        {
            // Retrieve the delegate.
            MetodoLungoAsyncCaller caller = (MetodoLungoAsyncCaller)ar.AsyncState;

            // Call EndInvoke to retrieve the results.
            TipoRisultatoCalcoloLungo risultato = caller.EndInvoke(ar);
            Session[SessionConstants.RISULTATO] = risultato;
            // set flag in session to comunicate scan completed
            Session[SessionConstants.SCAN_IN_PROGRESS] = false;
         }
         ...
}

pagina Wait:
protected void Page_Load(object sender, EventArgs e)
        {
            HtmlMeta meta = new HtmlMeta();
            meta.HttpEquiv = "refresh";
            meta.Content = "10";
            Header.Controls.Add(meta);

            if ((Boolean)Session[SessionConstants.SCAN_IN_PROGRESS] == false)
                Response.Redirect(WebFormsConstants.RESULT_ASPX);

            Message1.Text = "In Progress";
        }

 

Print | posted on venerdì 30 maggio 2008 06:45 | Filed Under [ Scoperte di un principiante ]

Feedback

Gravatar

# re: Thread asincrono e pagine asp.net

L'operazione purtroppo può durare anche diversi minuti (si tratta di un metodo eseguito da un componente COM che si interfaccia con una rete di strumenti hardware, che possono essere anche diverse decine). Per ora non gestiamo feedback parziali, ma in futuro dovremo farlo. Comunque stando così le cose posso provare anche ajax, così evito il continuo ricaricamento dell'intera pagina "clessidra".
01/06/2008 23:16 | Daniele Armanasco
Comments have been closed on this topic.

Powered by:
Powered By Subtext Powered By ASP.NET