Challenge with javascript/jquery $.get and python backend - javascript

I have an HTML form to enter a username/password to register for a site. I am attempting to implement a javascript/JQuery $.get to send an HTTP GET to check if the username is already in use. On the server side, the "username" value (pulled by request.form.get()) is coming back as None. The javascript source does not seem responsive either on the HTML page.
Javascript as below:
var username = document.getElementById("username");
var inputForm = document.getElementById("form");
document.getElementById("submit").addEventListener("click", function(event) {
event.preventDefault()
});
inputForm.onclick = function(data) {
$.get("/check?username=" + username.value, function() {
alert("CHECKING")
if (data == false) {
inputForm.submit();
}
else {
alert("Sorry - that username is taken!");
}
});
};
Python (Flask) on backend as follows:
#app.route("/check", methods=["GET"])
def check():
"""Return true if username available, else false, in JSON format"""
print("***RUNNING CHECK***")
# get username from web form
username = request.form.get("username")
print(username)
# check that username is longer than 1, then pull list from DB to check against
if len(username) > 1:
usernames = db.execute("SELECT username FROM users")
# return false if username is available
if username in usernames:
return jsonify(False)
# return true if username is NOT available
else:
return jsonify(True)
This is what comes back:
TypeError: object of type 'NoneType' has no len()
INFO:werkzeug:192.168.179.21 - - [22/Aug/2019 16:20:41] "GET /check?username=ajd HTTP/1.0" 500 -

The client side issue that I can see are...
Checking the Javascript console will probably tell you that data is undefined. If should be added as a parameter to the callback function.
You need to escape the get paramters with encodeURIComponenet.
You probably want to run this code when the input is received than when the form is clicked on.
username.oninput = function(data) {
$.get("/check?username=" + encodeURIComponenet(username.value), function(data) {
alert("CHECKING")
if (data == false) {
inputForm.submit();
} else {
alert("Sorry - that username is taken!");
}
});
};

Related

Cookie PHP LARAVEL

I have a cookie created in PHP with the jQuery method where the client enters a value in an input and this cookie is created with that Value while more values are created with a comma.
Example Creation cookie in jQuery:
<script type="text/javascript">
$(function () {
$("#btnAdd").click(function () {
if($('#addtokendelivery').val() === ''){
alert('Valor en Blanco');
}
else {
if ($.cookie('DeliveryToken')) {
$.cookie("DeliveryToken", $.cookie("DeliveryToken") + ',' + $("#addtokendelivery").val());
alert('Repartidores Agregados con Token´s: ' + $.cookie("DeliveryToken"));
} else{
$.cookie("DeliveryToken", $("#addtokendelivery").val());
alert('Repartidor Agregado con Token: ' + $.cookie("DeliveryToken"));
}
}
});
$("#btnRead").click(function () {
alert($.cookie("DeliveryToken"));
});
});
</script>
Example cookie in google chrome value:
DeliveryToken: value1,value2,value3
Example of variable to compare with in laravel:
$orderitemaddons32 = DB::table('users')->where('id', $id)->first();
$orderitemaddons32 = $orderitemaddons32->userdelivery_id;
//result variable dd laravel
"value1"
For example, if it detects that the value 1 is inside the cookie, it proceeds to display the page.
What I want is to verify in the laravel blade if the cookie matches the information of the variable that it creates in my function and to show the page, otherwise not to show it or to put a message that the information is not valid.
There are many ways to do what you want.
For having a condition before you proceed with a request or not, it's usual to use a middleware.
https://laravel.com/docs/8.x/middleware
From the middleware, you can continue with the request or to redirect the user to another page.
I guess your code could look like this in laravel:
$values = explode(',', $_COOKIE['DeliveryToken']);
if (in_array($orderitemaddons32, $values) {
//all good, proceed
// return $next($request);
} else {
/*
* return redirect()->route('home', [
* 'message' => 'The information is not valid'
* ]);
*/
}
Btw, I don't find it secure this kind of usage with cookies, I mean, setting them from javascript and not encrypting them and securing them in server side. One could easily change the value of cookie.
You could leave the cookies to laravel and thus use also the built-in functions.

Alert popping up multiple times and submit button only working after second click

I am working on my CS50 Final Project. I am designing a web app:
I am using flask.
This happens in the login/register page.
I am trying to check if the username is already taken( through jsonify) and if the password and the password confirmation are equal using JS.
So basically the problem is:
After loading tha page and filling out the register form nothing happens on the first click on the submit button. On the second click everything works just as it is supposed to: the functions run fine and check for matching passwords and if the username is available and alert if necessary. If I then close the alert window and click the submit button again I get two alerts from the usercheck function.
If do the same thing again 3 alerts then 4 and so on....For some reason the function gets called again and again but I can't figure out where....
Here's the HTML:
<form id='register' action='/register' method="POST" onsubmit="return !!(passwordcheck() & usercheck());" ></form>
Here's the two JS function in a script tag in the same page:
function passwordcheck(){
const password = document.getElementById('password').value;
const passwordc = document.getElementById('passwordc').value;
if (password != passwordc){
alert('Passwords do not match')
return false;
}
}
function usercheck(){
$('document').ready(function(){
$('form').on('submit',function(e){
e.preventDefault();
var username = document.querySelector('#username').value;
$.get('/check?username=' + username, function(r){
if(r == false){
alert('User taken');
$('#username').focus();
}
else{
(document).getElementById('register').submit();
}
} )
})
})
}
And here's the Python code from the application.py file that querys the database for the username:
#app.route("/check", methods=["GET"])
def check():
print(Fore.BLUE + "check function, line 99")
"""Return true if username available, else false, in JSON format"""
username = (request.args.get('username'),)
if username:
c.execute("SELECT username FROM users WHERE username =?", username)
old_user = c.fetchall()
if len(old_user) > 0:
return jsonify(False)
else:
return jsonify(True)
You have defined two handlers for the form submit event:
- the first in the html (onsubmit="return !!(passwordcheck() & usercheck());") is the userCheck function that does not actually make a request
- the second inside the userCheck function ($('form').on('submit',function(e){) that does make a request
So the first time you submit the userCheck function is called, it does not make a request but add a submit event handler to the form. That is why the request is made only after submitting the form a second time.
You should be better off with something like this:
function passwordcheck() {
const password = document.getElementById('password').value;
const passwordc = document.getElementById('passwordc').value;
if (password != passwordc) {
alert('Passwords do not match')
return false;
}
}
function usercheck(handleSuccess, handleError) {
var username = document.querySelector('#username').value;
$.get('/check?username=' + username, function(r) {
if (r == false) {
handleError();
} else {
handleSuccess();
}
})
}
function submit() {
(document).getElementById('register').submit();
}
function handleUserError () {
alert('User taken');
$('#username').focus();
}
$('document').ready(function() {
$('form').on('submit', function(e) {
e.preventDefault();
if (!passwordcheck()) {
return;
}
usercheck(submit, handleUserError);
})
})
and without the onsubmit attribute on your form element.

C# Razor View passing null object to JavaScript

Here's the rundown. Users can view a razor page both anonymously and logged in. If they are logged in, they get certain features. In my controller, I have a boolean isAnonymous which I set to true or false depending on if there's a signed in user or not. I pass isAnonymous to my view model which gets sent to the razor page.
In the razor page, I have a javascript script tag which needs to retrieve that boolean value and, if isAnonymous is false (meaning someone is signed in), fire off one of two ajax calls to the server.
The first thing I do in my script tag is get the isAnonymous value and convert it to a JavaScript boolean with this:
var isAnonymous = #Json.Encode(Model.IsAnonymous);
after console logging, this appears to return correctly.
Then i put in my if statement. The summary here is if the user is not logged in, none of these functions nested inside the if statement should fire, because they take an ApplicationUser as part of the model. If there is no signed in user, Model.User is null and throws a Null Reference Exception. I thought putting my ajax calls inside the if statement would guard against the exception, but the the logic seems to be blowing right through the if (isAnonymous == false) and hitting those functions despite the logic. Any thoughts as to why this is happening? When isAnonymous is true, I can't have the functions fire.
if (isAnonymous == false) {
if ($('.bookmark-btn').hasClass('bookmark-story-btn')) {
addBookmark();
} else {
removeBookmark();
}
function addBookmark() {
//bookmark a story btn click event
$('.bookmark-story-btn').on('click', function () {
var storyid;
//the storyid should come as a string -
//try to parse it as an int for the controller
if (!isNaN($(this).attr('storyid'))) {
storyid = parseInt($(this).attr('storyid'))
//verify successful conversion from string to int before ajax call
if (typeof (storyid) == 'number') {
var userid = $(this).attr('userId')
var newBookmark = {
UserId: userid,
StoryId: storyid,
};
$.ajax({
url: "/api/bookmark/new",
method: "POST",
data: newBookmark,
success: function (data) {
//remove the save bookmark btn and dynamically add
//the remove bookmark btn so
//the page doesn't require a refresh
$('.bookmark-story-btn').remove();
$('.bookmark-btn-group').append("<button bookmarkId='"
+ data.Id
+ "' userId=#Model.User.Id storyId=#Model.StoryId"
+" class='btn remove-bookmark-btn bookmark-btn'>"
+"<i class='fas fa-2x fa-bookmark'></i></button>")
removeBookmark();
},
error: function (error) {
$('.page-alert').css('visibility', 'visible')
.html("Whoops. Something went wrong."
+" Adding the bookmark failed.")
//automatically close the alert-danger div
//after 2 seconds
setTimeout(function () {
$('.page-alert').css('visibility', 'hidden')
}, 3000);
}
});
}
}
});
}
function removeBookmark() {
//remove a bookmark click event
$('.remove-bookmark-btn').on('click', function () {
if (!isNaN($(this).attr('bookmarkid'))) {
bookmarkid = parseInt($(this).attr('bookmarkid'))
//verify successful conversion from string to int before ajax call
if (typeof (bookmarkid) == 'number') {
//call the ajax
$.ajax({
url: "/api/bookmark/" + bookmarkid,
method: "DELETE",
success: function (data) {
//show-hide the appropriate icons
$('.remove-bookmark-btn').remove();
$('.bookmark-btn-group').append("<button userId=#Model.User.Id"
+" storyId=#Model.StoryId class='btn bookmark-story-btn"
+" bookmark-btn'><i class='far fa-2x fa-bookmark'>"
+"</i></button>")
addBookmark();
},
error: function (error) {
$('.page-alert').css('visibility', 'visible')
.html("Whoops. Something went wrong here."
+" Removing the bookmark didn't work.")
//automatically close the alert-danger div
//after 2 seconds
setTimeout(function () {
$('.page-alert').css('visibility', 'hidden')
}, 3000);
}
})
}
}
})
}
}
You can use Request.IsAuthenticated in both the Razor view:
#if(Request.IsAuthenticated)
{
<script>
' your authenticated client side script here
</script>
}
And then check again server side when posting in your controller for example:
public ActionResult Index()
{
if(Request.IsAuthenticated)
{
//server logic here
}
}
Better still if you decorate the method with the AuthoriseAttribute the user will get an 403 Unauthorized.
You can then do something similar server side for the UserId:
[Authorize]
public ActionResult Index()
{
var userId = User.Identity.Name;
}
Then you don't even need to pass the UserId about. This is all based on using the common Identity practices:
https://learn.microsoft.com/en-us/aspnet/identity/overview/getting-started/introduction-to-aspnet-identity

grails remoteField javascript

I'm having trouble returning a value to the view which then decides if the Submit button should be selectable or not. I'm checking the value of accNbr against an api call that returns JSON. I simple want to not if the user is found or not.
A snippet from within my form on my view - here is the account number input:
<g:remoteField paramName="accNbr" action="validateCustomer" update="[failure: 'error']" bean="${accNbrInstance}" required="" size='40' name="accNbr" value="${accNbr}" data-trigger="change" data-required="true" data-regexp="[0-9]{12}" data-regexp-message="This field requires a valid Account Number of 12 digits"/>
then I have JS (which I think has the errors:
function accountNoError(){
if($('#accountValid').html().value = "Not found"){
$('#submit').attr("disabled", true);
$('#clear_btn').show();
}else{
$('#submit').attr("disabled", true);
}
}
and my controller function:
def validateCustomer() {
def accountNo = params.accNbr
//def accountNo = "621137093178"
def accountValid
if(accountNo.length() == 12){
def http = new HTTPBuilder('https://my.API.call/' + accountNo)
http.auth.basic ('username','password')
http.request(GET, ContentType.JSON) { req ->
response.success = { resp, json ->
assert resp.statusLine.statusCode == 200
accountValid = json
print("JSON is: " + json)
println("Valid Account")
}
}
}else {
accountValid = "Not found"
println("Invalid Account")
}
return accountValid
}
In your jQuery you have an if...else statement.
In your if you disable your submit button:
$('#submit').attr("disabled", true);
and in your else you disable your submit button:
$('#submit').attr("disabled", true);

How to check if USERNAME already exists in PHP/MYSQL?

I'm currently configuring my "User Registration" form in PHP.
Trying to create a simple function to check if the username already exists in the database
After doing my research, I have found that there are several ways this can be done.
(a) the best way is probably to use a PHP/AJAX combination, to check right away if the username already exists (in other words, the check is done BEFORE the user clicks the "Submit" button;
(b) the other way is to do a simple SQL-query, which will return an error message, if that particular username already exists in the database. (The only drawback with this method is that : the check is done only AFTER the user clicks the "Submit" button.
I would have preferred Option A, of course. But, I was unsuccessful in my attempts to create a working AJAX/jQuery script.
So, I went with Option B instead.
And, I got it working.
Here is the simply query I used :
if(isset($_POST['submit1'])||isset($_POST['submit1'])) {
$login = $_POST['login'];
$query_login = "SELECT login FROM registration WHERE login='$login';";
$result_login = mysqli_query($conn,$query_login);
$anything_found = mysqli_num_rows($result_login);
//check if the username already exists
if($anything_found>0)
{
echo "Sorry, that Username is already taken. Please choose another.";
return false; }
else { //proceed with registration
It worked fine. The error was displayed.
The only problem is : the registration form itself disappeared.
I would have liked to display the error on the same page as the registration form, without having to RESET or somehow GO BACK.
I know that the reason for this is something very minor (and kinda stupid on my part :D :D)
Probably something to do with that "return false" thingy at the end of the query.
But, I am not sure.
(a) How can I get the error message displayed on the form-page itself?
(b) Or, better yet, is there a JavaScript Function I can use for this, so that I can simply call the function in the "Submit" button................like so : onSubmit = return function() ??
Thanks
UPDATE: Here is my form code.
form action="myform.php" method="post">
<br>
Choose a username : <input type="text" name="login" value="<?=$login?>"
required>
UPDATE
I was able to find the following jQuery code :
$(document).ready(function() {
//the min chars for username
var min_chars = 3;
//result texts
var characters_error = 'Minimum amount of chars is 3';
var checking_html = 'Checking...';
//when button is clicked
$('#check_username_availability').click(function(){
//run the character number check
if($('#username').val().length < min_chars){
//if it's bellow the minimum show characters_error text '
$('#username_availability_result').html(characters_error);
}else{
//else show the cheking_text and run the function to check
$('#username_availability_result').html(checking_html);
check_availability();
}
});
});
//function to check username availability
function check_availability(){
//get the username
var username = $('#username').val();
//use ajax to run the check
$.post("check_username.php", { username: username },
function(result){
//if the result is 1
if(result == 1){
//show that the username is available
$('#username_availability_result').html(username + ' is
Available');
}else{
//show that the username is NOT available
$('#username_availability_result').html(username + ' is not
Available');
}
});
}
I assume that, for my particular example :
(a) the jQuery file cannot be inserted into the actual PHP file (my php file is named : registration.php, which includes both the html and php);
(b) this particular jQuery file includes a "button", which needs to be clicked to check if the username already exists. This is not a bad idea; but, I would rather that this was done automatically, without the need to click on a button (let's face it : there are some users out there who are indeed too clueless to perform this simple check manually). My aim is free the user as much as possible from the need to do such trivial tasks :D
Anyway, my point is : so as to eliminate the need for a button, I would like to include an auto-function which checks once the user types in the username.
According to Google, the following function is what I need :
Replace $(‘#check_username_availability’).click(function(){ … with $(‘#username’).keyup(function(){ …
(c) Isn't there any way to actually insert that JQUERY into "registration.php" ?? Or, should it be a separate file entirely?
The better way would be you bind the ".blur" event on which you may check if the username is valid via ajax. Don't forget to check the username after form submission at before form submission.
Below your input box create a
<span class= "error">Username is already present. </span>
<span class= "success">Username can be assigned. </span>
and just display the message accordingly.
You may use the script as
$.ajax({
url : "check_username.php",// your username checker url
type : "POST",
data : {"username",$("input.username").val()},
success : function (data)
{
if(data == "success")
{$(".success").show();$(".error").hide();}
else
{$(".error").show();$(".success").hide();}
},
});
You php code would be something like this :
$query = "SELECT username FROM tab_users WHERE username = '".$_POST['username']."'";
$result_login = mysqli_query($conn,$query_login);
$anything_found = mysqli_num_rows($result_login);
//check if the username already exists
if($anything_found>0)
{
echo "fail";
return false;
}
else
{
echo "success";
return false;
}
You can disable the submit button and add a span message near the input field.
Check this code:
function checkUsername()
{
var username = document.getElementById('username');
var message = document.getElementById('confirmUsername');
/*This is just to see how it works, remove this lines*/
message.innerHTML = username.value;
document.getElementById("send").disabled = true;
/*********************************************/
$.ajax({
url : "check_username.php",// your username checker url
type : "POST",
data : {username: username},
success: function (response) {
if (response==0)
{
message.innerHTML = "Valid Username";
document.getElementById("send").disabled = false;
}
if (response==1)
{
message.innerHTML = "Already Used";
document.getElementById("send").disabled = true;
}
}
});
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.0/jquery.min.js"></script>
<label for="uername">Username:</label>
<input type="text" class="form-control" name="username" id="username" onkeyup="checkUsername(); return false;" required/>
<span id="confirmUsername" class="confirmUsername"></span>
<button type="submit" id="send" name="action" value="Send">Send</button>
put this
include([your validating php file]);
and in your form action link to your login form file.
note : your login file have to be php file.

Categories