<%
Set fileSystemObject = Server.CreateObject("Scripting.FileSystemObject")
' ... '
Set fileSystemObject = Nothing
%>
GetFolder 메소드로 폴더에 대한 객체 얻기
[Scripting.FileSystemObject].GetFolder 메소드는 폴더를 특정하는 경로를 받아서 이에 대한 객체를 반환한다.
<%
Set fileSystemObject = Server.CreateObject("Scripting.FileSystemObject")
Set folder = fileSystemObject.GetFolder(경로)
' ... '
Set folder = Nothing
Set fileSystemObject = Nothing
%>
이 때, 경로는 하드코딩도 되겠으나, Server.MapPath 메소드를 조합하면 다음과 같이 ASP 파일이 위치한 로컬 경로를 기준으로 한 상대 경로도 가능하다.
<%
Set fileSystemObject = Server.CreateObject("Scripting.FileSystemObject")
Set folder = fileSystemObject.GetFolder(Server.MapPath("."))
' ... '
Set folder = Nothing
Set fileSystemObject = Nothing
%>
현재 지정된 폴더의 절대 경로 얻기
위와 같이 얻은 폴더 객체의 절대 경로는 다음과 같이 Path 프로퍼티로 구할 수 있다.
<%=folder.Path%>
현재 지정된 폴더 속 하위 폴더의 개수
위와 같이 얻은 폴더 객체에서 하위 폴더가 몇 개인지를 알기 위해 다음과 같이 SubFolders.Count 프로퍼티를 사용할 수 있다.
<%=folder.SubFolders.Count%>
현재 지정된 폴더 속 파일의 개수
위와 같이 얻은 폴더 객체에서 파일이 몇 개인지를 알기 위해 다음과 같이 SubFolders.Count 프로퍼티를 사용할 수 있다.
<%=folder.Files.Count%>
폴더 속 폴더를 하나씩 순회하기
SubFolders 프로퍼티는 그 자체가 Collection 객체이기도 하므로 다음과 같이 For Each 루프를 돌려서 하위 폴더들을 하나씩 순회할 수 있다.
<%
Set fileSystemObject = Server.CreateObject("Scripting.FileSystemObject")
Set folder = fileSystemObject.GetFolder(Server.MapPath("."))
For Each f in folder.SubFolders ' f is also Folder object
' ... '
Next
Set folder = Nothing
Set fileSystemObject = Nothing
%>
폴더 속 파일을 하나씩 순회하기
마찬가지로 Files 프로퍼티도 그 자체가 Collection 객체이기도 하므로 다음과 같이 For Each 루프를 돌려서 폴더 속 파일들을 하나씩 순회할 수 있다.
<%
Set fileSystemObject = Server.CreateObject("Scripting.FileSystemObject")
Set folder = fileSystemObject.GetFolder(Server.MapPath("."))
For Each f in folder.Files ' f is File object
' ... '
Next
Set folder = Nothing
Set fileSystemObject = Nothing
%>
서버 로컬 경로 내 파일 및 폴더 순회 예
다음은 asp 파일 자신이 위치한 폴더 내 파일과 하위 폴더들을 순회하여 클라이언트에게 보여주는 예이다.
<%@ language="VBScript" codepage="65001" %>
<%
Session.CodePage = "65001"
Response.ContentType = "text/html"
Response.AddHeader "Content-Type", "text/html;charset=UTF-8"
Response.Charset = "UTF-8"
%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
<html>
<head>
<title>codingCat.kr</title>
<meta http-equiv="Content-Type" content="text/html;charset=UTF-8">
</head>
<body>
<%
fileSystemPath = Server.MapPath(".")
Dim fileSystemObject
Dim fileSystemFolder
Set fileSystemObject = Server.CreateObject("Scripting.FileSystemObject")
Set fileSystemFolder = fileSystemObject.GetFolder(fileSystemPath)
%>
<p>Local Path: <code><%=fileSystemFolder.Path%></code></p>
<p>FOLDER(S): <code><%=fileSystemFolder.SubFolders.Count%></code> item(s).</p>
<ul>
<% For Each f in fileSystemFolder.SubFolders %><li>[<%=f.Name%>]</li><% Next %>
</ul>
<p>FILE(S): <code><%=fileSystemFolder.Files.Count%></code> item(s).</p>
<ul>
<% For Each f in fileSystemFolder.Files %><li><%=f.Name%></li><% Next %>
</ul>
<%
Set fileSystemFolder = Nothing
Set fileSystemObject = Nothing
%>
</body>
</html>
본 시리즈에서는 웹 개발을 할 때 자주 사용되는 기능인 로그인/로그아웃 기능에 대한 예제를 정리한다. 아이디와 암호가 일치할 경우 이 상태를 쿠키cookie나 세션session에 기억시키고, 이후 페이지 접속 시 해당 쿠키 또는 세션의 보유 여부에 따라 로그인한 이용자와 로그인하지 않은 이용자를 구분하고 서로 다른 페이지를 보여주도록 하는 것이 본 시리즈에서 구현하는 주된 기능이다.
본 게시물에서는 ASP.NET 소스 코드로 세션에 의한 로그인/로그아웃 기능을 구현한다. 로그인 화면에서 아이디와 암호를 맞게 입력했다면 서버에 로그인 정보를 보관하고 이 정보에 접근할 수 있는 식별 번호를 클라이언트의 쿠키로 전송한다. 이후 클라이언트는 페이지를 접속할 때마다 쿠키를 통해 세션 번호를 서버에 전달하고, 서버는 해당 번호의 세션이 보유한 유효성 여부를 판별하여 회원 페이지를 보여줄 것인지, 비회원 페이지를 보여줄 것인지를 결정하게 된다.
step1.aspx - 로그인 화면
이 페이지를 통해 사용자로부터 아이디와 암호를 입력받는다. 아이디가 전달될 매개변수 이름은 trialUsername이라 하고 암호가 전달될 매개변수 이름은 trialPassword라 이름 붙인다. 예제 소스 코드의 구조를 단순하게 하기 위하여 아이디와 암호에 대한 보안 조치 등은 생략한 채 쿠키와 POST 데이터를 통해 직접 사용자 이름과 암호가 전달될 것이다.
위 소스 코드에서는 사용자 이름과 암호를 입력받는 폼form을 출력한다. name 속성이 각각 trialUsername과 trialPassword인 input을 통해 사용자 이름과 암호를 입력받은 뒤 POST 방식으로 다음 파일인 step2.aspx로 전달할 것이다.
step2.aspx - 사용자 인증
이 페이지는 step1.aspx에서 전달된 아이디(trialUsername)/암호(trialPassword)가 미리 준비된 아이디(authorizedUsername)/암호(authorizedPassword)와 일치하는지 여부를 검사할 것이다. 일치하면 membershipUsername와 membershipPassword라는 세션 변수에 각각 아이디와 암호를 보관하고, 해당 세션의 식별번호를 쿠키를 통해 클라이언트로 전송할 것이다. 일치하지 않으면 별도의 오류 메시지를 보여줄 것이다.
<%@ Page Language="C#" CodePage="65001" %>
<%
Response.Charset="UTF-8";
Response.ContentType="text/html;charset=UTF-8";
Session.CodePage=65001;
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>2 단계 : 사용자 인증</title>
<style>a { color: #0000FF; }</style>
<%--------------------------------------------------------------------
사용자 인증 로직
이름과 암호를 비교하며 승인되면 true, 승인 안 되면 false를 반환한다.
--------------------------------------------------------------------%>
<script language="C#" runat="server">
// 아래 이름의 사용자면 로그인 승인 함.
private const string authorizedUsername = "codingCat";
// 아래의 암호를 입력하면 로그인 승인 함.
private const string authorizedPassword = "qwerty123456!";
// 로그인 승인 시 true, 아니면 false
private bool authorizeStatus = false;
// authorizeMembership(trialUsername, trialPassword)
// 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
// trialUsername : 로그인을 시도하는 사용자 이름
// trialPassword : 로그인을 시도하는 사용자가 입력한 암호
// 로그인 승인하면 true를 반환하고 승인 거부 시 false를 반환한다.
private static bool authorizeMembership(string trialUsername, string trialPassword)
{
// 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
if (string.Equals(trialUsername, authorizedUsername))
{
// 이름이 일치하면, 암호가 같은지 검사
if (string.Equals(trialPassword, authorizedPassword))
{
// 이름과 암호가 모두 일치하면 로그인 승인
return true;
}
}
// 그렇지 않을 경우 로그인 거부
return false;
}
</script>
<%--------------------------------------------------------------------
웹 페이지 헤더 영역
이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다.
--------------------------------------------------------------------%>
<script language="C#" runat="server">
private void Page_Load(object sender, EventArgs e)
{
string trialUsername = null;
string trialPassword = null;
this.authorizeStatus = false;
// POST 방식으로 전달된 데이터 중 trialUsername이라는 데이터가 있는지 확인
if (Request.Form["trialUsername"] != null)
{
// trialUsername이 존재하면, trialPassword라는 데이터도 있는지 확인
if (Request.Form["trialPassword"] != null)
{
// POST 데이터에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
trialUsername = Request.Form["trialUsername"];
trialPassword = Request.Form["trialPassword"];
// trialUsername과 trialPassword가 모두 수신되면,
// 앞서 정의된 authorizeMembership 메서드로 로그인 요청한다.
this.authorizeStatus = authorizeMembership
(
trialUsername,
trialPassword
);
}
}
// 로그인 요청이 승인되었다면
if (this.authorizeStatus)
{
// membershipUsername이라 이름붙인 세션 변수에
// 사용자 이름을 기록한다.
Session["membershipUsername"] = trialUsername;
// membershipPassword이라 이름붙인 세션 변수에
// 사용자 암호를 기록한다.
Session["membershipPassword"] = trialPassword;
// 세션의 유효 기간은 12시간으로 한다.
Session.Timeout = 12 * 60;
}
return;
}
</script>
</head>
<%--------------------------------------------------------------------------
웹 페이지 본문 영역
------------------------------------------------------------------------%>
<body>
<header>
<h1>2 단계 : 사용자 인증</h1>
</header>
<hr />
<section>
<% if (authorizeStatus) { %>
<%-- 로그인 승인 되었다면... --%>
<p>로그인에 성공했습니다.</p>
<p><a href="./step3.aspx">회원 페이지</a></p>
<% } else { %>
<%-- 로그인 거부 되었다면... --%>
<p>로그인에 실패했습니다.</p>
<p><a href="./step1.aspx">로그인 화면</a></p>
<% } %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.aspx">1 단계(로그인)</a> | </span>
<span><strong>2 단계(사용자 인증)</strong> | </span>
<span><a href="./step3.aspx">3 단계(회원 페이지)</a> | </span>
<span><a href="./step4.aspx">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
ASP의 경우 세션 정보들은 객체의 형태로 메모리에 보관된다.
step3.aspx - 회원 전용 페이지
클라이언트 측으로부터 쿠키에 보관된 세션 식별 번호를 전달받는다. 서버의 특정 위치에서 해당 번호를 갖는 세션을 읽어온 후, 로그인 상태임이 확인되면 회원 전용 페이지를 출력한다. 그렇지 않다면 비회원용 페이지를 출력한다.
<%@ Page Language="C#" CodePage="65001" %>
<%
Response.Charset="UTF-8";
Response.ContentType="text/html;charset=UTF-8";
Session.CodePage=65001;
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>3 단계 : 회원 페이지</title>
<style>a { color: #0000FF; }</style>
<%--------------------------------------------------------------------
사용자 인증 로직
이름과 암호를 비교하며 승인되면 true, 승인 안 되면 false를 반환한다.
--------------------------------------------------------------------%>
<script language="C#" runat="server">
// 아래 이름의 사용자면 로그인 승인 함.
private const string authorizedUsername = "codingCat";
// 아래의 암호를 입력하면 로그인 승인 함.
private const string authorizedPassword = "qwerty123456!";
// 로그인 승인 시 true, 아니면 false
private bool authorizeStatus = false;
// authorizeMembership(trialUsername, trialPassword)
// 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
// trialUsername : 로그인을 시도하는 사용자 이름
// trialPassword : 로그인을 시도하는 사용자가 입력한 암호
// 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
private static bool authorizeMembership(string trialUsername, string trialPassword)
{
// 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
if (string.Equals(trialUsername, authorizedUsername))
{
// 이름이 일치하면, 암호가 같은지 검사
if (string.Equals(trialPassword, authorizedPassword))
{
// 이름과 암호가 모두 일치하면 로그인 승인
return true;
}
}
// 그렇지 않을 경우 로그인 거부
return false;
}
</script>
<%--------------------------------------------------------------------
웹 페이지 헤더 영역
클라이언트의 쿠키로부터 전송된 사용자 이름 및 암호를 읽어온다.
--------------------------------------------------------------------%>
<script language="C#" runat="server">
private void Page_Load(object sender, EventArgs e)
{
string membershipUsername = null;
string membershipPassword = null;
this.authorizeStatus = false;
// 세션 변수 중 membershipUsername이라는 데이터가 있는지 확인
if (Session["membershipUsername"] != null)
{
// membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
if (Session["membershipPassword"] != null)
{
// 세션 변수에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
membershipUsername = Session["membershipUsername"].ToString();
membershipPassword = Session["membershipPassword"].ToString();
// membershipUsername과 membershipPassword가 모두 수신되면,
// 앞서 정의된 authorizeMembership 메서드로 로그인 요청한다.
this.authorizeStatus = authorizeMembership
(
membershipUsername,
membershipPassword
);
}
}
// 로그인 요청이 승인되었다면
if (this.authorizeStatus)
{
// membershipUsername이라 이름붙인 세션 변수에
// 사용자 이름을 기록한다.
Session["membershipUsername"] = membershipUsername;
// membershipPassword이라 이름붙인 세션 변수에
// 사용자 암호를 기록한다.
Session["membershipPassword"] = membershipPassword;
// 세션의 유효기간은 12시간으로 한다.
Session.Timeout = 12 * 60;
}
return;
}
</script>
</head>
<%--------------------------------------------------------------------------
웹 페이지 본문 영역
------------------------------------------------------------------------%>
<body>
<header>
<h1>3 단계 : 회원 페이지</h1>
</header>
<hr />
<section>
<% if (authorizeStatus) { %>
<%-- 로그인 승인 되었다면... --%>
<p>회원 전용 페이지</p>
<p>환영합니다. <%=Session["membershipUsername"].ToString()%> 님.</p>
<p>쿠키 문자열 :</p>
<pre><code><%=Request.ServerVariables["HTTP_COOKIE"]%></code></pre>
<p><a href="./step4.aspx">로그아웃</a></p>
<% } else { %>
<%-- 로그인 거부 되었다면... --%>
<p>이 페이지를 보려면 로그인이 필요합니다.</p>
<p><a href="./step1.aspx">로그인</a></p>
<% } %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.aspx">1 단계(로그인)</a> | </span>
<span><a href="./step2.aspx">2 단계(사용자 인증)</a> | </span>
<span><strong>3 단계(회원 페이지)</strong> | </span>
<span><a href="./step4.aspx">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
step4.aspx - 로그아웃 화면
로그인 상태임이 확인되면 서버의 세션을 삭제하고 클라이언트의 쿠키를 만료시켜서 로그아웃 작업을 수행한다. 그렇지 않은 경우 이미 로그아웃 상태임을 알려준다.
<%@ Page Language="C#" CodePage="65001" %>
<%
Response.Charset="UTF-8";
Response.ContentType="text/html;charset=UTF-8";
Session.CodePage=65001;
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>4 단계 : 로그아웃</title>
<style>a { color: #0000FF; }</style>
<%--------------------------------------------------------------------
사용자 인증 로직
이름과 암호를 비교하며 승인되면 true, 승인 안 되면 false를 반환한다.
--------------------------------------------------------------------%>
<script language="C#" runat="server">
// 아래 이름의 사용자면 로그인 승인 함.
private const string authorizedUsername = "codingCat";
// 아래의 암호를 입력하면 로그인 승인 함.
private const string authorizedPassword = "qwerty123456!";
// 로그인 승인 시 True, 아니면 False
private bool authorizeStatus = false;
// authorizeMembership(trialUsername, trialPassword)
// 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
// trialUsername : 로그인을 시도하는 사용자 이름
// trialPassword : 로그인을 시도하는 사용자가 입력한 암호
// 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
private static bool authorizeMembership(string trialUsername, string trialPassword)
{
// 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
if (string.Equals(trialUsername, authorizedUsername))
{
// 이름이 일치하면, 암호가 같은지 검사
if (string.Equals(trialPassword, authorizedPassword))
{
// 이름과 암호가 모두 일치하면 로그인 승인
return true;
}
}
// 그렇지 않을 경우 로그인 거부
return false;
}
</script>
<%--------------------------------------------------------------------
웹 페이지 헤더 영역
클라이언트의 쿠키로부터 전송된 사용자 이름 및 암호를 읽어온다.
--------------------------------------------------------------------%>
<script language="C#" runat="server">
private void Page_Load(object sender, EventArgs e)
{
string membershipUsername = null;
string membershipPassword = null;
this.authorizeStatus = false;
// 세션 변수 중 membershipUsername이라는 데이터가 있는지 확인
if (Session["membershipUsername"] != null)
{
// membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
if (Session["membershipPassword"] != null)
{
// 세션 변수에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
membershipUsername = Session["membershipUsername"].ToString();
membershipPassword = Session["membershipPassword"].ToString();
// membershipUsername과 membershipPassword가 모두 수신되면,
// 앞서 정의된 authorizeMembership 메서드로 로그인 요청한다.
this.authorizeStatus = authorizeMembership
(
membershipUsername,
membershipPassword
);
}
}
// 로그아웃은 로그인 여부와 무관하게 시행된다.
// 클라이언트의 쿠키 유효기간을 현재 시점으로부터 12시간 이전으로 설정한다.
// membershipUsername이라 이름붙인 세션 변수에
// 사용자 이름을 기록한다.
Session["membershipUsername"] = "<undefined>";
// membershipPassword이라 이름붙인 세션 변수에
// 사용자 암호를 기록한다.
Session["membershipPassword"] = "<undefined>";
// 세션을 삭제한다.
Session.Abandon();
return;
}
</script>
</head>
<%--------------------------------------------------------------------------
웹 페이지 본문 영역
------------------------------------------------------------------------%>
<body>
<header>
<h1>4 단계 : 로그아웃</h1>
</header>
<hr />
<section>
<% if (authorizeStatus) { %>
<%-- 로그인 승인 되었다면... --%>
<p>로그아웃되었습니다.</p>
<p><a href="./step1.aspx">로그인</a></p>
<% } else { %>
<%-- 로그인 거부 되었다면... --%>
<p>로그인되어있지 않습니다.</p>
<p><a href="./step1.aspx">로그인</a></p>
<% } %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.aspx">1 단계(로그인)</a> | </span>
<span><a href="./step2.aspx">2 단계(사용자 인증)</a> | </span>
<span><a href="./step3.aspx">3 단계(회원 페이지)</a> | </span>
<span><strong>4 단계(로그아웃)</strong></span>
</p>
</footer>
</body>
</html>
step1.aspx - 중복 로그인을 방지하기 위한 소스 코드의 수정
앞서 작성한 step3.aspx을 살펴보면, 세션으로부터 사용자 이름과 암호를 읽은 후 로그인 유효성을 재검증하는 부분이 있다. 로그인이 재차 승인되면 쿠키의 유효기간이 연장되면서 회원 전용 페이지를 보여주고 그렇지 않으면 로그인 화면으로 안내하는 메시지를 보여주는데 이를 step1.aspx에 적용해본다. 중복 로그인을 방지하기 위해 쿠키를 읽어들이고 이미 로그인이 유효한 상태라면 곧바로 회원 페이지로 넘어갈 수 있도록 안내하는 기능이 추가된다.
<%@ Page Language="C#" CodePage="65001" %>
<%
Response.Charset="UTF-8";
Response.ContentType="text/html;charset=UTF-8";
Session.CodePage=65001;
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>1 단계 : 로그인</title>
<%--------------------------------------------------------------------
사용자 인증 로직
이름과 암호를 비교하며 승인되면 true, 승인 안 되면 false를 반환한다.
--------------------------------------------------------------------%>
<script language="C#" runat="server">
// 아래 이름의 사용자면 로그인 승인 함.
private const string authorizedUsername = "codingCat";
// 아래의 암호를 입력하면 로그인 승인 함.
private const string authorizedPassword = "qwerty123456!";
// 로그인 승인 시 true, 아니면 false
private bool authorizeStatus = false;
// authorizeMembership(trialUsername, trialPassword)
// 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
// trialUsername : 로그인을 시도하는 사용자 이름
// trialPassword : 로그인을 시도하는 사용자가 입력한 암호
// 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
private static bool authorizeMembership(string trialUsername, string trialPassword)
{
// 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
if (string.Equals(trialUsername, authorizedUsername))
{
// 이름이 일치하면, 암호가 같은지 검사
if (string.Equals(trialPassword, authorizedPassword))
{
// 이름과 암호가 모두 일치하면 로그인 승인
return true;
}
}
// 그렇지 않을 경우 로그인 거부
return false;
}
</script>
<%--------------------------------------------------------------------
웹 페이지 헤더 영역
이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다.
--------------------------------------------------------------------%>
<script language="C#" runat="server">
private void Page_Load(object sender, EventArgs e)
{
string membershipUsername = null;
string membershipPassword = null;
this.authorizeStatus = false;
// 세션 변수 중 membershipUsername이라는 데이터가 있는지 확인
if (Session["membershipUsername"] != null)
{
// membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
if (Session["membershipPassword"] != null)
{
// 세션 변수에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
membershipUsername = Session["membershipUsername"].ToString();
membershipPassword = Session["membershipPassword"].ToString();
// membershipUsername과 membershipPassword가 모두 수신되면,
// 앞서 정의된 authorizeMembership 메서드로 로그인 요청한다.
this.authorizeStatus = authorizeMembership
(
membershipUsername,
membershipPassword
);
}
}
// 로그인 요청이 승인되었다면
if (this.authorizeStatus)
{
// membershipUsername이라 이름붙인 세션 변수에
// 사용자 이름을 기록한다.
Session["membershipUsername"] = membershipUsername;
// membershipPassword이라 이름붙인 세션 변수에
// 사용자 암호를 기록한다.
Session["membershipPassword"] = membershipPassword;
// 세션의 유효기간은 12시간으로 설정한다.
Session.Timeout = 12 * 60;
}
return;
}
</script>
</head>
<%--------------------------------------------------------------------------
웹 페이지 본문 영역
------------------------------------------------------------------------%>
<body>
<header>
<h1>1 단계 : 로그인</h1>
</header>
<hr />
<section>
<% if (authorizeStatus) { %>
<%-- 로그인 승인 되었다면... --%>
<p>이미 로그인되어 있습니다.</p>
<p><a href="step3.aspx">회원 페이지</a></p>
<% } else { %>
<%-- 로그인 거부 되었다면... --%>
<p>사용자 이름과 사용자 암호를 입력하세요.</p>
<form action="./step2.aspx" method="post">
<label for="trialUsername">사용자 이름 : </label><input type="text" id="trialUsername" name="trialUsername" />
<label for="trialPassword">사용자 암호 : </label><input type="password" id="trialPassword" name="trialPassword" />
<input type="submit" />
</form>
<% } %>
</section>
<hr />
<footer>
<p>
<span><strong>1 단계(로그인)</strong> | </span>
<span><a href="./step2.aspx">2 단계(사용자 인증)</a> | </span>
<span><a href="./step3.aspx">3 단계(회원 페이지)</a> | </span>
<span><a href="./step4.aspx">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
본 시리즈에서는 웹 개발을 할 때 자주 사용되는 기능인 로그인/로그아웃 기능에 대한 예제를 정리한다. 아이디와 암호가 일치할 경우 이 상태를 쿠키cookie나 세션session에 기억시키고, 이후 페이지 접속 시 해당 쿠키 또는 세션의 보유 여부에 따라 로그인한 이용자와 로그인하지 않은 이용자를 구분하고 서로 다른 페이지를 보여주도록 하는 것이 본 시리즈에서 구현하는 주된 기능이다.
본 게시물에서는 ASP.NET 소스 코드로 세션에 의한 로그인/로그아웃 기능을 구현한다. 로그인 화면에서 아이디와 암호를 맞게 입력했다면 서버에 로그인 정보를 보관하고 이 정보에 접근할 수 있는 식별 번호를 클라이언트의 쿠키로 전송한다. 이후 클라이언트는 페이지를 접속할 때마다 쿠키를 통해 세션 번호를 서버에 전달하고, 서버는 해당 번호의 세션이 보유한 유효성 여부를 판별하여 회원 페이지를 보여줄 것인지, 비회원 페이지를 보여줄 것인지를 결정하게 된다.
step1.aspx - 로그인 화면
이 페이지를 통해 사용자로부터 아이디와 암호를 입력받는다. 아이디가 전달될 매개변수 이름은 trialUsername이라 하고 암호가 전달될 매개변수 이름은 trialPassword라 이름 붙인다. 예제 소스 코드의 구조를 단순하게 하기 위하여 아이디와 암호에 대한 보안 조치 등은 생략한 채 쿠키와 POST 데이터를 통해 직접 사용자 이름과 암호가 전달될 것이다.
위 소스 코드에서는 사용자 이름과 암호를 입력받는 폼form을 출력한다. name 속성이 각각 trialUsername과 trialPassword인 input을 통해 사용자 이름과 암호를 입력받은 뒤 POST 방식으로 다음 파일인 step2.aspx로 전달할 것이다.
step2.aspx - 사용자 인증
이 페이지는 step1.aspx에서 전달된 아이디(trialUsername)/암호(trialPassword)가 미리 준비된 아이디(authorizedUsername)/암호(authorizedPassword)와 일치하는지 여부를 검사할 것이다. 일치하면 membershipUsername와 membershipPassword라는 세션 변수에 각각 아이디와 암호를 보관하고, 해당 세션의 식별번호를 쿠키를 통해 클라이언트로 전송할 것이다. 일치하지 않으면 별도의 오류 메시지를 보여줄 것이다.
<%@ Page Language="C#" CodePage="65001" %>
<% Response.Charset="utf-8"; %>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>2 단계 : 사용자 인증</title>
<style>a { color: #0000FF; }</style>
<%-- 사용자 인증 로직 : 이름과 암호를 비교하며 승인되면 nonzero, 승인 안 되면 zero를 반환한다. --%>
<script language="C#" runat="server">
// 아래 이름의 사용자면 로그인 승인 함.
private const string authorizedUsername = "codingCat";
// 아래의 암호를 입력하면 로그인 승인 함.
private const string authorizedPassword = "qwerty123456!";
// 로그인 승인 시 True, 아니면 False
private bool authorizeStatus = false;
// authorizeMembership(trialUsername, trialPassword)
// 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
// trialUsername : 로그인을 시도하는 사용자 이름
// trialPassword : 로그인을 시도하는 사용자가 입력한 암호
// 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
private static bool authorizeMembership(string trialUsername, string trialPassword)
{
// 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
if (string.Equals(trialUsername, authorizedUsername))
{
// 이름이 일치하면, 암호가 같은지 검사
if (string.Equals(trialPassword, authorizedPassword))
{
// 이름과 암호가 모두 일치하면 로그인 승인
return true;
}
}
// 그렇지 않을 경우 로그인 거부
return false;
}
</script>
<%-- 웹 페이지 헤더 영역 : 이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다. --%>
<script language="C#" runat="server">
private void Page_Load(object sender, EventArgs e)
{
string trialUsername = null;
string trialPassword = null;
HttpCookie objectUsername = null;
HttpCookie objectPassword = null;
this.authorizeStatus = false;
// POST 방식으로 넘어온 데이터 중 membershipUsername이라는 데이터가 있는지 확인
if (Request.Form["trialUsername"] != null)
{
trialUsername = Request.Form["trialUsername"];
// membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
if (Request.Form["trialPassword"] != null)
{
trialPassword = Request.Form["trialPassword"];
// trialUsername과 trialPassword가 모두 수신되면,
// 위에서 선언한 authorizeMembership 서브루틴을 호출하여 로그인 요청한다
this.authorizeStatus = authorizeMembership(trialUsername, trialPassword);
}
}
// 로그인 요청이 승인되었다면
if (this.authorizeStatus)
{
// membershipUsername이라 이름붙인 유효기간 12시간짜리 쿠키변수에
// 사용자 이름을 적어 클라이언트로 전송한다.
objectUsername = new HttpCookie("membershipUsername");
objectUsername.Value = trialUsername;
objectUsername.Expires = DateTime.Now.AddHours(12.0);
// membershipPassword이라 이름붙인 유효기간 12시간짜리 쿠키변수에
// 사용자 암호를 적어 클라이언트로 전송한다.
objectPassword = new HttpCookie("membershipPassword");
objectPassword.Value = trialPassword;
objectPassword.Expires = DateTime.Now.AddHours(12.0);
// 쿠키는 HTTP 헤더 부분에 명시되어야 하므로 웹 페이지의 본문에 앞서 이를 출력함
Response.Cookies.Add(objectUsername);
Response.Cookies.Add(objectPassword);
}
return;
}
</script>
</head>
<%-- 웹 페이지 본문 영역 --%>
<body>
<header>
<h1>2 단계 : 사용자 인증</h1>
</header>
<hr />
<section>
<% if (authorizeStatus) { %>
<!-- 로그인 승인 되었다면... -->
<p>로그인에 성공했습니다.</p>
<p><a href="./step3.aspx">회원 페이지</a></p>
<% } else { %>
<!-- 로그인 거부 되었다면... -->
<p>로그인에 실패했습니다.</p>
<p><a href="./step1.aspx">로그인 화면</a></p>
<% } %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.aspx">1 단계(로그인)</a> | </span>
<span><strong>2 단계(사용자 인증)</strong> | </span>
<span><a href="./step3.aspx">3 단계(회원 페이지)</a> | </span>
<span><a href="./step4.aspx">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
ASP.NET의 경우 세션 정보들은 객체의 형태로 메모리에 보관된다.
step3.aspx - 회원 전용 페이지
클라이언트 측으로부터 쿠키에 보관된 아이디와 암호를 전달받는다. 로그인 상태임이 확인되면 회원 전용 페이지를 출력하고, 그렇지 않다면 비회원용 페이지를 출력한다.
<%@ Page Language="C#" CodePage="65001" %>
<% Response.Charset="utf-8"; %>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>2 단계 : 사용자 인증</title>
<style>a { color: #0000FF; }</style>
<%-- 사용자 인증 로직 : 이름과 암호를 비교하며 승인되면 nonzero, 승인 안 되면 zero를 반환한다. --%>
<script language="C#" runat="server">
// 아래 이름의 사용자면 로그인 승인 함.
private const string authorizedUsername = "codingCat";
// 아래의 암호를 입력하면 로그인 승인 함.
private const string authorizedPassword = "qwerty123456!";
// 로그인 승인 시 True, 아니면 False
private bool authorizeStatus = false;
// authorizeMembership(trialUsername, trialPassword)
// 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
// trialUsername : 로그인을 시도하는 사용자 이름
// trialPassword : 로그인을 시도하는 사용자가 입력한 암호
// 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
private static bool authorizeMembership(string trialUsername, string trialPassword)
{
// 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
if (string.Equals(trialUsername, authorizedUsername))
{
// 이름이 일치하면, 암호가 같은지 검사
if (string.Equals(trialPassword, authorizedPassword))
{
// 이름과 암호가 모두 일치하면 로그인 승인
return true;
}
}
// 그렇지 않을 경우 로그인 거부
return false;
}
</script>
<%-- 웹 페이지 헤더 영역 : 이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다. --%>
<script language="C#" runat="server">
private void Page_Load(object sender, EventArgs e)
{
string membershipUsername = null;
string membershipPassword = null;
HttpCookie objectUsername = null;
HttpCookie objectPassword = null;
this.authorizeStatus = false;
// POST 방식으로 넘어온 데이터 중 membershipUsername이라는 데이터가 있는지 확인
if (Request.Cookies["membershipUsername"] != null)
{
membershipUsername = Request.Cookies["membershipUsername"].Value;
// membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
if (Request.Cookies["membershipPassword"] != null)
{
membershipPassword = Request.Cookies["membershipPassword"].Value;
// trialUsername과 trialPassword가 모두 수신되면,
// 위에서 선언한 authorizeMembership 서브루틴을 호출하여 로그인 요청한다
this.authorizeStatus = authorizeMembership(membershipUsername, membershipPassword);
}
}
// 로그인 요청이 승인되었다면
if (this.authorizeStatus)
{
// membershipUsername이라 이름붙인 유효기간 12시간짜리 쿠키변수에
// 사용자 이름을 적어 클라이언트로 전송한다.
objectUsername = new HttpCookie("membershipUsername");
objectUsername.Value = membershipUsername;
objectUsername.Expires = DateTime.Now.AddHours(12.0);
// membershipPassword이라 이름붙인 유효기간 12시간짜리 쿠키변수에
// 사용자 암호를 적어 클라이언트로 전송한다.
objectPassword = new HttpCookie("membershipPassword");
objectPassword.Value = membershipPassword;
objectPassword.Expires = DateTime.Now.AddHours(12.0);
// 쿠키는 HTTP 헤더 부분에 명시되어야 하므로 웹 페이지의 본문에 앞서 이를 출력함
Response.Cookies.Add(objectUsername);
Response.Cookies.Add(objectPassword);
}
return;
}
</script>
</head>
<%-- 웹 페이지 본문 영역 --%>
<body>
<header>
<h1>3 단계 : 회원 페이지</h1>
</header>
<hr />
<section>
<% if (authorizeStatus) { %>
<!-- 로그인 승인 되었다면... -->
<p>회원 전용 페이지</p>
<p>환영합니다. <%=Request.Cookies["membershipUsername"].Value%> 님.</p>
<p>쿠키 문자열 :</p>
<pre><code><%=Request.ServerVariables["HTTP_COOKIE"]%></code></pre>
<p><a href="./step4.aspx">로그아웃</a></p>
<% } else { %>
<!-- 로그인 거부 되었다면... -->
<p>이 페이지를 보려면 로그인이 필요합니다.</p>
<p><a href="./step1.aspx">로그인</a></p>
<% } %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.aspx">1 단계(로그인)</a> | </span>
<span><a href="./step2.aspx">2 단계(사용자 인증)</a> | </span>
<span><strong>3 단계(회원 페이지)</strong> | </span>
<span><a href="./step4.aspx">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
step4.aspx - 로그아웃 화면
로그인 상태임이 확인되면 서버의 세션을 삭제하고 클라이언트의 쿠키를 만료시켜서 로그아웃 작업을 수행한다. 그렇지 않은 경우 이미 로그아웃 상태임을 알려준다.
<%@ Page Language="C#" CodePage="65001" %>
<% Response.Charset="utf-8"; %>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>2 단계 : 사용자 인증</title>
<style>a { color: #0000FF; }</style>
<%-- 사용자 인증 로직 : 이름과 암호를 비교하며 승인되면 nonzero, 승인 안 되면 zero를 반환한다. --%>
<script language="C#" runat="server">
// 아래 이름의 사용자면 로그인 승인 함.
private const string authorizedUsername = "codingCat";
// 아래의 암호를 입력하면 로그인 승인 함.
private const string authorizedPassword = "qwerty123456!";
// 로그인 승인 시 True, 아니면 False
private bool authorizeStatus = false;
// authorizeMembership(trialUsername, trialPassword)
// 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
// trialUsername : 로그인을 시도하는 사용자 이름
// trialPassword : 로그인을 시도하는 사용자가 입력한 암호
// 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
private static bool authorizeMembership(string trialUsername, string trialPassword)
{
// 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
if (string.Equals(trialUsername, authorizedUsername))
{
// 이름이 일치하면, 암호가 같은지 검사
if (string.Equals(trialPassword, authorizedPassword))
{
// 이름과 암호가 모두 일치하면 로그인 승인
return true;
}
}
// 그렇지 않을 경우 로그인 거부
return false;
}
</script>
<%-- 웹 페이지 헤더 영역 : 이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다. --%>
<script language="C#" runat="server">
private void Page_Load(object sender, EventArgs e)
{
string membershipUsername = null;
string membershipPassword = null;
HttpCookie objectUsername = null;
HttpCookie objectPassword = null;
this.authorizeStatus = false;
// POST 방식으로 넘어온 데이터 중 membershipUsername이라는 데이터가 있는지 확인
if (Request.Cookies["membershipUsername"] != null)
{
membershipUsername = Request.Cookies["membershipUsername"].Value;
// membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
if (Request.Cookies["membershipPassword"] != null)
{
membershipPassword = Request.Cookies["membershipPassword"].Value;
// trialUsername과 trialPassword가 모두 수신되면,
// 위에서 선언한 authorizeMembership 서브루틴을 호출하여 로그인 요청한다
this.authorizeStatus = authorizeMembership(membershipUsername, membershipPassword);
}
}
// 쿠키변수의 제거는 로그인 여부와 무관하게 시행된다.
// 클라이언트의 쿠키 유효기간을 현재 시점으로부터 12시간 이전으로 설정한다.
// membershipUsername이라 이름붙인 유효기간 만료된 쿠키변수에
// 사용자 이름을 적어 클라이언트로 전송한다.
objectUsername = new HttpCookie("membershipUsername");
objectUsername.Value = "<undefined>";
objectUsername.Expires = DateTime.Now.AddHours(-12.0);
// membershipPassword이라 이름붙인 유효기간 만료된 쿠키변수에
// 사용자 이름을 적어 클라이언트로 전송한다.
objectPassword = new HttpCookie("membershipPassword");
objectPassword.Value = "<undefined>";
objectPassword.Expires = DateTime.Now.AddHours(-12.0);
Response.Cookies.Add(objectUsername);
Response.Cookies.Add(objectPassword);
return;
}
</script>
</head>
<%-- 웹 페이지 본문 영역 --%>
<body>
<header>
<h1>4 단계 : 로그아웃</h1>
</header>
<hr />
<section>
<% if (authorizeStatus) { %>
<!-- 로그인 된 상태였다면... -->
<p>로그아웃되었습니다.</p>
<p><a href="./step1.aspx">로그인</a></p>
<% } else { %>
<!-- 로그인 안 된 상태였다면... -->
<p>로그인되어있지 않습니다.</p>
<p><a href="./step1.aspx">로그인</a></p>
<% } %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.aspx">1 단계(로그인)</a> | </span>
<span><a href="./step2.aspx">2 단계(사용자 인증)</a> | </span>
<span><a href="./step3.aspx">3 단계(회원 페이지)</a> | </span>
<span><strong>4 단계(로그아웃)</strong></span>
</p>
</footer>
</body>
</html>
step1.aspx - 중복 로그인을 방지하기 위한 소스 코드의 수정
앞서 작성한 step3.aspx을 살펴보면, 세션으로부터 사용자 이름과 암호를 읽은 후 로그인 유효성을 재검증하는 부분이 있다. 로그인이 재차 승인되면 쿠키의 유효기간이 연장되면서 회원 전용 페이지를 보여주고 그렇지 않으면 로그인 화면으로 안내하는 메시지를 보여주는데 이를 step1.aspx에 적용해본다. 중복 로그인을 방지하기 위해 쿠키를 읽어들이고 이미 로그인이 유효한 상태라면 곧바로 회원 페이지로 넘어갈 수 있도록 안내하는 기능이 추가된다.
<%@ Page Language="C#" CodePage="65001" %>
<% Response.Charset="utf-8"; %>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>1 단계 : 로그인</title>
<style>a { color: #0000FF; }</style>
<%-- 사용자 인증 로직 : 이름과 암호를 비교하며 승인되면 nonzero, 승인 안 되면 zero를 반환한다. --%>
<script language="C#" runat="server">
// 아래 이름의 사용자면 로그인 승인 함.
private const string authorizedUsername = "codingCat";
// 아래의 암호를 입력하면 로그인 승인 함.
private const string authorizedPassword = "qwerty123456!";
// 로그인 승인 시 True, 아니면 False
private bool authorizeStatus = false;
// authorizeMembership(trialUsername, trialPassword)
// 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
// trialUsername : 로그인을 시도하는 사용자 이름
// trialPassword : 로그인을 시도하는 사용자가 입력한 암호
// 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
private static bool authorizeMembership(string trialUsername, string trialPassword)
{
// 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
if (string.Equals(trialUsername, authorizedUsername))
{
// 이름이 일치하면, 암호가 같은지 검사
if (string.Equals(trialPassword, authorizedPassword))
{
// 이름과 암호가 모두 일치하면 로그인 승인
return true;
}
}
// 그렇지 않을 경우 로그인 거부
return false;
}
</script>
<%-- 웹 페이지 헤더 영역 : 이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다. --%>
<script language="C#" runat="server">
private void Page_Load(object sender, EventArgs e)
{
string membershipUsername = null;
string membershipPassword = null;
HttpCookie objectUsername = null;
HttpCookie objectPassword = null;
this.authorizeStatus = false;
// POST 방식으로 넘어온 데이터 중 membershipUsername이라는 데이터가 있는지 확인
if (Request.Cookies["membershipUsername"] != null)
{
membershipUsername = Request.Cookies["membershipUsername"].Value;
// membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
if (Request.Cookies["membershipPassword"] != null)
{
membershipPassword = Request.Cookies["membershipPassword"].Value;
// trialUsername과 trialPassword가 모두 수신되면,
// 위에서 선언한 authorizeMembership 서브루틴을 호출하여 로그인 요청한다
this.authorizeStatus = authorizeMembership(membershipUsername, membershipPassword);
}
}
// 로그인 요청이 승인되었다면
if (this.authorizeStatus)
{
// membershipUsername이라 이름붙인 유효기간 12시간짜리 쿠키변수에
// 사용자 이름을 적어 클라이언트로 전송한다.
objectUsername = new HttpCookie("membershipUsername");
objectUsername.Value = membershipUsername;
objectUsername.Expires = DateTime.Now.AddHours(12.0);
// membershipPassword이라 이름붙인 유효기간 12시간짜리 쿠키변수에
// 사용자 암호를 적어 클라이언트로 전송한다.
objectPassword = new HttpCookie("membershipPassword");
objectPassword.Value = membershipPassword;
objectPassword.Expires = DateTime.Now.AddHours(12.0);
// 쿠키는 HTTP 헤더 부분에 명시되어야 하므로 웹 페이지의 본문에 앞서 이를 출력함
Response.Cookies.Add(objectUsername);
Response.Cookies.Add(objectPassword);
}
return;
}
</script>
</head>
<%-- 웹 페이지 본문 영역 --%>
<body>
<header>
<h1>1 단계 : 로그인</h1>
</header>
<hr />
<section>
<% if (authorizeStatus) { %>
<p>이미 로그인되어 있습니다.</p>
<p><a href="step3.aspx">회원 페이지</a></p>
<% } else { %>
<p>사용자 이름과 사용자 암호를 입력하세요.</p>
<form action="./step2.aspx" method="post">
<label for="trialUsername">사용자 이름 : </label><input type="text" id="trialUsername" name="trialUsername" />
<label for="trialPassword">사용자 암호 : </label><input type="password" id="trialPassword" name="trialPassword" />
<input type="submit" />
</form>
<% } %>
</section>
<hr />
<footer>
<p>
<span><strong>1 단계(로그인)</strong> | </span>
<span><a href="./step2.aspx">2 단계(사용자 인증)</a> | </span>
<span><a href="./step3.aspx">3 단계(회원 페이지)</a> | </span>
<span><a href="./step4.aspx">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
본 시리즈에서는 웹 개발을 할 때 자주 사용되는 기능인 로그인/로그아웃 기능에 대한 예제를 정리한다. 아이디와 암호가 일치할 경우 이 상태를 쿠키cookie나 세션session에 기억시키고, 이후 페이지 접속 시 해당 쿠키 또는 세션의 보유 여부에 따라 로그인한 이용자와 로그인하지 않은 이용자를 구분하고 서로 다른 페이지를 보여주도록 하는 것이 본 시리즈에서 구현하는 주된 기능이다.
본 게시물에서는 ASP 소스 코드로 세션에 의한 로그인/로그아웃 기능을 구현한다. 로그인 화면에서 아이디와 암호를 맞게 입력했다면 서버에 로그인 정보를 보관하고 이 정보에 접근할 수 있는 식별 번호를 클라이언트의 쿠키로 전송한다. 이후 클라이언트는 페이지를 접속할 때마다 쿠키를 통해 세션 번호를 서버에 전달하고, 서버는 해당 번호의 세션이 보유한 유효성 여부를 판별하여 회원 페이지를 보여줄 것인지, 비회원 페이지를 보여줄 것인지를 결정하게 된다.
step1.asp - 로그인 화면
이 페이지를 통해 사용자로부터 아이디와 암호를 입력받는다. 아이디가 전달될 매개변수 이름은 trialUsername이라 하고 암호가 전달될 매개변수 이름은 trialPassword라 이름 붙인다. 예제 소스 코드의 구조를 단순하게 하기 위하여 아이디와 암호에 대한 보안 조치 등은 생략한 채 쿠키와 POST 데이터를 통해 직접 사용자 이름과 암호가 전달될 것이다.
위 소스 코드에서는 사용자 이름과 암호를 입력받는 폼form을 출력한다. name 속성이 각각 trialUsername과 trialPassword인 input을 통해 사용자 이름과 암호를 입력받은 뒤 POST 방식으로 다음 파일인 step2.asp로 전달할 것이다.
step2.asp - 사용자 인증
이 페이지는 step1.asp에서 전달된 아이디(trialUsername)/암호(trialPassword)가 미리 준비된 아이디(authorizedUsername)/암호(authorizedPassword)와 일치하는지 여부를 검사할 것이다. 일치하면 membershipUsername와 membershipPassword라는 세션 변수에 각각 아이디와 암호를 보관하고, 해당 세션의 식별번호를 쿠키를 통해 클라이언트로 전송할 것이다. 일치하지 않으면 별도의 오류 메시지를 보여줄 것이다.
<%@ Language="VBScript" CodePage="65001" %>
<%
Response.CharSet="UTF-8"
Response.CodePage="65001"
Response.ContentType="text/html;charset=UTF-8"
Session.CodePage="65001"
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 사용자 인증 로직
' 이름과 암호를 비교하며 승인되면 True, 승인 안 되면 False를 반환한다.
' 아래 이름의 사용자면 로그인 승인 함.
Const authorizedUsername = "codingCat"
' 아래의 암호를 입력하면 로그인 승인 함.
Const authorizedPassword = "qwerty123456!"
' 로그인 승인 시 True, 아니면 False
Dim authorizeStatus
authorizeStatus = False
' authorizeMembership(trialUsername, trialPassword)
' 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
' trialUsername : 로그인을 시도하는 사용자 이름
' trialPassword : 로그인을 시도하는 사용자가 입력한 암호
' 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
Function authorizeMembership(trialUsername, trialPassword)
' 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
If StrComp(trialUsername, authorizedUsername) = 0 Then
' 이름이 일치하면, 암호가 같은지 검사
If StrComp(trialPassword, authorizedPassword) = 0 Then
' 이름과 암호가 모두 일치하면 로그인 승인
authorizeMembership = True
Exit Function
End If
End If
' 그렇지 않을 경우 로그인 거부
authorizeMembership = False
End Function
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 웹 페이지 헤더 영역
' 이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다.
Dim trialUsername
Dim trialPassword
authorizeStatus = False
' POST 방식으로 전달된 데이터 중 trialUsername이라는 데이터가 있는지 확인
If Not IsNull(Request.Form("trialUsername")) Then
trialUsername = Request.Form("trialUsername")
' trialUsername이 존재하면, trialPassword라는 데이터도 있는지 확인
If Not IsNull(Request.Form("trialPassword")) Then
trialPassword = Request.Form("trialPassword")
' trialUsername과 trialPassword가 모두 수신되면,
' 앞서 정의된 authorizeMembership 함수로 로그인 요청한다.
authorizeStatus = authorizeMembership(trialUsername, trialPassword)
End If
End If
' 로그인 요청이 승인되었다면
If authorizeStatus = True Then
' membershipUsername이라 이름붙인 세션 변수에
' 사용자 이름을 기록한다.
Session("membershipUsername") = trialUsername
' membershipPassword이라 이름붙인 세션 변수에
' 사용자 암호를 기록한다.
Session("membershipPassword") = trialPassword
' 세션의 유효기간을 12시간으로 설정한다. [단위: 분]
Session.Timeout = 12 * 60
End If
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 웹 페이지 본문 영역
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>2 단계 : 사용자 인증</title>
<style>a { color: #0000FF; }</style>
</head>
<body>
<header>
<h1>2 단계 : 사용자 인증</h1>
</header>
<hr />
<section>
<% If authorizeStatus = True Then %>
<% '로그인 승인 되었다면...' %>
<p>로그인에 성공했습니다.</p>
<p><a href="./step3.asp">회원 페이지</a></p>
<% Else %>
<% '로그인 거부 되었다면...' %>
<p>로그인에 실패했습니다.</p>
<p><a href="./step1.asp">로그인 화면</a></p>
<% End If %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.asp">1 단계(로그인)</a> | </span>
<span><strong>2 단계(사용자 인증)</strong> | </span>
<span><a href="./step3.asp">3 단계(회원 페이지)</a> | </span>
<span><a href="./step4.asp">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
ASP의 경우 세션 정보들은 객체의 형태로 메모리에 보관된다.
step3.asp - 회원 전용 페이지
클라이언트 측으로부터 쿠키에 보관된 세션 식별 번호를 전달받는다. 서버의 특정 위치에서 해당 번호를 갖는 세션을 읽어온 후, 로그인 상태임이 확인되면 회원 전용 페이지를 출력한다. 그렇지 않다면 비회원용 페이지를 출력한다.
<%@ Language="VBScript" CodePage="65001" %>
<%
Response.CharSet="UTF-8"
Response.CodePage="65001"
Response.ContentType="text/html;charset=UTF-8"
Session.CodePage="65001"
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 사용자 인증 로직
' 이름과 암호를 비교하며 승인되면 True, 승인 안 되면 False를 반환한다.
' 아래 이름의 사용자면 로그인 승인 함.
Const authorizedUsername = "codingCat"
' 아래의 암호를 입력하면 로그인 승인 함.
Const authorizedPassword = "qwerty123456!"
' 로그인 승인 시 True, 아니면 False
Dim authorizeStatus
authorizeStatus = False
' authorizeMembership(trialUsername, trialPassword)
' 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
' trialUsername : 로그인을 시도하는 사용자 이름
' trialPassword : 로그인을 시도하는 사용자가 입력한 암호
' 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
Function authorizeMembership(trialUsername, trialPassword)
' 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
If StrComp(trialUsername, authorizedUsername) = 0 Then
' 이름이 일치하면, 암호가 같은지 검사
If StrComp(trialPassword, authorizedPassword) = 0 Then
' 이름과 암호가 모두 일치하면 로그인 승인
authorizeMembership = True
Exit Function
End If
End If
' 그렇지 않을 경우 로그인 거부
authorizeMembership = False
End Function
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 웹 페이지 헤더 영역
' 이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다.
Dim membershipUsername
Dim membershipPassword
authorizeStatus = False
' 세션 변수 중 membershipUsername이라는 데이터가 있는지 확인
If Not IsNull(Session("membershipUsername")) Then
' membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
If Not IsNull(Session("membershipPassword")) Then
' 세션 변수에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
membershipUsername = Session("membershipUsername")
membershipPassword = Session("membershipPassword")
' trialUsername과 trialPassword가 모두 수신되면,
' 위에서 선언한 authorizeMembership 서브루틴을 호출하여 로그인 요청한다
authorizeStatus = authorizeMembership(membershipUsername, membershipPassword)
End If
End If
' 로그인 요청이 승인되었다면
If authorizeStatus = True Then
' membershipUsername이라 이름붙인 세션 변수에
' 사용자 이름을 기록한다.
Session("membershipUsername") = membershipUsername
' membershipPassword이라 이름붙인 세션 변수에
'' 사용자 암호를 기록한다.
Session("membershipPassword") = membershipPassword
' 세션의 유효기간을 12시간으로 설정한다. [단위: 분]
Session.Timeout = 12 * 60
End If
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 웹 페이지 본문 영역
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>3 단계 : 회원 페이지</title>
</head>
<body>
<header>
<h1>3 단계 : 회원 페이지</h1>
</header>
<hr />
<section>
<% If authorizeStatus = True Then %>
<% '로그인 승인 되었다면...' %>
<p>회원 전용 페이지</p>
<p>환영합니다. <%=membershipUsername%> 님.</p>
<p>쿠키 문자열 :</p>
<pre><code><%=Request.ServerVariables("HTTP_COOKIE")%></code></pre>
<p><a href="./step4.asp">로그아웃</a></p>
<% Else %>
<% '로그인 거부 되었다면...' %>
<p>이 페이지를 보려면 로그인이 필요합니다.</p>
<p><a href="./step1.asp">로그인</a></p>
<% End If %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.asp">1 단계(로그인)</a> | </span>
<span><a href="./step2.asp">2 단계(사용자 인증)</a> | </span>
<span><strong>3 단계(회원 페이지)</strong> | </span>
<span><a href="./step4.asp">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
step4.asp - 로그아웃 화면
로그인 상태임이 확인되면 서버의 세션을 삭제하고 클라이언트의 쿠키를 만료시켜서 로그아웃 작업을 수행한다. 그렇지 않은 경우 이미 로그아웃 상태임을 알려준다.
<%@ Language="VBScript" CodePage="65001" %>
<%
Response.CharSet="UTF-8"
Response.CodePage="65001"
Response.ContentType="text/html;charset=UTF-8"
Session.CodePage="65001"
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 사용자 인증 로직
' 이름과 암호를 비교하며 승인되면 True, 승인 안 되면 False를 반환한다.
' 아래 이름의 사용자면 로그인 승인 함.
Const authorizedUsername = "codingCat"
' 아래의 암호를 입력하면 로그인 승인 함.
Const authorizedPassword = "qwerty123456!"
' 로그인 승인 시 True, 아니면 False
Dim authorizeStatus
authorizeStatus = False
' authorizeMembership(trialUsername, trialPassword)
' 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
' trialUsername : 로그인을 시도하는 사용자 이름
' trialPassword : 로그인을 시도하는 사용자가 입력한 암호
' 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
Function authorizeMembership(trialUsername, trialPassword)
' 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
If StrComp(trialUsername, authorizedUsername) = 0 Then
' 이름이 일치하면, 암호가 같은지 검사
If StrComp(trialPassword, authorizedPassword) = 0 Then
' 이름과 암호가 모두 일치하면 로그인 승인
authorizeMembership = True
Exit Function
End If
End If
' 그렇지 않을 경우 로그인 거부
authorizeMembership = False
End Function
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 웹 페이지 헤더 영역
' 세션에 저장된 사용자 이름 및 암호를 읽어온다.
Dim membershipUsername
Dim membershipPassword
authorizeStatus = False
' 세션 변수 중 membershipUsername이라는 데이터가 있는지 확인
If Not IsNull(Session("membershipUsername")) Then
' membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
If Not IsNull(Session("membershipPassword")) Then
' 세션 변수에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
membershipUsername = Session("membershipUsername")
membershipPassword = Session("membershipPassword")
' membershipUsername과 membershipPassword가 모두 수신되면,
' 앞서 정의된 authorizeMembership 메서드로 로그인 요청한다.
authorizeStatus = authorizeMembership(membershipUsername, membershipPassword)
End If
End If
' 로그아웃은 로그인 여부와 무관하게 수행된다.
' membershipUsername이라 이름붙인 세션 변수에
' 사용자 이름을 기록한다.
Session("membershipUsername") = "<undefined>"
' membershipPassword이라 이름붙인 세션 변수에
' 사용자 암호를 기록한다.
Session("membershipPassword") = "<undefined>"
' 서버에서 세션을 제거한다.
Session.Abandon()
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 웹 페이지 본문 영역
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>4 단계 : 로그아웃</title>
<style>a { color: #0000FF; }</style>
</head>
<body>
<header>
<h1>4 단계 : 로그아웃</h1>
</header>
<hr />
<section>
<% If authorizeStatus = True Then %>
<% '로그인 된 상태였다면...' %>
<p>로그아웃되었습니다.</p>
<p><a href="./step1.asp">로그인</a></p>
<% Else %>
<% '로그인 안 된 상태였다면...' %>
<p>로그인되어있지 않습니다.</p>
<p><a href="./step1.asp">로그인</a></p>
<% End If %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.asp">1 단계(로그인)</a> | </span>
<span><a href="./step2.asp">2 단계(사용자 인증)</a> | </span>
<span><a href="./step3.asp">3 단계(회원 페이지)</a> | </span>
<span><strong>4 단계(로그아웃)</strong></span>
</p>
</footer>
</body>
</html>
step1.asp - 중복 로그인을 방지하기 위한 소스 코드의 수정
앞서 작성한 step3.asp을 살펴보면, 세션으로부터 사용자 이름과 암호를 읽은 후 로그인 유효성을 재검증하는 부분이 있다. 로그인이 재차 승인되면 쿠키의 유효기간이 연장되면서 회원 전용 페이지를 보여주고 그렇지 않으면 로그인 화면으로 안내하는 메시지를 보여주는데 이를 step1.asp에 적용해본다. 중복 로그인을 방지하기 위해 쿠키를 읽어들이고 이미 로그인이 유효한 상태라면 곧바로 회원 페이지로 넘어갈 수 있도록 안내하는 기능이 추가된다.
<%@ Language="VBScript" CodePage="65001" %>
<%
Response.CharSet="UTF-8"
Response.CodePage="65001"
Response.ContentType="text/html;charset=UTF-8"
Session.CodePage="65001"
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 사용자 인증 로직
' 이름과 암호를 비교하며 승인되면 True, 승인 안 되면 False를 반환한다.
' 아래 이름의 사용자면 로그인 승인 함.
Const authorizedUsername = "codingCat"
' 아래의 암호를 입력하면 로그인 승인 함.
Const authorizedPassword = "qwerty123456!"
' 로그인 승인 시 True, 아니면 False
Dim authorizeStatus
authorizeStatus = False
' authorizeMembership(trialUsername, trialPassword)
' 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
' trialUsername : 로그인을 시도하는 사용자 이름
' trialPassword : 로그인을 시도하는 사용자가 입력한 암호
' 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
Function authorizeMembership(trialUsername, trialPassword)
' 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
If StrComp(trialUsername, authorizedUsername) = 0 Then
' 이름이 일치하면, 암호가 같은지 검사
If StrComp(trialPassword, authorizedPassword) = 0 Then
' 이름과 암호가 모두 일치하면 로그인 승인
authorizeMembership = True
Exit Function
End If
End If
' 그렇지 않을 경우 로그인 거부
authorizeMembership = False
End Function
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 웹 페이지 헤더 영역
' 이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다.
Dim membershipUsername
Dim membershipPassword
authorizeStatus = False
' 세션 변수 중 membershipUsername이라는 데이터가 있는지 확인
If Not IsNull(Session("membershipUsername")) Then
' membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
If Not IsNull(Session("membershipPassword")) Then
' 세션 변수에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
membershipUsername = Session("membershipUsername")
membershipPassword = Session("membershipPassword")
' trialUsername과 trialPassword가 모두 수신되면,
' 위에서 선언한 authorizeMembership 서브루틴을 호출하여 로그인 요청한다
authorizeStatus = authorizeMembership(membershipUsername, membershipPassword)
End If
End If
' 로그인 요청이 승인되었다면
If authorizeStatus = True Then
' membershipUsername이라 이름붙인 세션 변수에
' 사용자 이름을 기록한다.
Session("membershipUsername") = membershipUsername
' membershipPassword이라 이름붙인 세션 변수에
' 사용자 암호를 기록한다.
Session("membershipPassword") = membershipPassword
' 세션의 유효기간을 12시간으로 설정한다. [단위: 분]
Session.Timeout = 12 * 60
End If
%>
<%
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' 웹 페이지 본문 영역
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>1 단계 : 로그인</title>
</head>
<body>
<header>
<h1>1 단계 : 로그인</h1>
</header>
<hr />
<section>
<% If authorizeStatus = True Then %>
<% '로그인 승인 되었다면...' %>
<p>이미 로그인되어 있습니다.</p>
<p><a href="step3.asp">회원 페이지</a></p>
<% Else %>
<% '로그인 거부 되었다면...' %>
<p>사용자 이름과 사용자 암호를 입력하세요.</p>
<form action="./step2.asp" method="post">
<label for="trialUsername">사용자 이름 : </label>
<input type="text" id="trialUsername" name="trialUsername" />
<label for="trialPassword">사용자 암호 : </label>
<input type="password" id="trialPassword" name="trialPassword" />
<input type="submit" />
</form>
<% End If %>
</section>
<hr />
<footer>
<p>
<span><strong>1 단계(로그인)</strong> | </span>
<span><a href="./step2.asp">2 단계(사용자 인증)</a> | </span>
<span><a href="./step3.asp">3 단계(회원 페이지)</a> | </span>
<span><a href="./step4.asp">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
본 시리즈에서는 웹 개발을 할 때 자주 사용되는 기능인 로그인/로그아웃 기능에 대한 예제를 정리한다. 아이디와 암호가 일치할 경우 이 상태를 쿠키cookie나 세션session에 기억시키고, 이후 페이지 접속 시 해당 쿠키 또는 세션의 보유 여부에 따라 로그인한 이용자와 로그인하지 않은 이용자를 구분하고 서로 다른 페이지를 보여주도록 하는 것이 본 시리즈에서 구현하는 주된 기능이다.
본 게시물에서는 ASP 소스 코드로 세션에 의한 로그인/로그아웃 기능을 구현한다. 로그인 화면에서 아이디와 암호를 맞게 입력했다면 서버에 로그인 정보를 보관하고 이 정보에 접근할 수 있는 식별 번호를 클라이언트의 쿠키로 전송한다. 이후 클라이언트는 페이지를 접속할 때마다 쿠키를 통해 세션 번호를 서버에 전달하고, 서버는 해당 번호의 세션이 보유한 유효성 여부를 판별하여 회원 페이지를 보여줄 것인지, 비회원 페이지를 보여줄 것인지를 결정하게 된다.
step1.asp - 로그인 화면
이 페이지를 통해 사용자로부터 아이디와 암호를 입력받는다. 아이디가 전달될 매개변수 이름은 trialUsername이라 하고 암호가 전달될 매개변수 이름은 trialPassword라 이름 붙인다. 예제 소스 코드의 구조를 단순하게 하기 위하여 아이디와 암호에 대한 보안 조치 등은 생략한 채 쿠키와 POST 데이터를 통해 직접 사용자 이름과 암호가 전달될 것이다.
위 소스 코드에서는 사용자 이름과 암호를 입력받는 폼form을 출력한다. name 속성이 각각 trialUsername과 trialPassword인 input을 통해 사용자 이름과 암호를 입력받은 뒤 POST 방식으로 다음 파일인 step2.asp로 전달할 것이다.
step2.asp - 사용자 인증
이 페이지는 step1.asp에서 전달된 아이디(trialUsername)/암호(trialPassword)가 미리 준비된 아이디(authorizedUsername)/암호(authorizedPassword)와 일치하는지 여부를 검사할 것이다. 일치하면 membershipUsername와 membershipPassword라는 세션 변수에 각각 아이디와 암호를 보관하고, 해당 세션의 식별번호를 쿠키를 통해 클라이언트로 전송할 것이다. 일치하지 않으면 별도의 오류 메시지를 보여줄 것이다.
<%@ Language="VBScript" CodePage="65001" %>
<%
Response.CharSet="UTF-8"
Response.CodePage="65001"
Response.ContentType="text/html;charset=UTF-8"
%>
<%
'###############################################################################
' 사용자 인증 로직
' 이름과 암호를 비교하며 승인되면 True, 승인 안 되면 False를 반환한다.
' 아래 이름의 사용자면 로그인 승인 함.
Const authorizedUsername = "codingCat"
' 아래의 암호를 입력하면 로그인 승인 함.
Const authorizedPassword = "qwerty123456!"
' 로그인 승인 시 True, 아니면 False
Dim authorizeStatus
authorizeStatus = False
' authorizeMembership(trialUsername, trialPassword)
' 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
' trialUsername : 로그인을 시도하는 사용자 이름
' trialPassword : 로그인을 시도하는 사용자가 입력한 암호
' 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
Function authorizeMembership(trialUsername, trialPassword)
' 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
If StrComp(trialUsername, authorizedUsername) = 0 Then
' 이름이 일치하면, 암호가 같은지 검사
If StrComp(trialPassword, authorizedPassword) = 0 Then
' 이름과 암호가 모두 일치하면 로그인 승인
authorizeMembership = True
Exit Function
End If
End If
' 그렇지 않을 경우 로그인 거부
authorizeMembership = False
End Function
%>
<%
'###############################################################################
' 웹 페이지 헤더 영역 : 이전 페이지에서 POST 방식으로 전송된 사용자 이름 및 암호를 읽어온다.
Dim trialUsername
Dim trialPassword
authorizeStatus = False
' POST 방식으로 넘어온 데이터 중 trialUsername이라는 데이터가 있는지 확인
If Not IsNull(Request.Form("trialUsername")) Then
' trialUsername이 존재하면, trialPassword라는 데이터도 있는지 확인
If Not IsNull(Request.Form("trialPassword")) Then
' POST 데이터에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
trialUsername = Request.Form("trialUsername")
trialPassword = Request.Form("trialPassword")
' trialUsername과 trialPassword가 모두 수신되면,
' 앞서 정의된 authorizeMembership 메서드로 로그인 요청한다.
authorizeStatus = authorizeMembership(trialUsername, trialPassword)
End If
End If
' 로그인 요청이 승인되었다면
If authorizeStatus = True Then
' 쿠키는 HTTP 헤더 부분에 명시되어야 하므로 웹 페이지의 본문에 앞서 이를 출력함
' membershipUsername이라 이름붙인 유효기간 12시간짜리 쿠키변수에
' 사용자 이름을 기록한다.
Response.Cookies("membershipUsername") = trialUsername
Response.Cookies("membershipUsername").Expires = DateAdd("h", 12, Now())
Response.Cookies("membershipUsername").Path = "/"
' membershipPassword이라 이름붙인 유효기간 12시간짜리 쿠키변수에
' 사용자 암호를 기록한다.
Response.Cookies("membershipPassword") = trialPassword
Response.Cookies("membershipPassword").Expires = DateAdd("h", 12, Now())
Response.Cookies("membershipPassword").Path = "/"
End If
%>
<%
'###############################################################################
' 웹 페이지 본문 영역
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>2 단계 : 사용자 인증</title>
<style>a { color: #0000FF; }</style>
</head>
<body>
<header>
<h1>2 단계 : 사용자 인증</h1>
</header>
<hr />
<section>
<% If authorizeStatus = True Then %>
<% '로그인 승인 되었다면... %>
<p>로그인에 성공했습니다.</p>
<p><a href="./step3.asp">회원 페이지</a></p>
<% Else %>
<% '로그인 거부 되었다면... %>
<p>로그인에 실패했습니다.</p>
<p><a href="./step1.asp">로그인 화면</a></p>
<% End If %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.asp">1 단계(로그인)</a> | </span>
<span><strong>2 단계(사용자 인증)</strong> | </span>
<span><a href="./step3.asp">3 단계(회원 페이지)</a> | </span>
<span><a href="./step4.asp">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
ASP의 경우 세션 정보들은 객체의 형태로 메모리에 보관된다.
step3.asp - 회원 전용 페이지
클라이언트 측으로부터 쿠키에 보관된 아이디와 암호를 전달받는다. 로그인 상태임이 확인되면 회원 전용 페이지를 출력하고, 그렇지 않다면 비회원용 페이지를 출력한다.
<%@ Language="VBScript" CodePage="65001" %>
<%
Response.CharSet="UTF-8"
Response.CodePage="65001"
Response.ContentType="text/html;charset=UTF-8"
%>
<%
'###############################################################################
' 사용자 인증 로직
' 이름과 암호를 비교하며 승인되면 True, 승인 안 되면 False를 반환한다.
' 아래 이름의 사용자면 로그인 승인 함.
Const authorizedUsername = "codingCat"
' 아래의 암호를 입력하면 로그인 승인 함.
Const authorizedPassword = "qwerty123456!"
' 로그인 승인 시 True, 아니면 False
Dim authorizeStatus
authorizeStatus = False
' authorizeMembership(trialUsername, trialPassword)
' 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
' trialUsername : 로그인을 시도하는 사용자 이름
' trialPassword : 로그인을 시도하는 사용자가 입력한 암호
' 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
Function authorizeMembership(trialUsername, trialPassword)
' 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
If StrComp(trialUsername, authorizedUsername) = 0 Then
' 이름이 일치하면, 암호가 같은지 검사
If StrComp(trialPassword, authorizedPassword) = 0 Then
' 이름과 암호가 모두 일치하면 로그인 승인
authorizeMembership = True
Exit Function
End If
End If
' 그렇지 않을 경우 로그인 거부
authorizeMembership = False
End Function
%>
<%
'###############################################################################
' 웹 페이지 헤더 영역
' 쿠키에 기록된 사용자 이름 및 암호를 읽어와서 로그인 유효성을 검증한다.
Dim trialUsername
Dim trialPassword
authorizeStatus = False
' 쿠키 변수 중 membershipUsername이라는 데이터가 있는지 확인
If Not IsNull(Request.Cookies("membershipUsername")) Then
' membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
If Not IsNull(Request.Cookies("membershipPassword")) Then
' 쿠키 변수에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
trialUsername = Request.Cookies("membershipUsername")
trialPassword = Request.Cookies("membershipPassword")
' membershipUsername과 membershipPassword가 모두 수신되면,
' 앞서 정의된 authorizeMembership 메서드로 로그인 요청한다.
authorizeStatus = authorizeMembership(trialUsername, trialPassword)
End If
End If
' 로그인 요청이 승인되었다면
If authorizeStatus = True Then
' 클라이언트의 쿠키 유효기간을 현재 시점으로부터 12시간으로 연장한다.
' 쿠키는 HTTP 헤더 부분에 명시되어야 하므로 웹 페이지의 본문에 앞서 이를 출력함
' membershipUsername이라 이름붙인 유효기간 12시간짜리 쿠키변수에
' 사용자 이름을 적어 클라이언트로 전송한다.
Response.Cookies("membershipUsername") = trialUsername
Response.Expires = DateAdd("h", 12, Now())
' membershipPassword이라 이름붙인 유효기간 12시간짜리 쿠키변수에
' 사용자 이름을 적어 클라이언트로 전송한다.
Response.Cookies("membershipPassword") = trialPassword
Response.Expires = DateAdd("h", 12, Now())
End If
%>
<%
'###############################################################################
' 웹 페이지 본문 영역
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>3 단계 : 회원 페이지</title>
<style>a { color: #0000FF; }</style>
</head>
<body>
<header>
<h1>3 단계 : 회원 페이지</h1>
</header>
<hr />
<section>
<% If authorizeStatus = True Then %>
<% '로그인 승인 되었다면... %>
<p>회원 전용 페이지</p>
<p>환영합니다. <%=membershipUsername%> 님.</p>
<p>쿠키 문자열 :</p>
<pre><code><%=Request.ServerVariables("HTTP_COOKIE")%></code></pre>
<p><a href="./step4.asp">로그아웃</a></p>
<% Else %>
<% '로그인 거부 되었다면... %>
<p>이 페이지를 보려면 로그인이 필요합니다.</p>
<p><a href="./step1.asp">로그인</a></p>
<% End If %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.asp">1 단계(로그인)</a> | </span>
<span><a href="./step2.asp">2 단계(사용자 인증)</a> | </span>
<span><strong>3 단계(회원 페이지)</strong> | </span>
<span><a href="./step4.asp">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>
step4.asp - 로그아웃 화면
로그인 상태임이 확인되면 서버의 세션을 삭제하고 클라이언트의 쿠키를 만료시켜서 로그아웃 작업을 수행한다. 그렇지 않은 경우 이미 로그아웃 상태임을 알려준다.
<%@ Language="VBScript" CodePage="65001" %>
<%
Response.CharSet="UTF-8"
Response.CodePage="65001"
Response.ContentType="text/html;charset=UTF-8"
%>
<%
'###############################################################################
' 사용자 인증 로직
' 이름과 암호를 비교하며 승인되면 True, 승인 안 되면 False를 반환한다.
' 아래 이름의 사용자면 로그인 승인 함.
Const authorizedUsername = "codingCat"
' 아래의 암호를 입력하면 로그인 승인 함.
Const authorizedPassword = "qwerty123456!"
' 로그인 승인 시 True, 아니면 False
Dim authorizeStatus
authorizeStatus = False
' authorizeMembership(trialUsername, trialPassword)
' 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
' trialUsername : 로그인을 시도하는 사용자 이름
' trialPassword : 로그인을 시도하는 사용자가 입력한 암호
' 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
Function authorizeMembership(trialUsername, trialPassword)
' 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
If StrComp(trialUsername, authorizedUsername) = 0 Then
' 이름이 일치하면, 암호가 같은지 검사
If StrComp(trialPassword, authorizedPassword) = 0 Then
' 이름과 암호가 모두 일치하면 로그인 승인
authorizeMembership = True
Exit Function
End If
End If
' 그렇지 않을 경우 로그인 거부
authorizeMembership = False
End Function
%>
<%
'###############################################################################
' 웹 페이지 헤더 영역
' 쿠키에 기록된 사용자 이름 및 암호를 읽어와서 로그인 유효성을 검증한다.
Dim membershipUsername
Dim membershipPassword
authorizeStatus = False
' 쿠키 변수 중 membershipUsername이라는 데이터가 있는지 확인
If Not IsNull(Request.Cookies("membershipUsername")) Then
' membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
If Not IsNull(Request.Cookies("membershipPassword")) Then
' 쿠키 변수에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
membershipUsername = Request.Cookies("membershipUsername")
membershipPassword = Request.Cookies("membershipPassword")
' membershipUsername과 membershipPassword가 모두 수신되면,
' 앞서 정의된 authorizeMembership 메서드로 로그인 요청한다.
authorizeStatus = authorizeMembership(membershipUsername, membershipPassword)
End If
End If
' 로그아웃은 로그인 여부와 무관하게 수행된다.
' 클라이언트의 쿠키 유효기간을 현재 시점으로부터 12시간 이전으로 설정한다.
' 쿠키는 HTTP 헤더 부분에 명시되어야 하므로 웹 페이지의 본문에 앞서 이를 출력함
' membershipUsername이라 이름붙인 유효기간 만료된 쿠키변수에
' 사용자 이름을 적어 클라이언트로 전송한다.
Response.Cookies("membershipUsername") = "<undefined>"
Response.Cookies("membershipUsername").Expires = DateAdd("h", -12, Now())
Response.Cookies("membershipUsername").Path = "/"
' membershipPassword이라 이름붙인 유효기간 12시간짜리 쿠키변수에
' 사용자 이름을 적어 클라이언트로 전송한다.
Response.Cookies("membershipPassword") = "<undefined>"
Response.Cookies("membershipPassword").Expires = DateAdd("h", -12, Now())
Response.Cookies("membershipPassword").Path = "/"
%>
<%
'###############################################################################
' 웹 페이지 본문 영역
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>4 단계 : 로그아웃</title>
<style>a { color: #0000FF; }</style>
</head>
<body>
<header>
<h1>4 단계 : 로그아웃</h1>
</header>
<hr />
<section>
<% If authorizeStatus = True Then %>
<% '로그인 된 상태였다면... %>
<p>로그아웃되었습니다.</p>
<p><a href="./step1.asp">로그인</a></p>
<% Else %>
<% '로그인 안 된 상태였다면... %>
<p>로그인되어있지 않습니다.</p>
<p><a href="./step1.asp">로그인</a></p>
<% End If %>
</section>
<hr />
<footer>
<p>
<span><a href="./step1.asp">1 단계(로그인)</a> | </span>
<span><a href="./step2.asp">2 단계(사용자 인증)</a> | </span>
<span><a href="./step3.asp">3 단계(회원 페이지)</a> | </span>
<span><strong>4 단계(로그아웃)</strong></span>
</p>
</footer>
</body>
</html>
step1.asp - 중복 로그인을 방지하기 위한 소스 코드의 수정
앞서 작성한 step3.asp을 살펴보면, 세션으로부터 사용자 이름과 암호를 읽은 후 로그인 유효성을 재검증하는 부분이 있다. 로그인이 재차 승인되면 쿠키의 유효기간이 연장되면서 회원 전용 페이지를 보여주고 그렇지 않으면 로그인 화면으로 안내하는 메시지를 보여주는데 이를 step1.asp에 적용해본다. 중복 로그인을 방지하기 위해 쿠키를 읽어들이고 이미 로그인이 유효한 상태라면 곧바로 회원 페이지로 넘어갈 수 있도록 안내하는 기능이 추가된다.
<%@ Language="VBScript" CodePage="65001" %>
<%
Response.CharSet="UTF-8"
Response.CodePage="65001"
Response.ContentType="text/html;charset=UTF-8"
%>
<%
'###############################################################################
' 사용자 인증 로직
' 이름과 암호를 비교하며 승인되면 True, 승인 안 되면 False를 반환한다.
' 아래 이름의 사용자면 로그인 승인 함.
Const authorizedUsername = "codingCat"
' 아래의 암호를 입력하면 로그인 승인 함.
Const authorizedPassword = "qwerty123456!"
' 로그인 승인 시 True, 아니면 False
Dim authorizeStatus
authorizeStatus = False
' authorizeMembership(trialUsername, trialPassword)
' 사용자 이름과 암호를 비교하여 로그인 승인 여부를 결정하는 서브루틴.
' trialUsername : 로그인을 시도하는 사용자 이름
' trialPassword : 로그인을 시도하는 사용자가 입력한 암호
' 로그인 승인하면 nonzero를 반환하고 승인 거부 시 zero를 반환한다.
Function authorizeMembership(trialUsername, trialPassword)
' 로그인 요청하는 사용자 이름이 미리 지정된 이름과 같은지 검사
If StrComp(trialUsername, authorizedUsername) = 0 Then
' 이름이 일치하면, 암호가 같은지 검사
If StrComp(trialPassword, authorizedPassword) = 0 Then
' 이름과 암호가 모두 일치하면 로그인 승인
authorizeMembership = True
Exit Function
End If
End If
' 그렇지 않을 경우 로그인 거부
authorizeMembership = False
End Function
%>
<%
'###############################################################################
' 웹 페이지 헤더 영역
' 쿠키에 기록된 사용자 이름 및 암호를 읽어와서 로그인 유효성을 검증한다.
Dim trialUsername
Dim trialPassword
authorizeStatus = False
' 쿠키 변수 중 membershipUsername이라는 데이터가 있는지 확인
If Not IsNull(Request.Cookies("membershipUsername")) Then
' membershipUsername이 존재하면, membershipPassword라는 데이터도 있는지 확인
If Not IsNull(Request.Cookies("membershipPassword")) Then
' 쿠키 변수에서 얻은 사용자 이름과 암호로 로그인 상태가 유효한지 검증
trialUsername = Request.Cookies("membershipUsername")
trialPassword = Request.Cookies("membershipPassword")
' membershipUsername과 membershipPassword가 모두 수신되면,
' 앞서 정의된 authorizeMembership 메서드로 로그인 요청한다.
authorizeStatus = authorizeMembership(trialUsername, trialPassword)
End If
End If
' 로그인 요청이 승인되었다면
If authorizeStatus = True Then
' 클라이언트의 쿠키 유효기간을 현재 시점으로부터 12시간으로 연장한다.
' 쿠키는 HTTP 헤더 부분에 명시되어야 하므로 웹 페이지의 본문에 앞서 이를 출력함
' membershipUsername이라 이름붙인 유효기간 12시간짜리 쿠키변수에
' 사용자 이름을 적어 클라이언트로 전송한다.
Response.Cookies("membershipUsername") = trialUsername
Response.Expires = DateAdd("h", 12, Now())
' membershipPassword이라 이름붙인 유효기간 12시간짜리 쿠키변수에
' 사용자 이름을 적어 클라이언트로 전송한다.
Response.Cookies("membershipPassword") = trialPassword
Response.Expires = DateAdd("h", 12, Now())
End If
%>
<%
'###############################################################################
' 웹 페이지 본문 영역
%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<title>1 단계 : 로그인</title>
<style>a { color: #0000FF; }</style>
</head>
<body>
<header>
<h1>1 단계 : 로그인</h1>
</header>
<hr />
<section>
<% If authorizeStatus = True Then %>
<% '로그인 승인 되었다면... %>
<p>이미 로그인되어 있습니다.</p>
<p><a href="step3.asp">회원 페이지</a></p>
<% Else %>
<% '로그인 거부 되었다면... %>
<p>사용자 이름과 사용자 암호를 입력하세요.</p>
<form action="./step2.asp" method="post">
<label for="trialUsername">사용자 이름 : </label><input type="text" id="trialUsername" name="trialUsername" />
<label for="trialPassword">사용자 암호 : </label><input type="password" id="trialPassword" name="trialPassword" />
<input type="submit" />
</form>
<% End If %>
</section>
<hr />
<footer>
<p>
<span><strong>1 단계(로그인)</strong> | </span>
<span><a href="./step2.asp">2 단계(사용자 인증)</a> | </span>
<span><a href="./step3.asp">3 단계(회원 페이지)</a> | </span>
<span><a href="./step4.asp">4 단계(로그아웃)</a></span>
</p>
</footer>
</body>
</html>