Ska försöka sammanfatta det jag tror jag kan efter att ha vigt ett bra stund till genomsökning på forumet. Är väldigt tacksam för kommentarer!
Mitt mål är att skapa en inloggningssida som är säker! Så säker den KAN bli förutom att använda certifikat vill säga.
Först och främst - databasen.
Den läggs ovanför wwwroot på servern.
server/wwwroot/index.asp
server/db/databas.mdb
Detta förhindrar från att användare kan ändra/ladda hem/förstöra databasen. Om webbhotellet har spärrat mappen vill säga. Detta innebär alltså att databasen inte behöver lösenordsskyddas.
Ändå döper jag databasen till bcbcbvvcdsadsadasd.mdb och lösenordsskyddar den. En fattigmanskryptering mao:)
Inkluderade filer ska inte heta .inc utan .asp för att förhindra nedladdning av dem och därigenom läsning av kod.
I mitt fall använder jag Access och vill få bort '
Passar dessutom på att rensa bort lite annat obehag som rekomenderades i artiklen ovan.
Ta bort fnutt mm.
function safeSQL(strText)
strText = replace(strText,"'","''")
dim badChars
dim newChars
badChars = array("select", "drop", ";", "--", "insert", "delete", "xp_")
newChars = strText
for i = 0 to uBound(badChars)
newChars = replace(newChars, badChars(i), "")
next
strText=newChars
safeSQL=strText
end function
user = safeSQL(Request.Form ("uname"))
pass = safeSQL(Request.Form ("pword"))
SQL-fråga
sql = "select * FROM users WHERE " & _
"User = '" & user & "' and " & _
"Pass = '" & pass & "' "
Begränsar dessuom inputfälten för att ytterliga försvåra strul.
<input name="uname" type="text" maxlength="15">
Ett övrigt tillägg till SQL-injections som jag läst om men inte ser ut att behöva applicera här är att titta om ID och dylikt är numeriskt med "isNumeric()" eller konvertera direkt t ex CLng(Request.QueryString("ID")).
Slutligen är det dags för själva loginchecken och kollen att man är inloggad. Iom att det är ASP som gäller så förutsätter jag att SESSIONS är säkrast och bäst. Läste någonstans att det slöar ner men hellre det än intrång (i databasen).
<%@LANGUAGE="VBSCRIPT" CODEPAGE="1252"%>
<!--#include file="global_scripts/oDB.asp"-->
<% If Request("action")="" Then
Session.abandon()
%>
<!DOCTYPE HTML Public "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
<title>Login</title>
</head>
<body>
<form method="post" action="login.asp?action=login">
USER: <input name="uname" type="text" maxlength="15">
<br>
PASS: <input name="pword" type="password" maxlength="15">
<br>
<br>
<input type="submit" name="Submit" value="Submit">
</form>
<%
Else
dim user, pass, nextpage
function safeSQL(strText)
strText = replace(strText,"'","''")
dim badChars
dim newChars
badChars = array("select", "drop", ";", "--", "insert", "delete", "xp_")
newChars = strText
for i = 0 to uBound(badChars)
newChars = replace(newChars, badChars(i), "")
next
strText=newChars
safeSQL=strText
end function
user = safeSQL(Request.Form ("uname"))
pass = safeSQL(Request.Form ("pword"))
Set Rs=Server.CreateObject("ADODB.Recordset")
sql = "select * FROM users WHERE " & _
"User = '" & user & "' and " & _
"Pass = '" & pass & "' "
Rs.Open sql, DataConn
If NOT Rs.EOF Then
Session("userId")=RS(0)
nextPage="default.asp"
Else
nextPage="login.asp"
End If
Response.Redirect(nextPage)
End If
%>
</body>
</html>
<!--#include file="global_scripts/cDB.asp"-->
Och den skyddade sidan default.asp ....
<%@LANGUAGE="VBSCRIPT" CODEPAGE="1252"%>
<%
'cacha inte sidan
Response.Expires=0
Response.ExpiresAbsolute = Now() -2
Response.AddHeader "pragma", "no-cache"
Response.AddHeader "cache-control", "private"
Response.CacheControl = "no-cache"
'om sessionen inte finns åker man till inloggningssidan
If Session("userId")="" Then
Response.Redirect("login.asp")
Else
%>
<!DOCTYPE HTML Public "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
<title>Skyddad sida</title>
</head>
<body>
Denna sida är skyddad ...<br>
<a href="login.asp">Logga ut</a>
</body>
</html>
<%End If%>
I början av loginsidan har jag Session.abandon() för att tömma sessionen om man kommer dit genom att logga ut t ex. På de skyddade sidorna kollar jag sessionen samt säger till att sidan inte ska cachas.
Så vad tror vi? Som sagt väldigt tacksamt för svar:)
Laddar även upp min testmiljö för lek och testning:)
I mitt fall använder jag Access och vill få bort '
Passar dessutom på att rensa bort lite annat obehag som rekomenderades i artiklen ovan.
Tycker att förslagen på sista sidan i den där artikeln var rätt dåliga. Att skydda sig från injektioner genom att ta bort "farliga" tecken eller fraser är värdelöst. Använd parametriserade frågor (sök här i forumet) så kan man skriva in vad som helst utan att kunna härja runt i din databas.
Då slipper du även quotingfunktioner som safeSQL. För det första är de bökiga, en extra grej att använda överallt, de kräver att du verkligen kommer ihåg ALLA kombinationer som kan ställa till problem, och inte ens då är de nödvändigtvis säkra. I PHP kunde man en gång i tiden lura sig runt quotingfunktioner genom att använda kluriga kombinationer av teckenuppsättningar. Med lite otur dyker det upp något likadant till ASP. Kanske inte så sannolikt, men icke desto mindre är quotingfunktioner en extra potentiell felkälla som kan undvikas med parametriserade frågor.
Sen, om man vill ha mer lätthanterad kod och därmed färre säkerhetsrisker, ska man använda sig av ett Riktigt Webbramverk, som ASP.NET eller J2EE, inte en scriptlösning som ASP.
1. Bra!
2. Ja, det skadar inte
3. Utan tvekan! Ett måste!
4. Håller med spango. Om man måste skydda sig genom att ta bort specifika ord så är man helt fel ute. Parametriserade frågor (ADODB.Command) är det som gäller om man vill ha totalt injection-skydd. Dessutom ger det vissa prestandafördelar och det är, inte minst, roligare att använda, jämfört med konkateneringshysterin som man kan hamna i annars.
5. IsNumeric ska man inte lita på, utan den bör endast användas i valideringssammanhang. Typomvandling är däremot att rekommendera.
6a. Det är riktigt att sessioner är lite prestandakrävande, men det blir inte hållbart att bygga ett inloggningssystem utan dem (man kan överleva med endast egna cookies, men då får man bygga en hel del runt ikring, som antagligen blir mer prestandakrävande)
6b. Funktionsdeklaration ska ligga utanför flödet, dvs. inte inne i en "else"
I övrigt såg det helt ok ut.
Spango har helt rätt när han skriver "Sen, om man vill ha mer lätthanterad kod och därmed färre säkerhetsrisker, ska man använda sig av ett Riktigt Webbramverk, som ASP.NET eller J2EE, inte en scriptlösning som ASP."
Det primära där är inte ASP:s tillkortakommanden, utan just att "lätthanterad kod [ger] färre säkerhetsrisker". Sträva efter att göra ditt system enkelt och strukturerat, så kan du bygga fullgod säkerhet även i ASP.
Varför jag la en funtion i elsesatsen kan bara min sovande hjärna svara på. I "verkligheten" hade jag nog inkluderat en fil ist. Jag har med den här ändå trots att ni ni sagt nej till att byta ut ord. Mest för att sammanfatta vad som är sagt.