0

I'm trying to retrieve a list of users from a simple MySQL database table, e.g., called TableA, which looks something like: Username(varchar), Level(tinyint), DateCreated(datetime).

On an html page I have a search input box, say - and underneath it I have a div, say to display the results. I have it so that when I start typing a word (to look for a username), jQuery makes makes an ajax request to a php file which queries the TableA for the usernames.

The jQuery part looks like:

$("#search_bar").keyup(function()
{
   var user = $(this).val();
   $.post('get_user.php', user_name : user, function(data)
   {
       $("#result_box").html();
   });
} 

The php script, get_user.php, again is a simple script which looks something like

<?php
$user = $_POST['user_name'];
//connect db,
$query = mysqli_query (select Username from TableA where Username like '$user%');

//IMPORTANT PART HERE, I create a <DIV> or can be  <P> and display it back
while ($row = mysqli_fetch_array($query))
{
   echo "<div id="user_info" username='".$row['Username']."'>".$row['Username']."</div>
   //I have the username as an attribute so I can make another .post request and get detailed user info.
}
?>

Now, previously using jQuery, every result that is being returned as a is being dumped in the result_box div ($("#result_box").html();). The problem I have with this is that if I have 3 users, say Mick, Mike and Mila and I start searching by typing 'M', the query returns all three (that's fine), however, when I click on a name, say the last one returned would be Mila, this will trigger another jQuery function which say for now just prints the name of the selected in a popup box - it however picks up the attribute of the first name, Mick, from the the first div that appeared there and not the one I clicked on. It's strange. If the search returns only a single entry then that's fine - however with multiple entries, regardless of which one I click, jQuery picks up only the first one.

I suspect its because the divs all have the same ID, and since they are being 'dynamically' created - jQuery just picks up the attribute (e.g., $("#user_info").attr('username') ) of the very first one or only one created?

Any help would be appreciated.

Thanks

2
  • 3
    your id's should be unique. why not make the div id be the username returned from query? Commented Feb 24, 2014 at 5:57
  • 1
    You can use jquery .on() method for access dynamically access content Commented Feb 24, 2014 at 5:59

2 Answers 2

1

You should use jQuery data()
You should create the div like :

<div class="userLink" data-username="$row['username']"></div>

And acces it from jQuery like

    $('.userLink').on('click',function(e) {
         var username = $(this).data('username');
    }

And the attribute ID must be UNIQUE.

Sign up to request clarification or add additional context in comments.

2 Comments

Thanks! this worked. However, since I was dumping the returning results into a div with the ID of "search_results", I used:` $("#search_results").on('click', '.userLink', function() { //Rest of stuff here//});` I'm also considering another method of retrieving search results as this one queries the database each time a user starts typing in the search box. I was thinking of importing the users list in JSON format and so the search can happen locally - after which I call another php script which returns detailed user data. Any suggestions are most welcome! Thanks.
Well, you could query the DB only once, export the results as JSON in php, and with jQuery parse the JSON array to find the user.. But, considering a really big database, MySQL would be faster. If I were you, I'd stick to MySQL.
1

First off, you need to fix the issue of multiple DOM objects with the same id. Perhaps you can just use a class name. But, that probably won't fix your click issue. The click issue should be fixed by using the this reference that comes with the click event. This will tell you exactly which items was clicked on so even if there are multiple items, you can know which one was clicked on and can reference the attributes on that particular object with code like this:

$(this).attr("username");

FYI, you perhaps should use the HTML5 convention of data attributes. So, instead of an attribute of username="xxx", you would use data-username="xxx". Then, you can use:

$(this).data("username");

You can combine all these changes with delegated event handling to have a click handler like this:

Your PHP (switch to a class name and data-username attribute):

//IMPORTANT PART HERE, I create a <DIV> or can be  <P> and display it back
while ($row = mysqli_fetch_array($query))
{
   echo "<div class="userInfo" data-username='".$row['Username']."'>".$row['Username']."</div>
   //I have the username as an attribute so I can make another .post request and get detailed user info.
}

Your delegated event handling click handler in the page:

$("#result_box").on("click", ".userInfo", function(e) {
    var username = $(this).data("username");
});

1 Comment

Thanks! That is exactly what I used and it works fine now. I'm also considering another method of retrieving search results as this one queries the database each time a user starts typing in the search box. I was thinking of importing the users list in JSON format and so the search can happen locally - after which I call another php script which returns detailed user data. Any suggestions are most welcome! Thanks.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.