Generating a POST request for PayPal button in C# ASP.net - c#

I'm trying to allow a web form to use a PayPal buy it now.
The relevant page is here.
Based on which radio button a user selects, depends on which paypal button they are "redirected" to.
The subscriptions are easy - they are just a simple redirect.
The last option, requires a user select a venue.
For this, i require to use the form below:
<form action="https://www.paypal.com/cgi-bin/webscr" method="post">
<input type="hidden" name="cmd" value="_s-xclick">
<input type="hidden" name="hosted_button_id" value="10956105">
<table>
<tr><td><input type="hidden" name="on0" value="Venue">Venue</td></tr><tr><td>
<input type="text" name="os0" maxlength="60"></td></tr>
</table>
<input type="image" src="https://www.paypal.com/en_US/GB/i/btn/btn_buynowCC_LG.gif" border="0" name="submit" alt="PayPal - The safer, easier way to pay online.">
<img alt="" border="0" src="https://www.paypal.com/en_GB/i/scr/pixel.gif" width="1" height="1">
</form>
But of course, I want to do it without using that form.
What I have so far is:
if (singleOneOff.Checked)
{
paypalForm.Text = getPaypalForm(venueSelect.SelectedItem.Text);
var strJS = getPayPalPostJS("_xclick");
paypalJs.Text = strJS;
var xxx = "dd";
}
This determines if that particular radio button was ticked.
getPaypalForm
private String getPaypalForm(string venue)
{
StringBuilder strForm = new StringBuilder();
strForm.Append(#"<form action=""https://www.paypal.com/cgi-bin/webscr"" name=""_xclick"" method=""post"">");
strForm.Append(#"<input type=""hidden"" name=""cmd"" value=""_s-xclick"">");
strForm.Append(#"<input type=""hidden"" name=""hosted_button_id"" value=""10956105"">");
strForm.Append(#"<input type=""hidden"" name=""on0"" value=""Venue"">");
strForm.Append(#"<input type=""text"" name=""os0"" value=""{0}"" maxlength=""60"">");
strForm.Append("</form>");
return String.Format(strForm.ToString(), venue);
}
getPayPalPostJS
private String getPayPalPostJS(string strFormId)
{
StringBuilder strScript = new StringBuilder();
strScript.Append("<script language='javascript'>");
strScript.Append("var paypalForm = document.forms.namedItem('{0}');");
strScript.Append("paypalForm.submit();");
strScript.Append("</script>");
return String.Format(strScript.ToString(), strFormId);
}
However, if i select the radio button, and a venue, and press the button, nothing happens....
Any ideas where i've gone wrong?
I followed this guide: http://www.netomatix.com/development/postrequestform.aspx

Here's a much cleaner, server-side solution to the ASP.NET/PayPal single form problem:
http://codersbarn.com/post/2008/03/08/Solution-to-ASPNET-Form-PayPal-Problem.aspx

The root of the problem is that ASP.Net web forms wrap everything on the page inside of one large <form> tag. Your paypal code is rendering a nested form and that doesn't work.
Read this question for more information.

Related

Page does not load when pressing back on browser

I have a small project in asp.net core 3.
In one of the razor page I have this:
<form method="post" enctype="multipart/form-data">
<table class="basic">
#for (int i = 0; i < Model.activeSlides.Count; i++)
{
<tr>
<td>
#Model.activeSlides[i].Filename
</td>
<td>
<input type="submit" value="Move Up" asp-page-handler="MoveUp" asp-route-num="#i" />
<input type="submit" value="Move Down" asp-page-handler="MoveDown" asp-route-num="#i" />
<input type="submit" value="Archive" asp-page-handler="Archive" asp-route-num="#i" />
</td>
</tr>
}
</table>
...
</form>
So each of the buttons has their own OnPost function. Each of them modify an XML file and loads the same webpage.
public void OnPostMoveUp(string num)
{
...
}
public void OnPostMoveDown(string num)
{
...
}
public void OnPostArchive(string num)
{
...
}
I have noticed that when the buttons are used, they show the page handler and route in the URL. E.g. https://localhost:44342/screens/edit?num=2&handler=MoveUp
The problem I am facing is after a button has been pressed, the user may select a hyperlink in the first column. This is just an image, but the when the back button on the browser is pressed the page does not load.
P.S. I am not using MVC.
I have fixed this by adding Response.Redirect("/screens/edit"); at the end of all the OnPost methods.
This means the url params don't show therefore then clicking a link and choosing back on the browser now works.
This also fixes refreshing the page so it doesn't submit the form again.

Trying to log into a website programmatically

I am trying to login into a website using a c# program. Right now my program accesses the website and opens the link I want but is redirected to a page where it shows a link to login I go to that and it shows a log in form. Right now I just have this program running in a console application and when I put it into a winform I'd like for the only input to be the username and password.
I have tried several different things using webclient, MSHTML and SHDocVw, and HTTPRequest.
<fieldset class="input">
<p id="com-form-login-username">
<label for="username">Username</label><br />
<input name="username" id="username" type="text" class="inputbox" alt="username" size="18" />
</p>
<p id="com-form-login-password">
<label for="passwd">Password</label><br />
<input type="password" id="passwd" name="passwd" class="inputbox" size="18" alt="password" />
</p>
<p id="com-form-login-remember">
<label for="remember">Remember Me</label>
<input type="checkbox" id="remember" name="remember" class="inputbox" value="yes" alt="Remember Me" />
</p>
<input type="submit" name="Submit" class="button" value="Login" />
</fieldset>
I would like to be able to access the first link and pull all the source code to grab the information that I need.
I think your looking for selenium its a really useful automation library it also can run in headless mode which means that it wont show the google tab where the automation is happening.
you can also get an elements value and many more things
you can see more at : https://www.seleniumhq.org/
Tutorial: https://www.guru99.com/selenium-csharp-tutorial.html
I managed to figure out something that works I couldn't get Selenium to work.
wb.Visible = true;
wb.Navigate(MainSite);
{
while (wb.Busy) { Thread.Sleep(100); }
document = ((HTMLDocument)wb.Document);
if (document.body.outerHTML.Contains("Logout")) { Loggedin = true; }
if (!(document.body.outerHTML.Contains("Logout"))) { Loggedin = false; }
if (Loggedin == false)
{
element = document.getElementById("Username");
username = (HTMLInputElement)element;
username.value = Username;
username = null;
element = document.getElementById("Passwd");
password = (HTMLInputElement)element;
password.value = Password;
password = null;
element = document.getElementById("Submit");
Submit = (HTMLInputElement)element;
Submit.click();
Submit = null;
while (wb.Busy) { Thread.Sleep(100); }
SourceCode = document.body.outerHTML;
}
}

Capture URL Before Form Post

I'm trying to capture the URL submitted when the page loads. When the page loads, it's appended with provided parameters to give me information i need save off. The issue is when I have the user fill in form fields and submit, the URL contains the handler method. What seems obvious is that I need to capture the URL before the form is submitted. I'm not familiar enough w/ Razor to understand if there's an event that fires on load, or how to accomplish this. Is there something simple like a page load event? Thanks!
1) Starts as: https://localhost:44384/sign
2) On submit takes the handler name: https://localhost:44384/Sign?handler=SubmitAndRedirect
<form method="post">
First name:<br>
<input type="text" name="firstname" autocomplete="on" maxlength="10" required><br>
Last name:<br>
<input type="text" name="lastname" autocomplete="on" maxlength="10" required><br>
Employee number:<br>
<input type="text" name="empnum" maxlength="10">
<br>
<br>I agree to the terms above:<br>
<input type="checkbox" name="check" required>
<button type="submit" asp-page-handler="SubmitAndRedirect">Submit and Redirect</button>
</form>
public ActionResult OnPostSubmitAndRedirect()
{
//Capture Form Data and Push to SQL DB
var firstname = Request.Form["firstname"];
var lastname = Request.Form["lastname"];
var empnum = Request.Form["empnum"];
bool isValidUser = ValidateUser(empnum, lastname);
if (isValidUser == true)
{
WriteToDB(firstname, lastname, empnum, url);
return Redirect(hardcoded);
}
else
{
return Redirect("/sign");
}
}
Model binding features of MVC might be what you're looking for. Take a look at this article.
See how it uses the EmployeeViewModel class and how the form gets posted to the action.
There is no protected void Page_Load(object sender, EventArgs e) in MVC as in Web Forms that I'm aware of.
Also check out jQuery's submit handler. Maybe this can allow you to capture some information and process it before submitting.
Thanks all. I was able to resolve adding a property on the C# side and then capture the request before the form was submitted by setting the property outside the form using inline code between paragraph tags.
<p>
#{
var QS = Request.QueryString.Value;
JT.query = QS;
}
#*<h1> #JT.query</h1>*#
</p>

ajax only sends the first value of input and not the others?

I made a school website where teachers will be able to upload the students' marks. Up to now I have these three files:
The first one, will display every students name depending on the subject and course
<table class="check">
<tr class="arrow">
<th>Student</th>
<th>Add Mark</th>
</tr>
#foreach(var users in user){
<tr class="arrow">
<td>#users.Nombre #users.Apellido</td>
<td>
<form method="post">
<input type="text" id="user" style="display: none" name="user" #Validation.For("nombre") value="#users.UserId" />
<input type="text" id="galleryId" style="display: none" name="galleryId" #Validation.For("nombre") value="#galleryId" />
<input type="text" id="note" name="button2" name="note" #Validation.For("nombre") />
<input type="button" value="Ready" title="Ready" onclick="loco(document.getElementById('user').value, document.getElementById('galleryId').value, document.getElementById('note').value)" />
</form>
</td>
</tr>
}
</table>
Here you can see that I used foreach to display every student's name, and then next to it there should be displayed an input textbox for the teacher to write the mark of a specific student. That's why I included the form in the foreach.Next is the ajax file:
function loco(user, gallery, note) {
var xmlhttp;
var user = document.getElementById("user").value;
var galleryid = document.getElementById("galleryId").value;
var note = document.getElementById("note").value;
if (window.XMLHttpRequest) {// code for IE7+, Firefox, Chrome, Opera, Safari
xmlhttp = new XMLHttpRequest();
}
else {// code for IE6, IE5
xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
}
xmlhttp.open("GET", "/Marks/add1/" + gallery + "/" + user + "/" + note, true);
xmlhttp.send();
}
And finally, we have the page which will insert the marks to the database without returning any table or div, just uploading the mark.
#{
var db2 = Database.Open("ica");
var user = UrlData[1];
var galleryId = UrlData[0];
var note = UrlData[2].AsInt();
db2.Execute("INSERT INTO Notas (Nota, UserId, Sub_Id) VALUES (#0, #1, #2)", note, user, galleryId);
}
So, why does the ajax send the values of the first student to the upload file and not the second, third, etc? Why, when I click on the submit button of the second student does it sends the mark of the first student again, and only that of the first student?
You're using hard-coded IDs in the HTML inside your for-each loop, so you're going to get multiple elements on your page with the same IDs for user, galleryId and note. That means that your selector can only select the first no matter which you're actually trying to use. You need to do something such as adding an index number to the end of the ID instead of fully hard-coded IDs, so that they can be distinguished from one another.
NOTE:
I observed you using name multiple times in same input please remove that:
<input type="text" id="note" name="button2" name="note" #Validation.For("nombre") />
here you gave name as button2 as well note please remove button2
Make the changes as below:
function loco(form) {
var xmlhttp;
var user = form.name.value;
var gallery = form.galleryId.value;
var note = form.note.value;
if (window.XMLHttpRequest) {// code for IE7+, Firefox, Chrome, Opera, Safari
xmlhttp = new XMLHttpRequest();
}
else {// code for IE6, IE5
xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
}
xmlhttp.open("GET", "/Marks/add1/" + gallery + "/" + user + "/" + note, true);
xmlhttp.send();
return false;
}
change your html related code as below:
<form onsubmit="return loco(this)">
<input type="text" id="user" style="display: none" name="user" #Validation.For("nombre") value="#users.UserId" />
<input type="text" id="galleryId" style="display: none" name="galleryId" #Validation.For("nombre") value="#galleryId" />
<input type="text" id="note" name="note" #Validation.For("nombre") />
<input type="submit" value="Ready" title="Ready" />
</form>

Dynamic load of html code

In my Asp.net website I have a repeater which loads dynamically from code-behind. In code outside the repeater I have an "add" button. On click, I want to add the same controls from repeater asynchronously. On click of the "add" button function NewRow() is called:
function NewRow(){
var guid = jQuery.guid++;
var panel = $('#MainContent_Panel1');
var textboxText = $('#MainContent_TextBox');
panel.after("<span LabelGroup="+i+">Test Text:</span>
<span TextGroup="+i+">"+textboxText.val()+"<br /></span>
<span LabelGroup="+i+">Test Text : </span>
<input type='text' customID="+guid+"/>
<input type='button' Class='Button' ButtonGroup='"+i+"' value='Button Text' /></br>
");
i++;
}
I hate what I am currently doing, because there is so much hardcoded code. Is there any way I can make it more dynamic?
And is there any way to place my newly added row more precisely in dynamic control like repeater?
You could try a templating engine like mustache.js, or you can do it by hand like this:
In your HTML, include a script tag, with type="text/html". This will tell the rendering engine to do not try to render the contents. Inside this tag, you will write the template code for each column.
I marked each variable section as $variable:
$i
$textboxText
$guid
​<script type="text/html"​​​​​​​​​​​​​​​​ id="template">
<span LabelGroup='$i'>Test Text:</span>
<span TextGroup='$i'>$textboxText<br /></span>
<span LabelGroup='$i'>Test Text : </span>
<input type='text' customID='$guid'/>
<input type='button' Class='Button' ButtonGroup='$i' value='Button Text' /></br>
</script>
<!-- And here, some testing elements -->
​<input type="button" id="New" value="New Row">
<input type="text" id="MainContent_TextBox" value="Some Value">
<div id="MainContent_Panel1"></div>​​​​​​​
And then, in your javascript, you only need to get the html contents of the script tag, then replace each $variable with the value to use.
Please note that you should use /g when calling .replace, to replace all ocurrencies of your $variable in the template.
i = 1;
$("#New").click(NewRow);
function NewRow(){
var guid = jQuery.guid++;
var panel = $('#MainContent_Panel1');
var textboxText = $('#MainContent_TextBox').val();
var html = $("#template").html()
.replace(/\$i/g,i)
.replace(/\$guid/g,guid)
.replace(/\$textboxText/g,textboxText);
panel.append(html);
i++;
​}​
Using this approach, you are separating html from js code. Something that will help you in the future if you have to maintain this.
Hope it helps.
You could create your tags on the fly like this:
var $span1 = $("<span />").text("your text").attr("TextGroup", i);
...
var $text = $('<input type="text" />').attr("customID", guid);
...
var $button = $('<input type="button" />').addClass("Button").val("Button text").attr("ButtonGroup", i);
And then just add them to the control container
$panel.append($span1).append(...);
Try it live on Fiddler

Categories