Istanziare una classe nel global.asax

sabato 21 gennaio 2006 - 01.00

hopera Profilo | Newbie

Ciao a tutti,

ho creato una classe Sessione che dovrebbe gestire l'elenco degli utenti loggati .
Vorrei poter istanziare la classe nell'evento application_start e fino a quì tutto bene penso.
Vorrei a questo punto in una pagina di login poter accedere all'oggetto creato nel global.asax ma non riesco a vederlo.
Avete qualche suggerimento in merito ? Spero di essermi spiegato bene.

Grazie come sempre in anticipo

GD

micto27 Profilo | Senior Member

In che modo stai provando a referenziare l'istanza di cui parli?

Ciao.

hopera Profilo | Newbie

Ciao, allora ho abbozzato in un file Sessioni.cs una classe fatta così:

public class Sessioni:System.Web.HttpApplication
{
private ArrayList i_objArrUtentiInSessione;
private string i_strUtenteCorrente;

public Sessioni()
{
i_objArrUtentiInSessione = new ArrayList(0);
i_strUtenteCorrente="";
}

public void AggiungiUtenteInSessione(string strUtenteCorrente)
{
i_strUtenteCorrente=strUtenteCorrente;
i_objArrUtentiInSessione.Add(i_strUtenteCorrente);
}

public int NumeroUtentiInSessione
{
get
{
return(i_objArrUtentiInSessione.Count );
}
}

public bool UtenteInSessione(string strUtenteCorrente)
{
return i_objArrUtentiInSessione.Contains(strUtenteCorrente);
}

}

Nel global.asax faccio così:


protected void Application_Start(Object sender, EventArgs e)
{
ArchivioSessioni = new Sessioni();
}


A questo punto mi piacerebbe usare l'oggetto "ArchivioSessioni" anche nella pagina di login, dove dovrei riempirlo con gli utenti che si loggano.

... Solo che non lo vedo.

Ciao grazie GD



micto27 Profilo | Senior Member

Ti passo uno spunto (se ti può andar bene). Per far prima ho però usato VB.NET, lascio a te la conversione.

Ciao, Michele

//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////


//--> la classe Sessioni non mi sembra serva derivarla da System.Web.HttpApplication


//--> Aggiungerei il seguente metodo Static (per far prima te lo scrivo in VB.NET
// in questo modo nel global.asax non serve far nulla.
//
// nel resto dell'applicazione e quindi anche nella pagina di cui parlavi puoi referenziare la classe
// nel seguante modo:

dim ss as Sessioni = Sessioni.Current()

---------------------------


public shared function Current() as Sessioni

dim app as System.Web.HttpApplicationState
app = System.Web.HttpContext.Current.Application

dim ss as Sessioni = app("Sessioni")
if ss is Nothing then
ss = new Sessioni()
app("Sessioni") = ss
end if

return ss
end function

//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////


hopera Profilo | Newbie

Ciao Michele,
sei stato molto gentile ... ho seguito il metodo che mi hai consigliato.
Ho tradotto il codice in c# e sembra funzionare tutto.
Mi sono solo perso un passaggio cioè l'istanziare una classe all'interno della classe stessa.
Poresti spiegarmi se hai voglia/tempo qualcosa in + su questo particolare ?
Grazie in anticipo
Ciao H

micto27 Profilo | Senior Member

Ciao, mi fa piacere che hai risolto.
Per quanto riguarda il chiarimento che richiedi:

la funzione "public shared function Current() as Sessioni" poteva benissimo essere scritta
in un modulo a parte, o in un'altra classe, in quanto il suo scopo è quello di gestire
in modo trasparente l'oggetto Application("Sessioni").
Io in genere rimappo sempre i vari oggetti Application("...") e Session("...") con delle funzioni
o con delle proprietà, in questo modo il resto dell'applicazione non deve curarsi di quale chiave
è stata assegnata (in Session e Application) al singolo oggetto e che così rimane confinata (la chiave) in un unico
punto (la funzione Current in questo caso).
La scelta di mettere tale funzione come funzione Shared esposta dalla stessa classe Sessioni
è solo un'idea per mantenere tutta la logica che gestisce la classe all'interno della classe stessa.

Il fatto che all'interno di tale funzione venga istanziata la classe stessa non ha nulla di strano proprio
perchè si tratta di una funzione Shared (per te Static credo). E' un po' come nel caso:

dim sGuid as string = Guid.NewGuid.ToString() --> NewGuid è un metodo Static esposto dalla classe Guid e quindi
posso utilizzarlo direttamente, senza istanziare la classe Guid.

Spero di non averti fatto confusione :)

Michele.




hopera Profilo | Newbie

Grazie Michele,

quanto hai scritto tutto risulta "abbastanza chiaro".

Forse mi è poco chiaro l'utilizzo, nel senso: quando nella pagina di login intercetto l'utente , e se si è loggato lo

aggiungo come dire agli utenti loggati così:

ss = Sessioni.Current():

ss.Aggiungi.utente(nomeutente):

AggiungiUtente è un metodo che nella classe aggiunge un metodo ad un array.

se ad ogni pagina di login successivamente faccio stampare il numero totale degli utenti loggati mi da sempre 1.

Forse dovrei utilizzare un metodo statico che salva in un array statico.

Ma così aggiro l'utilizzo della mappatura dell'application come mi hai indicato tu.

Esatto oppure no ?

Grazie ancora ciao H









micto27 Profilo | Senior Member

Ciao,

il metodo Sessioni.Current non fa altro che rimappare sempre, per tutta la durata dell'Application, la stessa istanza della classe Sessioni, il cui riferimento è registrato in Application (.... app("Sessioni") = ss)
Di conseguenza il metodo AggiungiUtente va sempre ad insistere sullo stesso ArrayList "i_objArrUtentiInSessione",
pertanto mi sembra strano che che dopo ogni login tale array contenga sempre e solo 1 elemento.

E' possibile che abbia qualche istanziazione di troppo della classe Sessioni? (L'unica istanziazione dovrebbe essere all'interno del metodo Current).

Se vuoi puoi postarmi il codice per verificare.

Michele

hopera Profilo | Newbie

Grazie Michele, molto gentile
anch'io mi sarei aspettato la stessa cosa.

La chiamata la faccio così:

s = Sessioni.Current();

s.AggiungiUtenteInSessione(txtUtente.Text);

Response.Write(s.NumeroUtentiInSessione.ToString());

dove s.NumeroUtentiInSessione è una proprietà che espone array.count sostanzialmente.

Ciao H

hopera Profilo | Newbie

Ciao Michele , ti riposto il codice della classe con la modifica che mi hai indicato.
Grazie di nuovo ciao H


public class Sessioni
{

private ArrayList i_objArrUtentiInSessione;
private string i_strUtenteCorrente;

public Sessioni()
{
i_objArrUtentiInSessione = new ArrayList(10);
i_strUtenteCorrente="";
}

public void AggiungiUtenteInSessione(string strUtenteCorrente)
{
i_strUtenteCorrente=strUtenteCorrente;
i_objArrUtentiInSessione.Add(i_strUtenteCorrente);
}

public int NumeroUtentiInSessione
{
get
{
return(i_objArrUtentiInSessione.Count);
}
}

public string UtenteCorrente
{
get
{
return(i_strUtenteCorrente);
}
}

public bool UtenteGiaInSessione(string strUtenteCorrente)
{
return i_objArrUtentiInSessione.Contains(strUtenteCorrente);
}

public static Sessioni Current()
{
System.Web.HttpApplicationState app;

app = System.Web.HttpContext.Current.Application;

Sessioni ss;

ss = new Sessioni();

app.Add("Sessioni",ss);

return ss;
}


}
}

micto27 Profilo | Senior Member

Ciao,
era come pensavo quando, nel precedente post, ti chiedevo se della classe veniva fatta una sola
istanziazione.
Quando hai tradotto il metodo Current ti sei dimenticato un'istruzione fondamentale:

public shared function Current() as Sessioni

dim app as System.Web.HttpApplicationState
app = System.Web.HttpContext.Current.Application

dim ss as Sessioni = app("Sessioni")
if ss is Nothing then
ss = new Sessioni()
app("Sessioni") = ss
end if

return ss
end function

traducendo in C# hai dimenticato di tradurre

if ss is Nothing then
...
...
end if

di conseguenza ogni volta che invochi il metodo Current dai luogo ad una nuova istanziazione
della classe Sessioni

ss = new Sessioni();

ripartendo quindi con l'array degli utenti vuoto.


Michele


hopera Profilo | Newbie

vero, che sbadato .... e dire che me l'avevi anche scritto.
Lo devo aver cancellato erroneamente.

Grazie per la disonibilità, sei veramente molto gentile.
A presto ciao H

Partecipa anche tu! Registrati!
Hai bisogno di aiuto ?
Perchè non ti registri subito?

Dopo esserti registrato potrai chiedere
aiuto sul nostro Forum oppure aiutare gli altri

Consulta le Stanze disponibili.

Registrati ora !
Copyright © dotNetHell.it 2002-2024
Running on Windows Server 2008 R2 Standard, SQL Server 2012 & ASP.NET 3.5