BotDetect ASP.NET 2.0 CAPTCHA Validation C# Code Sample
The CAPTCHA validation sample contains the basic code required to add a CAPTCHA control to an ASP.NET 2.0 page and validate the user input. It can be used as a starting point when you are first learning how to use BotDetect CAPTCHA, and is equivalent to the result you will get if you are following the How To use BotDetect ASP.NET CAPTCHA in Visual Studio 2005 instructions.
Sample Project Location
By default, this sample project is installed at
C:\Program Files\Lanapsoft\BotDetect\ASP.NET 2.0\v2.0\Samples\CSharpBotDetect2Demo\.
You can also run it from the Start Menu:
Programs > Lanapsoft > BotDetect > ASP.NET 2.0 > v2.0 > Samples > C# BotDetect Demo Preview.
Default.aspx
Full Source Code Listing
<%@ Page Language="C#" AutoEventWireup="true"
CodeFile="Default.aspx.cs" Inherits="_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>
Explanation
Lines required to add the BotDetect CAPTCHA control to the ASP.NET form are bolded. To use the <BotDetect:Captcha> control, we must first register the Lanap.BotDetect.dll assembly using the <%@Register %> directive.
The form also contains an <asp:TextBox> for the user input, an <asp:Button> to submit the page, and a pair of <asp:Label> controls which are used to show the CAPTCHA validation result.
The rest of the file is either generated by Visual Studio 2005 by default, or just defines the layout and visual presentation of the page.
Default.aspx.cs
Full Source Code Listing
using System;
using System.Data;
using System.Configuration;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;
public partial class _Default : System.Web.UI.Page
{
protected void Page_PreRender(object sender, EventArgs e)
{
/// initial page setup
if (!IsPostBack)
{
/// 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;
}
CodeTextBox.Attributes.Add("onkeyup",
"this.value = this.value.toLowerCase();");
if (IsPostBack)
{
/// validate the input code, and show the
/// appropriate message
string code = CodeTextBox.Text.Trim().ToUpper();
if (SampleCaptcha.Validate(code))
{
MessageCorrectLabel.Visible = true;
MessageIncorrectLabel.Visible = false;
}
else
{
MessageCorrectLabel.Visible = false;
MessageIncorrectLabel.Visible = true;
}
/// clear previous user code input
CodeTextBox.Text = null;
}
}
}
Explanation
Form processing is done in the Page_PreRender event handler, so all individual control events are executed before the CAPTCHA validation. If you want to validate the CAPTCHA before individual control events, you can move the code to the Page_Load event handler.
Also, the processing is not done in the ValidateButton_Click handler on purpose, in case there are multiple controls which can submit the page – we want to validate the CAPTCHA regardless of what caused the page to submit. Not to mention that most bots will not submit the page by clicking the button, but by simply constructing the POST request data, which might or might not include the "control which caused the postback" part, responsible for triggering the button click event. Checking the CAPTCHA on each page load ensures proper CAPTCHA security in all cases.
On the first page load ( if (!IsPostBack) ), the button and label controls are initialized, and the CAPTCHA validation is skipped, because the user didn't have a chance to solve it yet.
On each page load, we add a small JavaScript fragment to the textbox onkeyup client-side event handler, so the user input is immediately lowercased during typing. This serves to communicate the fact that the CAPTCHA code is not case-sensitive to the user.
When the page is submitted ( if (IsPostBack) ), we forward the user input to the Captcha.Validate() method. In this simplified sample, we use the validation result just to display a message, and always show a new CAPTCHA. In most use cases, you will show a new CAPTCHA only if the user didn't solve the previous one correctly, and execute the protected code fragment (user registration, comment recording, etc.) if the CAPTCHA was solved correctly.
If you redirect the user to a different page upon successful CAPTCHA completion, and you want to protect such pages as well, it might be a good idea to set a Session variable (for example, Session["IsHuman"] = true;), and check it on subsequent pages. Otherwise, some bots could be written to skip the CAPTCHA-protected page and go to those later pages directly, bypassing some of the protection.
Finally, since a new CAPTCHA image is shown on each page load and each CAPTCHA code can only be validated once (regardless of the validation result), the user input should always be cleared after the CAPTCHA validation.
Web.config
Full Source Code Listing
<?xml version="1.0"?>
<!--
Note: As an alternative to hand editing this file you can use the
web admin tool to configure settings for your application. Use
the Website->Asp.Net Configuration option in Visual Studio.
A full list of settings and comments can be found in
machine.config.comments usually located in
\Windows\Microsoft.Net\Framework\v2.x\Config
-->
<configuration>
<connectionStrings/>
<system.web>
<httpHandlers>
<add verb="*" path="LanapCaptcha.aspx"
type="Lanap.BotDetect.CaptchaHandler, Lanap.BotDetect"/>
</httpHandlers>
<sessionState mode="InProc" cookieless="AutoDetect" timeout="20"
sessionIDManagerType="Lanap.BotDetect.Persistence.
CustomSessionIDManager, Lanap.BotDetect" />
<!--
Set compilation debug="true" to insert debugging
symbols into the compiled page. Because this
affects performance, set this value to true only
during development.
-->
<compilation debug="false">
<assemblies>
<add assembly="System.Design, Version=2.0.0.0,
Culture=neutral, PublicKeyToken=B03F5F7F11D50A3A"/>
</assemblies>
</compilation>
<!--
The <authentication> section enables configuration
of the security authentication mode used by
ASP.NET to identify an incoming user.
-->
<authentication mode="None"/>
<!--
The <customErrors> section enables configuration
of what to do if/when an unhandled error occurs
during the execution of a request. Specifically,
it enables developers to configure html error pages
to be displayed in place of a error stack trace.
<customErrors mode="RemoteOnly"
defaultRedirect="GenericErrorPage.htm">
<error statusCode="403" redirect="NoAccess.htm" />
<error statusCode="404" redirect="FileNotFound.htm" />
</customErrors>
-->
</system.web>
<system.webServer>
<validation validateIntegratedModeConfiguration="false" />
<handlers>
<remove name="LanapCaptchaHandler" />
<add name="LanapCaptchaHandler" preCondition="integratedMode"
verb="*" path="LanapCaptcha.aspx"
type="Lanap.BotDetect.CaptchaHandler, Lanap.BotDetect" />
</handlers>
</system.webServer>
</configuration>
Explanation
Lines neccesary for BotDetect CAPTCHA to function properly have been bolded, other lines are all standard values generated by Visual Studio 2005 by default.
The <httpHandlers> element registers the path used for CAPTCHA image and sound requests for processing by Lanap.BotDetect.dll code. The <system.webServer> element serves the same purpose, but is used only by IIS 7.0 machines configured to integrate the ASP.NET pipeline in the IIS process.
The validateIntegratedModeConfiguration="false" declaration ensures that the web.config file can be processed by by older versions of IIS (5.1, 6.0) as well as the 7.0 version. Since the HttpHandler registration syntax differs between IIS versions and ASP.NET integration modes, having both elements makes the web.config file compatible with all supported IIS versions.
The <sessionState> element declares the persistence mechanism used by BotDetect to keep the CAPTCHA codes and settings for each user. Different Session State modes, providers and timeouts can be used, but the sessionIDManagerType element is required to fix a bug caused by Windows Media Player 11 when requesting audio CAPTCHAs (as explained in this FAQ item). Also, special care should be taken if you are running multiple load-balanced servers, as explained in this FAQ item.
The cookieless element value is set to allow CAPTCHAs to be solved even by users who have cookies disables in their browser. However, note that for such users all Urls in the application will be rewritten to contain the session identifier, making them dynamic. This can cause problems with various crawlers, which don't support cookies as a rule.
One common side-effect of this setting is that Google and other Search Engines might keep multiple copies of the CAPTCHA-protected page in their index (since they are always redirected to a different Url). If you want the CAPTCHA-protected page to be indexed by Search Engines, you should use the cookieless="false" setting, or find a way to use cookieless Sessions for human users, but not for crawlers (via the User Agent string, the App_Browsers .browser files, etc.)


