webForumDet fria alternativet

Databashantering

16 svar · 657 visningar · startad av andreas_lindh

andreas_lindhMedlem sedan jan. 20011 091 inlägg
#1

Jag har tittat lite i den här tråden
http://www.webforum.nu/showthread.php?s=&postid=520173#post520173

För att testa det här har jag kopierat koden som P skrivit

jag har skapat en funktion i BusinessL

Public Function Login(Username as string, password as string)
        Return(RetriveDataReader("SELECT * FROM users WHERE password = '"& password &"' and username='" & username &"' "))
        End Function

Hur gör jag nu för att använda den här datareadern på aspx sidan?

PatrikBMedlem sedan mars 20002 713 inlägg
#2

En datareader bör (ska) inte användas på .aspx-sidan. Strider mot OOP'n.

.aspx-sidan ska "prata" med lagret "närmast till höger" (BusinessLayer) som i sin tur "pratar med lagret närmast till höger" (BusinessDataLayer/DataLayer).

rent tekniskt:

Dim _dr As SqlDataReader = Login(Username, Password)

MEN!!!
Enligt mig ska denna metod egentligen inte returnera något annat än ett Booleskt värde (True/False) beroende på om inloggningen är lyckad eller inte.

Public Function Login(Username as string, password as string) As Boolean
	Dim _dr As SqlDataReader = RetriveDataReader("SELECT * FROM users WHERE password = '"& password &"' and username='" & username &"' ")
	Dim isMember As Boolean = _dr.Read()
	_dr.Close()
	Return isMember
End Function

cya,
PatrikB

andreas_lindhMedlem sedan jan. 20011 091 inlägg
#3

jag skapar ju datareadern i codebehindfilen för aspx sidan.

Ska man inte göra det? Och i så fall. Var ska man skapa datareadern?

andreas_lindhMedlem sedan jan. 20011 091 inlägg
#4

Jag har testat det där nu men får ett felmeddelande

Dim objBusinessL As BusinessL = New BusinessL()
        Dim _dr As OdbcDataReader = objBusinessL.Login(FixaTecken(tbUsername.Text), FixaTecken(tbPassword.Text))

        If _dr.Read Then
            Session("user") = _dr("id")
            Response.Redirect("inloggad.aspx")
        Else

        End If

Felet

Exception Details: System.InvalidOperationException: Invalid attempt to Read when reader is closed.

Source Error: 

Line 52:         Dim _dr As OdbcDataReader = objBusinessL.Login(FixaTecken(tbUsername.Text), FixaTecken(tbPassword.Text))
Line 53: 
Line 54:         If _dr.Read Then
Line 55:             Session("user") = _dr("id")
Line 56:             Response.Redirect("inloggad.aspx")
 

Source File: d:\inetpub\wwwroot\gService\default.aspx.vb    Line: 54
WalkerMedlem sedan okt. 2002185 inlägg
#5

andreas_lindh skrev:

jag skapar ju datareadern i codebehindfilen för aspx sidan.

Ska man inte göra det? Och i så fall. Var ska man skapa datareadern?

tanken är att datalagert, dit räknas en datareader skall endast finnas i datalagret. Datareadern skall sedan fylla ett objekt på något sätt. Detta objekt är ditt affärslagers objekt, en del av ditt logiklager, businesslayer eller vad man kallar det för. detta objekt skickar du sedan upp till din aspx sida..

Detta är det som är renast om man skall vara OO purist. Men det kan bli en hel del overhead om du bara har ett litet projekt då du måste skapa ett userobjekt ett usermanager objekt (databaslagret).

Om man skall göra det så oo som möjligt så skulle jag göra så här. Du skapar ett User object där du har en statisk metod Login(string username, string password). denna metod anropar din usermanager och här skapar du din datareader och läser in datan om du nu behöver ett helt objekt. så i c# blir det något sånt här..

i aspx sidan..

myUser = cUser.Login(username, password);

if (myUser.IsApproved == false)
{
// felhantering
}

Då du skapar ett nytt user objekt så är detta tomt, och således så returnerar IsApproved false per default.

i din User klass..

public static User Login(string usename, string password)
{
Usermanager dal = new Usermanager();
User myUser = new User();
myUser = dal.LoadUser(username, password);
if (myUser.IsLoggedIn == false)
{
/* felhantering.. eller om du vill ha det längre upp vilket nog känns mer ok */
}
return myUser;
}

i Usermanager så skapar du datareadern som hämtar datan för det aktuella objektet och fyller det med data.

Jag tycker detta fungerar bra men det finns säkert en massa andra metoder och tekniker för att lösa detta.. Men jag tror att pricipen är korrekt..

/w

PMedlem sedan jan. 20012 107 inlägg
#6

Walker skrev:

tanken är att datalagert, dit räknas en datareader skall endast finnas i datalagret. Datareadern skall sedan fylla ett objekt på något sätt. Detta objekt är ditt affärslagers objekt, en del av ditt logiklager, businesslayer eller vad man kallar det för.

2 skilda klasser alltså? En där dataobjektet skapas som returnerar det till affärslagret där valideringen görs?

red/citatfel

WalkerMedlem sedan okt. 2002185 inlägg
#7

P skrev:

Walker skrev:

tanken är att datalagert, dit räknas en datareader skall endast finnas i datalagret. Datareadern skall sedan fylla ett objekt på något sätt. Detta objekt är ditt affärslagers objekt, en del av ditt logiklager, businesslayer eller vad man kallar det för.

2 skilda klasser alltså? En där dataobjektet skapas som returnerar det till affärslagret där valideringen görs?

fattar inte riktigt vad du menar.. :r

PMedlem sedan jan. 20012 107 inlägg
#8

Typ:
Klass Data
Funktion päron()
'Make my object, dataset eller ngt
Retunerar till klass Business
End Function

Klass Business
'Hämtar från dataklassen
'Gör validering etc
Retunerar till presentationslagret

osv...

WalkerMedlem sedan okt. 2002185 inlägg
#9

Japp två skilda klasser.. Jag brukar dock inte skapa objektet i datalagert utan jag skickar objekt som en referens till datalagret..

tex i en user klass..

public void Load(){ datalager.FillObject(this);}

Datalagret hämtar sen data från datakällan och fyller det aktuella objektet.. Men det är bara en metod, det finns massvis av andra metoder och vad som är rätt för mig kan vara helt fel för någon annan person.. tex så vet jag att en del skickar har ett connectionobject som de bollar med i logiklagret.. Detta fungerar enligt dem kanon.. jag tycker inte om det..

andreas_lindhMedlem sedan jan. 20011 091 inlägg
#10

Nu har jag försökt göra som PatrikB sa att ha en funktion som returnerar true eller false

Public Function Login(ByVal Adress As String, ByVal password As String) As Boolean
                Dim _dr As OdbcDataReader = RetriveDataReader("SELECT * FROM wmUsers WHERE password = '" & password & "' and Adress='" & Adress & "' ")
                Dim isMember As Boolean = _dr.Read()
                _dr.Close()
                Return isMember
            End Function

Men jag får fortfarande felet
System.InvalidOperationException: Invalid attempt to Read when reader is closed.

funktionen RetriveDataReader ser ut så här.

Function RetriveDataReader(ByVal SqlStatement As String)
                Try

                    objConn.Open()
                    Dim Command As OdbcCommand = CreateCommand(SqlStatement)
                    Dim dr As OdbcDataReader = Command.ExecuteReader(CommandBehavior.CloseConnection)
                    objConn.Close()
                    Return dr

                Catch Exp As OdbcException
                    Throw (Exp)

                Finally
                    objConn.Close()
                End Try

            End Function
renholmMedlem sedan apr. 20012 048 inlägg
#11

Du har objConn.Close() i finally vilket gör att objConn stängs innan den kommer till Login funktionen.

PatrikBMedlem sedan mars 20002 713 inlägg
#12

När du kör:

_dr = cmd.ExecuteReader(CommandBehavior.CloseConnection)

så behöver du inte stänga connection. Det görs när du kör _dr.Close()

cya,
PatrikB

PMedlem sedan jan. 20012 107 inlägg
#13

Kör med datatable annars. Om du använder mysql kan du kolla på p.latmask.com/CodeGenP/CodeGenP.exe, det kan hjälpa dig ( den genererar all kod som behövs)

PatrikBMedlem sedan mars 20002 713 inlägg
#14

Har du läst Jimmy Nilssons artiklar på https://www.informit.com ?

Om inte, gör det. Just nu finns det fyra artiklar om "Data Containers" och en femte är väl på G snart, hoppas jag.

cya,
PatrikB

PMedlem sedan jan. 20012 107 inlägg
#15

Bara jag som inte hittar artiklarna?

JosefMedlem sedan mars 20023 123 inlägg
PatrikBMedlem sedan mars 20002 713 inlägg
#17

Det går inte att länka till artiklarna direkt.

I menyn till vänster välj "More Topics" under "Web Development".
Klicka sedan på NET i sectionen "In Articles".

Sedan heter artiklarna: Choosing Data Containers for .NET, Part 1

Totalt finns det 4 artiklar.

OK, de visar inte direkt hur man "ska göra" utan det är mer en genomgång av olika typer av DataContainers som DataSets, Hashtables etc som jag tycker att man bör läsa så man vet vad det finns för möjliga Data Containers.

cya,
PatrikB

Genererad på 367 ms · cache AV · v20260730165559-full.f96bc7eb