I am attempting to implement a Captcha on a partial view of a page in my application. I have the captcha being refrenced through web.config as a control. I have used the GenericHandler and Class file from this forum post: http://forums.asp.net/t/1871186.aspx/1
How can I reference the user's input if i am using a simple input tag? Should I use an HtmlHelper instead?
<div class="captcha">
<rhcap:Captcha ID="Captcha1" runat="server"></rhcap:Captcha>
<input type="text" id="UserCaptchaText"><input/>
<%= Html.TextAreaFor(m => m.UserCaptcha) %>
</div>
<%if(Captcha1.Text != /* How can get the users input here?*/ ) {
//display error
}else{
//proceed
}%>
Use NuGet and install Recaptcha for .NET (supports MVC as well)
http://nuget.org/packages/RecaptchaNet/
Documentation is on the site:
http://recaptchanet.codeplex.com/
There are other captchas:
http://captchamvc.codeplex.com/
EDIT:
This project has moved to GitHub
https://github.com/tanveery/recaptcha-net
NuGet Google reCAPTCHA V2 for MVC 4 and 5
NuGet Package
Demo And Document
Web.config File in the appSettings section of your web.config file, add the keys as follows:
<appSettings>
<add name="reCaptchaPublicKey" value="Your site key" />
<add name="reCaptchaPrivateKey" value="Your secret key" />
</appSettings>
Add Recaptcha in your view.
#using reCAPTCHA.MVC
#using (Html.BeginForm())
{
#Html.Recaptcha()
#Html.ValidationMessage("ReCaptcha")
<input type="submit" value="Register" />
}
Verifying the user's response.
[HttpPost]
[CaptchaValidator]
public ActionResult Index(RegisterModel registerModel, bool captchaValid)
{
if (ModelState.IsValid)
{
}
return View(registerModel);
}
EDIT:
You should also add this in your head tag or you might see improper captcha
<script src="https://www.google.com/recaptcha/api.js" async defer></script>
First off, it looks like you are mixing standard ASP.NET and ASP.NET MVC. If you want to do MVC, the standard way to do it is the Html.TextBoxFor() type of stuff, and then you handle the value of that in a controller action method rather than write something inline in the page. So you have something like this:
Page.aspx
<rhcap:Captcha ID="Captcha1" runat="server"></rhcap:Captcha>
<%= Html.TextBoxFor(m => m.UserCaptcha) %>
and then in:
SomeController.cs
[HttpGet]
public ActionResult Page()
{
// generate captcha code here
ControllerContext.HttpContext.Session["Captcha"] = captchaValue;
return View(new PageViewModel());
}
[HttpPost]
public ActionResult Page(PageViewModel model)
{
if (model.UserCaptcha == ControllerContext.HttpContext.Session["Captcha"])
{
// do valid captcha stuff
}
}
To take this to the next level would be to implement it in a FilterAttribute. But this should work for most uses.
I would recommend you to use Google reCAPTCHA, is the best and easy to implement plus it comes with the trust of Google.
Very very effective and easy to implement.
Read this article written by me on implementing Google reCAPTCHA in ASP.NET MVC
Thanks
Related
Im new to asp .net mvc3. I have a requirement that i post a form to a url say "www.abc.com/asa" . I have added a submit button to my application. But every time i click the button, form gets submitted to corresponding controller. How can i post to my required url?
Normally in mvc we follow below convention:
[httpGet] //default not to mention
public ActionResult Index()
{
// Todo code here
}
[httpPost]
public ActionResult Index(FormCollection collection)
{
// Form submit here, all form data available here
}
But in your case you may write following in your view:
#using (Html.BeginForm("ActionName", "Controller", "FormMethod", "HTML Attributes"))
{
// Here Controller: it defines whose actionmethod need to be called when form get submitted.
}
EX:
#using(Html.BeginForm(null, null, FormMethod.Post, new {#action="http://www.abc.com/asa"})
{
}
In this case I would suggest using a standard html <form /> tag with the appropriate url in action parameter.
BeginForm helpers always take action and controller as parameters - you can't use the standard ones.
If you want you can define your own helper too. I would do that if this is a bigger application and you'll be using this multiple times.
<form action="www.abc.com/asa" method="POST">
<legend>
Foo
</legend>
<fieldset>
<p>Fields</p>
</fieldset>
<input type="submit" name"submitForm" value="submitForm" />
</form>
I have an i-Frame on my view that links to an external site. This site takes in some values and some config settings. As part of these config settings is a "CallBackURL". This external website posts to this CallBackUrl.
I specified the CallBackURL to be an action on my control.
View Code
<form id="testForm" method="post" target="testFrame">
<input type="hidden" name="RequestXML" ID="RequestXML" value="<Request><RedirectURL>Account/TokenRequest</RedirectURL></Request>"
</form>
<iframe id="testFrame" name="testFrame" frameborder="0" style="width:1000px;height:500px"></iframe>
Controller Code
[HttpPost]
[ValidateInput(false)]
public ActionResult TokenRequest()
{
if (Request.Form["ResponseXML"] != null)
ViewBag.ResponseXML = Request.Form["ResponseXML"];
return PartialView();
}
inside my controller action I get the following error:"a potentially dangerous request.form value was detected from the client"
I also set this in the webconfig
<httpRuntime requestValidationMode="2.0" />
<pages validateRequest="false"...
What am I doing wrong?
EDIT
I was editing the wrong web.config file. I was adding it to the web.config inside the views folder. Once I changed it to the right place it started working.
The above solution was not working for me in MVC4. What works for me is only to put an attribute above the action. No need to change your web.config or add AllowHtml attribute.
[HttpPost]
[ValidateInput(false)]
public ActionResult TokenRequest(TokenRequestModel model)
{
if (!string.IsNullOrEmpty(model.ResponseXML))
ViewBag.ResponseXML = model.ResponseXML;
// ...
Try using a model instead of just using html control direct. and also use the AllowHtml Attribute.
Model:
public TokenRequestModel
{
[AllowHtml]
public string ResponseXML {get;set;}
}
Action:
[HttpPost]
public ActionResult TokenRequest(TokenRequestModel model)
{
if (!string.IsNullOrEmpty(model.ResponseXML))
ViewBag.ResponseXML = model.ResponseXML;
return PartialView();
}
You can try
[HttpPost]
public ActionResult TokenRequest()
{
if (Request.Unvalidated().Form["ResponseXML"] != null)
ViewBag.ResponseXML = Request.Unvalidated().Form["ResponseXML"];
return PartialView();
}
I think the Unvalidated() will make the error go away without the need to edit webconfig
I tried this and worked for me:
on form submit call a javascript function that saves in an hiddenfield the value encoded using 'encodeURIComponent'.
Then in the same function clear the value of the textbox with the dangerous value. In this way the form will submit just the encoded value.
<input type="submit" value="Save" class="btn btn-danger" onclick="encodeLabel1()" />
<script>
function encodeLabel1() {
var label = $('#txt').val();
$('#hfLabel1Encoded').val(encodeURIComponent(label));
$('#txt').val('');
}
</script>
This is a workaround but it works and the validation is still active.
I'm trying to create a basic application, i created facebook application before but everything has been changed :(
I looked every where to create a basic application, but now i'm getting mad because there isn't any working sample. Because of the changed links, facebook api changes, facebook wiki changes i couldn't find a working copy.
I wonder if anyone can help me to write a basic app that gets permission to write user name to screen in facebook developer toolkit asp.net. I looked computerbeacon.net, codeplex, and some other pages but i couldn't succeed, so please don't give me the links :)
Edit: I' m adding some screenshots and some codes, it will may be help you to find my problem.
Here some screenshots from fb;
This is the core settings,
This is the Facebook integration settings,
Web.config file
<?xml version="1.0"?>
<configuration>
<appSettings>
<add key="FaceBookAPIKey" value="MyapiKey"/>
<add key="FaceBookSecretKey" value="MyapiSecret"/>
</appSettings>
<system.web>
<compilation debug="false" targetFramework="4.0" />
</system.web>
</configuration>
My Default.aspx file;
<%# Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" %>
<%# Register Assembly="Facebook.Web" Namespace="Facebook.Web" TagPrefix="cc1" %>
<cc1:CanvasFBMLLoginControl ID="CanvasFBMLLoginControl1" runat="server" RequireLogin="true" />
Result;
Thanks
I faced the same problems.
please make sure that
please fill canvas url with your webapp correct URL when you create facebook application
I paste here the following running example that update my status in facebook profile
the following code in markeup
<script type="text/javascript" src="http://static.ak.connect.facebook.com/js/api_lib/v0.4/FeatureLoader.js.php"></script>
<form method="post">
<input type="submit" value="Submit Comment" />
<%--<fb:login-button></fb:login-button>
<fb:prompt-permission perms="status_update"> Grant permission for status updates </fb:prompt-permission>
</form>
and the following in form page to send status
/// <summary>
/// To send status to your facebook account
/// </summary>
/// <param name="statusMessage">status message</param>
public bool publishToFaceBook(string statusMessage)
{
//please Change call back url in FB app accoroding to your web site application
Facebook.Rest.Api Api;
Facebook.Session.ConnectSession _connectSession;
_connectSession = new Facebook.Session.ConnectSession(ConfigurationManager.AppSettings["FaceBookAPIKey"], ConfigurationManager.AppSettings["FaceBookSecretKey"]);
bool sucess=false;
if (_connectSession.IsConnected())
{
try
{
Api = new Facebook.Rest.Api(_connectSession);
Facebook.Schema.user u = Api.Users.GetInfo();
Facebook.Schema.user_status _status = new Facebook.Schema.user_status();
Api.Users.SetStatus(statusMessage);
sucess = true;
}
catch (Exception ex)
{
sucess = false;
}
}
return sucess;
}
I hope that help you
Best Regards,
Mohammed Thabet Zaky
I'm trying to develop my first site in ASP.Net using Web Forms.
I have a form with some controls and a TextBox control. While now I use GETrequest. When user submits a form his browser expects to get long URL, something like
http://mysite.com/search.aspx?__VIEWSTATE=%2FwEPDwUJNTE2NjY5jMY4D2QWAgICD2QWAgIDDW8wAh4EVGV4dAUBMWRkZKthQ0zeIP5by49qIHwSuW6nOj8iLTdoCUzpH369xyg8&__EVENTVALIDATION=%2FwEWAwLnrcHhBQLs0bLrBgKM54rGBjGtX5fJOylLy4qRbt6DqPxO%2FnfcMOkHJBRFqZTZdsBD&TextBox1=sfs&Button1=Button
if his input is a word sfs in TextBox1.
So I need to return him response. I would like to show this response on a user-friendly URL like
http://mysite.com/search.aspx?TextBox1=sfs
or
http://mysite.com/sfs
or
http://mysite.com/search/sfs
How can I do that? If I use Response.Redirect, it first returns 302, and only then work on short URL. Server.Transfer doesn't change URL and user sees ugly long URL in browser.
It seems to me that it is possible to solve via RouteCollection.MapPageRoute which appeared in 4.0 Framework but it's unclear to me how I can use it.
Any help is appreciated.
UPDATE. It is not a problem to use POST instead of GET. But in this way URL will always look like http://mysite.com/search.aspx
UPDATE2. The form MUST be server control and it has another controls except submit and textbox. It would be good (though, still, not necessary if this parameters don't appear in URL showing in the browser.
Using GET requests with ASP.NET server forms will unfortunately always yield those "ugly" URLs.
One thing that you can do is change the form to not be a server form and instead be a regular form:
<form method="get" action="Search.aspx">
<input type="text" name="query" />
<input type="submit" name="SearchButton" value="Search" />
</form>
One limitation of this solution is that you can no longer place certain ASP.NET controls within this form. For example, the <asp:Button> control will not work in this form because it must be contained within a server form (that is, a form that has runat="server" on it).
Since its a GET request you can also use javascript, setting the
location.href = 'http://mysite.com/search/' + query;
Then on the ASP.NET side you can use the URL Rewriting feature to redirect that url to a specific ASPX page as a query string parameter.
Let me know if you would like a more detailed sample.
Sample:
Here is a sample, please note I haven't tested it, but this should get you started.
<html>
<head>
<script type="text/javascript">
function searchRedirect()
{
var query = $get('query');
location.href = "/search/" + query.value;
}
</script>
</head>
<body>
<div class="search">
<input type="text" id="query" /><br />
<input type="button" id="search" value="Search" onclick="searchRedirect();" />
</div>
</body>
</html>
Then on the redirect side you have have a RouteModule like this:
public class UrlRewriter : IHttpModule
{
public void Dispose()
{
}
public void Init(HttpApplication context)
{
context.AuthorizeRequest += new EventHandler(OnBeginRequest); //this ensures the login page has the vitual url not the mapped url
}
private void OnBeginRequest(object sender, EventArgs e)
{
var application = sender as HttpApplication;
if (application != null)
{
var requestPath = application.Request.AppRelativeCurrentExecutionFilePath;
if (requestPath.ToLower().StartsWith("/search/"))
{
var query = requestPath.Substring(8);
application.Context.RewritePath("Search.aspx", null, "query=" + query, false);
}
// .. Other Routes
}
}
}
And assuming the code is in your App_Code folder you could use this in your web.config
<system.web>
<!-- ... -->
<httpModules>
<add name="UrlRewriter" type="UrlRewriter, __code"/>
</httpModules>
</system.web>
<!-- If IIS7 -->
<system.webServer>
<modules>
<add name="UrlRewriter" type="UrlRewriter, __code" />
</modules>
</system.webServer>
Well, the main thing that's making that 'look bad', is you're using ViewSate and GET; so don't do that (either disable the ViewSate and adjust code accordingly, or use POST).
What you may also be interested in, however, is URL Re-Writing. You can do that in a few ways, I typically do it with a wildcard mapping in IIS and appropriate changes to the Global.asax file. Searching will reveal how to do this.
Let's say I have a search page called Search.aspx that takes a search string as a url parameter ala Google (e.g. Search.aspx?q=This+is+my+search+string).
Currently, I have an asp:TextBox and an asp:Button on my page. I'm handling the button's OnClick event and redirecting in the codebehind file to Search.aspx?q=
What about with ASP.NET MVC when you don't have a codebehind to redirect with? Would you create a GET form element instead that would post to Search.aspx? Or would you handle the redirect in some other manner (e.g. jQuery event attached to the button)?
You need to understand that MVC doesn't directly reference .aspx pages like WebForms in its URLs. Its main purpose is to separate concerns, that is model (data), controller (logic), and view (presentation).
First, you'd have to create a route matching your URLs, which would now look like this for example : /home/search/This+is+my+search+string
This would call the Search action method of the Home controller, which would get "This is my search string" as an input parameter. This action is responsible for accessing the model and pulling the results probably from a database.
Typically, your search action would then return a ViewResult containing the view placed in the folder /Views/Home/Search.aspx. Here, you can use neither the Postback functionality nor the events of your Web controls like in WebForms, because MVC applications are stateless and not event-driven. It's more like a request/dispatch way of doing things.
Read more about MVC here.
Create a user control called Search.ascx with a form:
<% using (Html.BeginForm ("Search", "Home")) { %>
<input name="search" type="text" size="16" id="search" />
<input type="image" name="search-image" id="search-image" src="search.gif" />
<% } %>
And in your search action all you need is the following:
public class HomeController : Controller
{
public ActionResult Search (string search)
{
throw new Exception (string.Format ("Search: {0}", search));
}
}
In your master page or wherever you can then add
<% Html.RenderPartial ("Search"); %>
You can use a simple javascript in the button's onclick to redirect to the search page:
Search <input type="text" id="go" size="4" /><input type="button" value="<%=Html.Encode(">>") %>" onclick="javascript:window.location='<%=Url.Action("Search", "Home") %>/' + document.getElementById('go').getAttribute('value')" />