HTML/JS works in debugger, but not real-time

Celegorm

Site Team
Staff member
Messages
11,741
Location
USA
Ok, so I need some help here. I"m not a good web developer and I've been tasked with helping a team I'm on figure something out.

I need to create a HTML password field that responds to the key down event of the enter button. When that is done, it should make a call to a javascript function which takes in the username and a hashed version of the password and validate the user's info.

If the credentials are valid the users is forwarded to a permissions-appropriate page, if invalid they are sent to a page to re-try the log in.

When done in the debugger in chrome and FF, this works perfectly. When I run it in real time nothing happens. Below is the script that calls the event, and the javascript itself that's doing all the logic. As a kicker, I'll mention that the javascript works perfectly at any time, if we click on the log-in button.

HTML:
<script>
           $(document).ready(function()
           {
               $("#topnav_login").keypress(function(event)
                   {
                       if(event.keyCode == 13)
                       {
                           doLogin();
                           if (event.preventDefault)
                               event.preventDefault();
                           else event.returnValue = false;
                       }
                   });
           });
	</script>

Code:
function doLogin() {
	// Getting the hashed value of the password from the form
	var uhash = document.getElementById('f_pw_hashed').value;
	// Getting the username entered into the login form
	var uname = document.getElementById('f_username').value;
	// Var to track the success or failure of login
	var valid = true;

	// Checking to see if a username was entered
	if(uname == "" || uname.length < 1) {
		valid = false;
		// TODO: Display error message of invalid username

	} else if(uhash == "" || uhash.length <= 0) {
		valid = false;
		// TODO: Display password error

	} else {
		// TODO: AJAX Call to check if valid login
		// Get uname hashed pw from API
		// Compare the hashed value from form to response from API
		// If success, then setLoginCookie(uname, hashed, utype)
		// Otherwise display error message.

		// API Implementation to create user
		var url = getGURL() + "/validateAccount?userName=" + uname + "&password=" + uhash;

      	// readyState is now 0 - Uninitialized

      	xhr.open("GET", url, true); // true means async
      	xhr.setRequestHeader( "Content-Type", "application/x-www-form-urlencoded" );
      	// readyState is now 1 - Loading

      	xhr.send(null);

      	// readyState is now 2 - Loaded

      	xhr.onreadystatechange = function() { 
      		switch( xhr.readyState ) { 

      		case 3: // Interactive 
      			// readyState is now 2
      			break;

      		case 4: 	// Completed
      			if( xhr.status == 200 ) {
      				var jsonObject = JSON.parse(xhr.responseText);
					if(jsonObject.status) {
						// Successful login - get user info so cookies can be set
						// TODO: NEED A WAY TO POST UserId here from datastore

						setAccountInfo(uname, uhash);
					} else {
						// Login Failed - Forward to login page
						window.location.replace("login.html");
					}
				
      			} else if( xhr.status == 404 ) {
					// Display error message in case of 404 error returned
					
      			} else {
      				// Display error message in case of any other error returned

      			}
      		break;
      		} // end switch
      	};
 
Few things quickly spring to mind:

1) Where is xhr declared? It's obviously meant to be an XMLHTTPRequest, but where do you initialise it?
2) You're setting the "onreadystatechange" after you call the send method on your xmlhttprequest, while it *should* be ok, if the ready state changes before it executes that line then you'll miss it and nothing will happen.
3) does getGURL() return an address that's equal to the current server? Cross site AJAX won't work in normal mode, but sometimes it can be enabled in debug mode.
4) You can still do some form of debugging without a debugger by putting alert statements in the code at various points to print out various values along the way and check they're what you expect (or even check if your code has got that far at all.)
5) Your brackets don't match up as is (but I'm assuming you've just missed the last couple off in copying and pasting it.)
 
To answer in order of the questions (or ask some of my own) in order:

1) xhr is declared up at the top as a new XMLHTTPRequestwith all the other variables that are global to that file.
2) What exactly do you mean by this? Are you saying to do the xhr.send after declaring the onreadstatechange function?
3) Yes. We were originally hosting the website and the database on separate systems but ran into problems with cross-site and then moved everything onto the google app engine server
4) That's something I can.
5) Yeah, I just didn't copy them over. The two that are missing here are actually in the file :)
 
For 2) yup that's exactly what I meant - it's unlikely it's causing the issue, just a passing thought.

My advice at this stage would be to try 4) and report back on how far it's getting, that way we can take a specific look at where the code is (or isn't) reaching.
 
Thanks for the input, I'll give it a shot tonight after work and class and let you know what I find out!
 
Had some "time" in a lecture today so I tried this out... I put alerts in (see below) and then played with the order of the send/statechanged function. In both cases, the alerts were not being hit unless I was in the debugger. They were still hit when I pressed the actual login button (not pressing enter to submit)

Here's what I did so you can see:

Code:
alert("Sending");

      	xhr.send(null);
        
        alert("Sent");

      	// readyState is now 2 - Loaded

      	xhr.onreadystatechange = function() { 
      		switch( xhr.readyState ) { 

      		case 3: // Interactive 
      			// readyState is now 2
                alert("sate 3");
      			break;

      		case 4: 	// Completed
                alert("State 4");
      			if( xhr.status == 200 ) {
                    alert("got something");
      				var jsonObject = JSON.parse(xhr.responseText);
					if(jsonObject.status) {
                        alert ("valid");
						// Successful login - get user info so cookies can be set
						// TODO: NEED A WAY TO POST UserId here from datastore

						setAccountInfo(uname, uhash);
					} else {
                        alert("failed");
						// Login Failed - Forward to login page
						window.location.replace("login.html");
					}
				
      			} else if( xhr.status == 404 ) {
					// Display error message in case of 404 error returned
					
      			} else {
      				// Display error message in case of any other error returned
                    alert ("something else");
      			}
      		break;
      		} // end switch
      	}; // end anonymous function
 
Hmm, where abouts in the web page is the first bit of Javascript you linked to? Have you tried using the onKeyPress attribute in the HTML tags in the form rather than attaching it the way you are at the moment?
 
To be honest, I'm not sure how to add the onKeyPress so it calls the script above. That scipt is (our should be) called on every keyup on what is call the topnav_login.

The project itself is partially confidential to our stakeholders so I can't really post more of the files than I have. However, I could email you the files if that'd help. Just PM me with your email address if you're willing.
 
Back
Top Bottom