Mã nguồn ví dụ mẫu BotDetect ASP.NET 1.1 CAPTCHA - VB.NET
Ví dụ mẫu sinh ngẫu nhiên BotDetect ASP.NET CAPTCHA cho bạn thấy việc sinh ngẫu nhiên các tham số của Captcha dễ dàng như thế nào, việc này làm tăng đáng kể tính bảo mật của CAPTCHA và đây là cách tốt nhất để tận dụng hết 50 giải thuật khác nhau của BotDetect.
Vị trí dự án mẫu
Mặc định, dự án mẫu này được cài đặt tại
C:\Program Files\Lanapsoft\BotDetect\ASP.NET 1.1\v2.0\Samples\VBNetBotDetect2RandomDemo\.
Bạn cũng có thể chạy nó từ Start Menu:
Programs > Lanapsoft > BotDetect > ASP.NET 1.1 > v2.0 > Samples > VB.NET BotDetect CAPTCHA Randomization Sample.
Default.aspx
Mã nguồn đầy đủ
<%@ Page Language="vb" AutoEventWireup="false"
Codebehind="Default.aspx.vb" Inherits="VBNetBotDetectDemo._Default"
%>
<%@ Register Assembly="Lanap.BotDetect" Namespace="Lanap.BotDetect"
TagPrefix="BotDetect" %>
<html xmlns="http://www.w3.org/1999/xhtml">
<head id="Head1" runat="server">
<title>BotDetect Demo</title>
<link type='text/css' rel='Stylesheet' href="StyleSheet.css" />
</head>
<body>
<form id="form1" runat="server">
<fieldset id="Preview">
<legend>
<span id="PreviewLegend">CAPTCHA Preview</span>
</legend>
<div id="PromptDiv">
<span id="Prompt">Type the characters you see in
the picture</span>
</div>
<div id="CaptchaDiv">
<BotDetect:Captcha ID="SampleCaptcha" runat="server" />
</div>
<div id="ValidationDiv">
<asp:TextBox ID="CodeTextBox" runat="server">
</asp:TextBox>
<asp:Button ID="ValidateButton" runat="server" />
<asp:Label ID="MessageCorrectLabel" runat="server">
</asp:Label>
<asp:Label ID="MessageIncorrectLabel" runat="server">
</asp:Label>
</div>
</fieldset>
<div id="Note">
<span>NOTE: the Trial version will use "LANAP" instead of a
random code in 50% of renderings.</span>
</div>
</form>
</body>
</html>
Giải thích
Những dòng cần thiết để thêm BotDetect CAPTCHA vào trang ASP.NET được tô đậm. Để sử dụng <BotDetect:Captcha>, trước hết chúng ta phải đăng ký Lanap.BotDetect.dll sử dụng <%@Register %>.
Trang web còn chứa <asp:TextBox> để người dùng nhập câu trả lời, một <asp:Button> để gửi câu trả lời, và một cặp <asp:Label> dùng để hiển thị kết quả xác thực. Phần còn lại của file được sinh ra bởi Visual Studio 2003, hoặc dùng để định nghĩa cách thức sắp xếp và hiển thị của trang.
Không có sự khác biệt nào giữa file .aspx của ví dụ này với file cơ bản, vì tất cả việc sinh ngẫu nhiên đều được thực hiện ở mã xử lý trang.
Default.aspx.vb
Mã nguồn đầy đủ
Public Class _Default
Inherits System.Web.UI.Page
#Region " Web Form Designer Generated Code "
'This call is required by the Web Form Designer.
<System.Diagnostics.DebuggerStepThrough()> Private Sub _
InitializeComponent()
End Sub
Protected WithEvents MessageCorrectLabel As _
System.Web.UI.WebControls.Label
Protected WithEvents MessageIncorrectLabel As _
System.Web.UI.WebControls.Label
Protected WithEvents SampleCaptcha As _
Lanap.BotDetect.Captcha
Protected WithEvents CodeTextBox As _
System.Web.UI.WebControls.TextBox
Protected WithEvents ValidateButton As _
System.Web.UI.WebControls.Button
'NOTE: The following placeholder declaration is required by
'the Web Form Designer. Do not delete or move it.
Private designerPlaceholderDeclaration As System.Object
Private Sub Page_Init(ByVal sender As System.Object, _
ByVal e As System.EventArgs) Handles MyBase.Init
'CODEGEN: This method call is required by the Web Form
'Designer. Do not modify it using the code editor.
InitializeComponent()
End Sub
#End Region
Protected Sub Page_Load(ByVal sender As System.Object,
ByVal e As System.EventArgs) Handles MyBase.Init
'register CAPTCHA-specific event handler
AddHandler SampleCaptcha.PreDrawCaptchaImage,
AddressOf SampleCaptcha_PreDrawCaptchaImage
End Sub
Protected Sub Page_PreRender(ByVal sender As System.Object, _
ByVal e As System.EventArgs) Handles MyBase.PreRender
' initial page setup
If (Not IsPostBack) Then
'set control text
ValidateButton.Text = "Validate"
MessageCorrectLabel.Text = "Correct!"
MessageIncorrectLabel.Text = "Incorrect!"
'these messages are shown only after validation
MessageCorrectLabel.Visible = False
MessageIncorrectLabel.Visible = False
End If
' clear user input on Reload button clicks
Dim scriptTemplate As String
scriptTemplate = "<script type='text/javascript'>" & _
"function LBD_ClearUserInput() {{" & _
" var LBD_textBox = document.getElementById('{0}');" & _
" if(LBD_textBox) {{" & _
" LBD_textBox.value = '';" & _
" }}" & _
"}}" & _
"LBD_RegisterHandler('PreReloadCaptchaImage', _
LBD_ClearUserInput);</script>"
Dim script As String
script = String.Format(scriptTemplate, CodeTextBox.ClientID)
If (Not Page.ClientScript.IsStartupScriptRegistered( _
"CaptchaReloadClearInput")) Then
Page.ClientScript.RegisterStartupScript(Me.GetType(), _
"CaptchaReloadClearInput", script, True)
End If
' automatically lowercase user input
CodeTextBox.Attributes.Add("onkeyup", _
"this.value = this.value.toLowerCase();")
If (IsPostBack) Then
'validate the input code, and show the
'appropriate message
Dim code As String = CodeTextBox.Text.Trim().ToUpper()
If (SampleCaptcha.Validate(code)) Then
MessageCorrectLabel.Visible = True
MessageIncorrectLabel.Visible = False
Else
MessageCorrectLabel.Visible = False
MessageIncorrectLabel.Visible = True
End If
'clear previous user code input
CodeTextBox.Text = ""
End If
End Sub
' all CAPTCHA randomization should be performed in this event
' handler instead of Page_Load or Page_PreRender, because this
' event is also fired for direct CAPTCHA image requests (which
' skip the page events since the page is never loaded), for
' example when clicking the Reload CAPTCHA button repeatedly
Protected Sub SampleCaptcha_PreDrawCaptchaImage( _
ByVal sender As System.Object, ByVal e As System.EventArgs)
Dim captcha As ICaptcha = sender
If (captcha.CaptchaId <> SampleCaptcha.CaptchaId) Then
Return
End If
' randomize code generation properties
captcha.CodeType = RandomizationHelper.GetRandomCodeType()
captcha.CodeLength = _
RandomizationHelper.GetRandomCodeLength(4, 6)
' randomize text style
Dim styles As TextStyleEnum() = { _
TextStyleEnum.Lego, TextStyleEnum.MeltingHeat, _
TextStyleEnum.Ghostly, TextStyleEnum.FingerPrints, _
TextStyleEnum.Graffiti2, TextStyleEnum.Bullets2, _
TextStyleEnum.CaughtInTheNet2, TextStyleEnum.Collage, _
TextStyleEnum.Chalkboard
}
captcha.TextStyle = _
RandomizationHelper.GetRandomTextStyle(styles)
End Sub
End Class
Giải thích
Trong quá trình Page_Init của trang ASP.NET, chúng ta đăng ký một phương thức xử lý sự kiện đặc biệt được thực thi trước mỗi lần hiển thị hình ảnh CAPTCHA, trong phương thức này chúng ta thực hiện việc sinh ngẫu nhiên. Vì các hình ảnh CAPTCHA được sinh ra và gửi tới máy khách trong một yêu cầu Http tách biệt khỏi yêu cầu tải trang ASP.NET (khi mã này được thực thi), chúng ta thêm phương thức xử lý sự kiện để đảm bảo các tham số của CAPTCHA được sinh ngẫu nhiên mỗi khi nó được vẽ, và không chỉ một lần khi trang được tải.
Điều này là quan trọng vì số lần yêu cầu hình ảnh CAPTCHA không nhất thiết phải bằng số lần tải trang - dễ thấy nhất là khi sử dụng nút Reload CAPTCHA, và khi bots truy cập trực tiếp vào hình ảnh CAPTCHA, hình ảnh CAPTCHA có thể được sinh ra chỉ sau một lần tải của trang (và thực thi hàm Page_PreRender tương ứng).
Trong phương thức Captcha_PreDrawCaptchaImage, đối tượng Captcha được truyền qua tham số sender. Để việc sinh ngẫu nhiên được thực hiện dễ dàng, chúng ta sử dụng lớp RandomizationHelper, cho phép chúng ta lấy giá trị ngẫu nhiên của một tham số cho trước từ một tập hợp các giá trị cho trước (ví dụ như CAPTCHA CodeType), hoặc một khoảng các giá trị (ví dụ như CAPTCHA CodeLength), hay từ một tập các giá trị (như CAPTCHA TextStyle).
Bạn cũng có thể sinh ngẫu nhiên các thông số khác của CAPTCHA với cách tương tự, nhưng giải thuật vẽ CAPTCHA và chiều dài ký tự CAPTCHA sẽ tăng tính bảo mật của CAPTCHA nhiều nhất khi chúng được sinh ngẫu nhiên. Mỗi giải thuật CAPTCHA riêng rẽ có thể bị bẻ gãy (nếu dành đủ công sức), nhưng nếu bot còn phải phân biệt từng giải thuật trong từng ảnh, nhiệm vụ sẽ khó khăn hơn gấp bội. Hơn nữa, nhiều giải thuật CAPTCHA phổ biến đã bị bẻ gãy vì nó dùng chiều dài ký tự cố định – "tìm 5 ký tự trong hình này" thì dễ hơn rất nhiều so với "tìm một số ký tự chưa biết trong hình này".
RandomizationHelper.vb
Mã nguồn đầy đủ
Imports Microsoft.VisualBasic
Imports System.Drawing
Imports Lanap.BotDetect
Public NotInheritable Class RandomizationHelper
Private Sub New()
'constructor omitted, static methods only
End Sub
' a single global generator is used for all random numbers
Private Shared ReadOnly _rand As Random = New Random()
Public Const DefaultCodeType As CodeTypeEnum = _
CodeTypeEnum.AlphaNumeric
Public Shared Function GetRandomCodeType( _
ByVal ParamArray usedValues As CodeTypeEnum()) As CodeTypeEnum
Dim codeType As CodeTypeEnum = DefaultCodeType
If (0 = usedValues.Length) Then
Dim max As Integer =
System.Enum.GetValues(GetType(CodeTypeEnum)).Length
codeType = CType(_rand.Next(max), CodeTypeEnum)
ElseIf (1 = usedValues.Length) Then
codeType = usedValues(0)
Else
Dim max As Integer = usedValues.Length
Dim index As Integer = _rand.Next(max)
codeType = usedValues(index)
End If
Return codeType
End Function
Public Const DefaultCodeLength As Integer = 5
Public Const MinCodeLength As Integer = 1
Public Const MaxCodeLength As Integer = 15
Public Shared Function GetRandomCodeLength( _
Optional ByVal min As Integer = 0, Optional ByVal max As _
Integer = 0) Integer
If ((max > MaxCodeLength) OrElse (max < MinCodeLength)) Then
max = MaxCodeLength
End If
If ((min < MinCodeLength) OrElse (min > max)) Then
min = MinCodeLength
End If
Return _rand.Next(min, max + 1)
End Function
Public Shared ReadOnly DefaultImageFormat As ImageFormatEnum = _
ImageFormatEnum.Jpeg
Public Shared Function GetRandomImageFormat( _
ByVal ParamArray usedValues As ImageFormatEnum()) As _
ImageFormatEnum
Dim imageFormat As ImageFormatEnum = DefaultImageFormat
If (0 = usedValues.Length) Then
Dim max As Integer = System.Enum.GetValues( _
GetType(ImageFormatEnum)).Length
imageFormat = CType(_rand.Next(max), ImageFormatEnum)
ElseIf (1 = usedValues.Length) Then
imageFormat = usedValues(0)
Else
Dim max As Integer = usedValues.Length
Dim index As Integer = _rand.Next(max)
imageFormat = usedValues(index)
End If
Return imageFormat
End Function
Public Shared ReadOnly DefaultImageSize As Size = New Size(250, 50)
Public Shared ReadOnly MinImageSize As Size = New Size(50, 40)
Public Shared ReadOnly MaxImageSize As Size = New Size(500, 200)
Public Shared Function GetRandomImageSize() As Size
Return GetRandomImageSize(New Size(0, 0), New Size(0, 0))
End Function
Public Shared Function GetRandomImageSize(ByVal maxSize As Size) _
As Size
Return GetRandomImageSize(New Size(0, 0), maxSize)
End Function
Public Shared Function GetRandomImageSize(ByVal minSize As Size, _
ByVal maxSize As Size) As Size
'determine width
If ((maxSize.Width > MaxImageSize.Width) OrElse _
(maxSize.Width < MinImageSize.Width)) Then
maxSize.Width = MaxImageSize.Width
End If
If ((minSize.Width < MinImageSize.Width) OrElse _
(minSize.Width > maxSize.Width)) Then
minSize.Width = MinImageSize.Width
End If
Dim width As Integer = _
_rand.Next(minSize.Width, maxSize.Width + 1)
'determine height
If ((maxSize.Height > MaxImageSize.Height) OrElse _
(maxSize.Height < MinImageSize.Height)) Then
maxSize.Height = MaxImageSize.Height
End If
If ((minSize.Height < MinImageSize.Height) OrElse _
(minSize.Height > maxSize.Height)) Then
minSize.Height = MinImageSize.Height
End If
Dim height As Integer = _
_rand.Next(minSize.Height, maxSize.Height + 1)
'the result
Return New Size(width, height)
End Function
Public Const DefaultTextStyle As TextStyleEnum = _
TextStyleEnum.Chalkboard
Public Shared Function GetRandomTextStyle( _
ByVal ParamArray usedValues As TextStyleEnum()) As _
TextStyleEnum
Dim textStyle As TextStyleEnum = DefaultTextStyle
If (0 = usedValues.Length) Then
Dim max As Integer = _
System.Enum.GetValues(GetType(TextStyleEnum)).Length
textStyle = CType(_rand.Next(max), TextStyleEnum)
ElseIf (1 = usedValues.Length) Then
textStyle = usedValues(0)
Else
Dim max As Integer = usedValues.Length
Dim index As Integer = _rand.Next(max)
textStyle = usedValues(index)
End If
Return textStyle
End Function
End Class
Giải thích
RandomizationHelper là một lớp tiện ích nhỏ bạn có thể sử dụng trong dự án của bạn để đơn giản hoá việc sinh ngẫu nhiên nhiều tham số khác nhau của CAPTCHA.
Các tham số CAPTCHA lấy các giá trị là số hoặc tập hợp, lớp này cung cấp phương thức trả về giá trị ngẫu nhiên. Mỗi tham số có một giá trị mặc định, và các tham số dạng số có giá trị nhỏ nhất và lớn nhất được định nghĩa trước.
Tất cả các phương thức sinh ngẫu nhiên dùng nhiều tham số khác nhau, thông qua phương thức overloads hoặc từ khoá params.
Phương thức trả về giá trị số (ví dụ, CodeLength) hoạt động như sau:
- Nếu không có tham số nào được truyền, giá trị ngẫu nhiên được chọn giữa giá trị nhỏ nhất và giá trị lớn nhất định nghĩa trước.
- Nếu một giá trị được truyền, giá trị ngẫu nhiên được chọn giữa giá trị nhỏ nhất định nghĩa trước và giá trị truyền vào như là giá trị lớn nhất. Chú ý rằng giá trị truyền vào phải nhỏ hơn giá trị lớn nhất được định nghĩa trước.
- If two values are given as parameters, the random value is selected between the first value as the minimum and the second value as the maximum. Chú ý rằng giá trị nhỏ nhất được truyền vào phải lớn hơn giá trị nhỏ nhất được định nghĩa trước, và giá trị lớn nhất truyền vào phải nhỏ hơn giá trị lớn nhất được định nghĩa trước.
Phương thức trả về giá trị trong tập hợp (ví dụ, CodeType) hoạt động như sau:
- Nếu không có tham số nào được truyền, giá trị ngẫu nhiên được chọn từ các giá trị có thể.
- Nếu một giá trị được truyền, nó được trả về như là kết quả - khi bạn truyền vào một giá trị thì sẽ không có sự ngẫu nhiên hoá nào cả. Và nếu bạn muốn dùng một giá trị thì chỉ việc gán trực tiếp vào tham số.
- Nếu một tập hợp (ví dụ như mảng) các giá trị được truyền, giá trị ngẫu nhiên được chọn trong tập hợp đó.
Dĩ nhiên là bạn có thể sử dụng mã này trực tiếp trong dự án của bạn nhưng đóng gói nó trong lớp RandomizationHelper làm việc đọc mã nguồn dễ dàng hơn và tăng tính tái sử dụng.
Web.config
Mã nguồn đầy đủ
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<system.web>
<httpHandlers>
<add verb="*" path="LanapCaptcha.aspx"
type="Lanap.BotDetect.CaptchaHandler, Lanap.BotDetect"/>
</httpHandlers>
<!-- DYNAMIC DEBUG COMPILATION
Set compilation debug="true" to enable ASPX debugging. Otherwise,
setting this value to false will improve runtime performance of
this application. Set compilation debug="true" to insert debugging
symbols (.pdb information) into the compiled page. Because this
creates a larger file that executes more slowly, you should set
this value to true only when debugging and to false at all other
times. For more information, refer to the documentation about
debugging ASP.NET files.
-->
<compilation
defaultLanguage="vb"
debug="false"
/>
<!-- CUSTOM ERROR MESSAGES
Set customErrors mode="On" or "RemoteOnly" to enable custom error
messages, "Off" to disable.
Add <error> tags for each of the errors you want to handle.
"On" Always display custom (friendly) messages.
"Off" Always display detailed ASP.NET error information.
"RemoteOnly" Display custom (friendly) messages only to users not
running on the local Web server. This setting is recommended for
security purposes, so that you do not display application detail
information to remote clients.
-->
<customErrors
mode="RemoteOnly"
/>
<!-- AUTHENTICATION
This section sets the authentication policies of the application.
Possible modes are "Windows", "Forms", "Passport" and "None".
"None" No authentication is performed.
"Windows" IIS performs authentication (Basic, Digest, or
Integrated Windows) according to its settings for the
application. Anonymous access must be disabled in IIS.
"Forms" You provide a custom form (Web page) for users to
enter their credentials, and then you authenticate them
in your application. A user credential token is stored
in a cookie.
"Passport" Authentication is performed via a centralized
authentication service provided by Microsoft that offers
a single logon and core profile services for member sites.
-->
<authentication mode="Windows" />
<!-- AUTHORIZATION
This section sets the authorization policies of the
application. You can allow or deny access to application
resources by user or role. Wildcards: "*" mean everyone,
"?" means anonymous (unauthenticated) users.
-->
<authorization>
<allow users="*" /> <!-- Allow all users -->
<!--
<allow users="[comma separated list of users]"
roles="[comma separated list of roles]"/>
<deny users="[comma separated list of users]"
roles="[comma separated list of roles]"/>
-->
</authorization>
<!-- APPLICATION-LEVEL TRACE LOGGING
Application-level tracing enables trace log output for
every page within an application.
Set trace enabled="true" to enable application trace
logging. If pageOutput="true", the trace information
will be displayed at the bottom of each page. Otherwise,
you can view the application trace log by browsing the
"trace.axd" page from your web application root.
-->
<trace
enabled="false"
requestLimit="10"
pageOutput="false"
traceMode="SortByTime"
localOnly="true"
/>
<!-- SESSION STATE SETTINGS
By default ASP.NET uses cookies to identify which requests
belong to a particular session. If cookies are not available,
a session can be tracked by adding a session identifier to the
URL. To disable cookies, set sessionState cookieless="true".
-->
<sessionState
mode="InProc"
stateConnectionString="tcpip=127.0.0.1:42424"
sqlConnectionString="data source=127.0.0.1;Trusted_Connection=yes"
cookieless="false"
timeout="20"
/>
<!-- GLOBALIZATION
This section sets the globalization settings of the application.
-->
<globalization
requestEncoding="utf-8"
responseEncoding="utf-8"
/>
</system.web>
</configuration>
Giải thích
Những dòng cần thiết để BotDetect CAPTCHA hoạt động đúng được tô đậm, những dòng khác là giá trị chuẩn được sinh ra bởi Visual Studio 2003. Không có thiết lập đặc biệt nào liên quan đến sinh ngẫu nhiên CAPTCHA trong file web.config.
Thành tố <httpHandlers> đăng ký đường dẫn sử dụng cho hình ảnh và âm thanh CAPTCHA được xử lý bởi Lanap.BotDetect.dll code. Thành tố <system.webServer> được sử dụng với cùng mục đích, nhưng chỉ được sử dụng cho IIS 7.0.
Khai báo validateIntegratedModeConfiguration="false" đảm bảo rằng file web.config có thể được xử lý bởi phiên bản cũ hơn của IIS (5.1, 6.0) cũng như phiên bản 7.0. Vì cú pháp đăng ký HttpHandler khác nhau giữa các phiên bản IIS và chế độ tích hợp ASP.NET, dùng cả hai thành tố trên giúp cho file web.config tương thích với tất cả các phiên bản IIS được hỗ trợ.
Thành tố <sessionState> khai báo cơ chế lưu trữ được sử dụng bởi BotDetect để lưu mã CAPTCHA và thiết lập cho mỗi người dùng. Thuộc tính Session State modes, providers, timeouts và cookieless attribute có thể được sử dụng, nhưng thành tố sessionIDManagerType được sử dụng để sửa lỗi gây bởi Windows Media Player 11 khi yêu cầu âm thanh CAPTCHAs (như được giải thích trong mục hỏi đáp).
Phiên bản hiện tại của BotDetect
- BotDetect ASP.NET CAPTCHA v2.0.152009–11–23
- BotDetect ASP CAPTCHA v2.0.92009–02–12
Xin lưu ý
Trang này là bản dịch tiếng Việt không chính thức của trang gốc tiếng Anh: BotDetect ASP.NET 1.1 CAPTCHA Randomization VB.NET Code Sample và có thể không chính xác, không đầy đủ hoặc không cập nhật.
Cập nhật ngày 2009-11-30. Áp dụng cho BotDetect ASP.NET CAPTCHA v2.0.15 và BotDetect ASP CAPTCHA v2.0.9.





