implementing a basic login page using closure xhrio and event handlers

109 views
Skip to first unread message

Closure noob

unread,
Nov 16, 2010, 7:15:40 PM11/16/10
to Closure Library Discuss
I am trying to implement a basic login page but am running into
issues. May be it is a flawed design I am following or it is a JS
gotcha that is tripping me, I would appreciate any feedback:


myproject.login = function() {


goog.events
.listen(
goog.dom.getElement(loginPost),
goog.events.EventType.SUBMIT,
function(e) {
var emailAddress = goog.dom
.getElement(loginEmailAddress).value;
var password = goog.dom.getElement(loginPassword).value;
var postData = new goog.string.StringBuffer(
'emailAddress=', emailAddress, '&',
'password=', password);
postData = postData.toString();
goog.net.XhrIo
.send(
'http://127.0.0.1:8080/myproject/login',
function(e) {

// e.type will be
// goog.net.EventType.COMPLETE
var xhr = /** @type {goog.net.XhrIo} */
(e.target);
var response = xhr
.getResponseText();
goog.dom.getElement('displayContent').innerHTML = response;
xhr.dispose();
}, 'POST', postData);

});
};



I have a login function that is listening on my login form(the id
of the form is "loginPost"). When the user submits this form, it will
make a Async POST request to http://127.0.0.1:8080/myproject/login
url.

The response from this request will be displayed in a div block whose
id is set to "displayContent". The following code snippet will do
that

goog.dom.getElement('displayContent').innerHTML = response;


On the server-side the response from a POST request to
http://127.0.0.1:8080/myproject/login could be of two types:

1) the user successfully logged in and will be taken to his/her
homepage

OR

2)failed login and the user will be shown the same login page again
with an appropriate error message

Lets ignore the first case and take the second case:

The login page with error message is now displayed.

So far so good.

Here comes the rub: As I submit the login form, the UI is non-
responsive. Apparently the event handler on the login submit is all
gone.

So, one option is to do the following, kinda recursive calling the
myproject.login() function:

..............................
..........................


var response = xhr
.getResponseText();
goog.dom.getElement('displayContent').innerHTML = response;

myproject.login();
xhr.dispose();
.....................

.,.......................

This is kinda behaving unpredictably; seems to working in chrome but
not on firefox.


May be it is flawed design I am following or it is a JS gotcha that
is tripping me, I would appreciate any feedback.

thanks a lot guys.

Rob Hofmeyr

unread,
Nov 17, 2010, 3:17:27 AM11/17/10
to Closure Library Discuss
Hi,

First a couple of comments:

1. goog.dom.getElement() expects a string, so give it one:
goog.dom.getElement('loginPost'). You're ommiting quotes in most of
your calls.
2. Instead of building postData, use
goog.dom.forms.getFormDataString('loginPost') to get the post
variables.

The issue you're running in to is due to your design. You're replacing
the form with the event handler attached so the event handler will no
longer exist. Using innerHTML will not execute js calls in your
response.

In my opinion as a best practice, an AJAX response should carry only
data, not logic. Your callback will perform any logic/processing that
needs to occur. So if you return HTML, rather return a stub (returning
and replacing just the input fields with their validation messages
will not affect the event handler). Have you considered returning JSON
instead of HTML stubs. For example:

{'code':0, 'errors':[{'loginEmailAddress':'Invalid email address'},
{'loginPassword':'Invalid email address'}]}

Code 0 would indicate an error (1 could indicate success), and you
have your field names and validation messages which you can easily
display.

In the above code, did you try calling myproject.login() just before
xhr.dispose()?

> make a  Async POST request tohttp://127.0.0.1:8080/myproject/login


> url.
>
> The response from this request will be displayed in a div block whose
> id is set to "displayContent". The following code snippet will do
> that
>
> goog.dom.getElement('displayContent').innerHTML = response;
>

> On the server-side the response from a POST request tohttp://127.0.0.1:8080/myproject/login could be of two types:

Reply all
Reply to author
Forward
0 new messages