Closed monroemann closed 5 years ago
@tute thank you! :D
Hi @monroemann! You have to define that method in a new file in your Rails app, copying the contents from https://github.com/merit-gem/merit/wiki/How-to-show-a-points-leaderboard. You can do it in a model or an initializer and it will work (the wiki suggests an initializer but I'd now do it within app/models/merit/
).
Best!
Hi @tute thanks for the quick response! Two follow ups:
Thanks very much! cc: @chen-robert @bhavyabh @shreepatel95
app/models/merit/score.rb
:)
Hi @tute Thanks again for your generous assistance!
We created the app/models/merit/score.rb file and pasted the code you listed on https://github.com/merit-gem/merit/wiki/How-to-show-a-points-leaderboard
And then, I put this code in the view:
<%= Merit::Score.top_scored %>
I reset the server and went to the leaderboard page and I'm still getting the same error:
undefined method
top_scored' for Merit::Score(id: integer, sash_id: integer, category: string):Class`
Is there still something I may be missing? Thanks!
:thinking: And does putting it as an initializer work?
I shall try that @tute
Doing that gives me this:
So it seems to be accessing something in the database, but it's not a leaderboard. Does this look like we're on the right track?
The view code is: <%= Merit::Score.top_scored %>
Is that an array it is displaying?
Ahh, it's a hash. I am getting closer:
I'm working on displaying the user's name, and the point value.
I'm getting closer. I was able to map them to just display user_id and sum_points. But I'm stuck on how to then access that user_id to turn it into the user's .full_name (which is a method we defined).
<% Merit::Score.top_scored.map.each do |x| %>
<% array = [] %>
<% array = x.values[0] %>
<% i = 0 %>
<% while i < x.length %>
<%= User.find(user_id: array[i]).first_name %>
<% i += 1 %>
<% end %>
<% end %>
This is what I am working on, but I think I'm probably making it too complicated.
Progress:
<% Merit::Score.top_scored.map.each do |x| %>
<% array = [] %>
<% x.each do |user| %>
<% array << x.values[0] %>
<% end %>
<% i = 0 %>
<% while i < x.size %>
<%= User.find(array[i]).first_name %>
<% i += 1 %>
<% end %>
<% end %>
give this output, which works, but is duplicating the first name:
Trying to figure out why there are duplicates.
I guess I'll stop at this point. Is there an easier way to display the leaderboard? ๐
I think you'd want something like:
<%= Merit::Score.top_scored.map do |top_score_hash|
User.find(top_score_hash[:user_id]).first_name
end.to_sentence %>
Closing this issue as it's not a bug in merit or its docs, but happy to continue further discussion. Good luck!
Hi @tute Sorry to bother you again, but I'm getting this error:
Thoughts?
And does this only show the first name? Is the score also included in this code?
top_score_hash
should have the score, too. To debug, what does the following show for you?
<%= p Merit::Score.top_scored.map(&:inspect).inspect %>
<%= p Merit::Score.top_scored.inspect %>
Hi @tute
Here is the output from each of those lines of code, separated by two line breaks:
Does this help you?
Yes, and it might help you too! The keys are strings not symbols so:
<%= Merit::Score.top_scored.map do |top_score_hash|
User.find(top_score_hash["user_id"]).first_name + " " + top_score_hash["sum_points"]
end.to_sentence %>
Another error! ๐
Thoughts on this one @tute
Do we need to turn sum_points into a string? Or maybe I'll just try displaying it without quotation marks?
I found this, but it's not quite clear to me: https://stackoverflow.com/questions/20450497/ruby-on-rails-no-implicit-conversion-of-string-into-integer-for-getting-json
Ahh! I got it work by adding .to_s !!
<%= Merit::Score.top_scored.map do |top_score_hash|
User.find(top_score_hash["user_id"]).first_name + " " + top_score_hash["sum_points"]**.to_s**
end.to_sentence %>
That produces this:
My final questions: how to display them in distinct columns. Can I just do two different User.find queries, each displayed within a different column? Or better, perhaps I should move these queries into the controller or model, and save the results as instance variables? Thanks so much @tute
I wish we were closer so we could pair in a meetup, I think it will be way easier for you to grasp this in a collaborative space like that.
No need of another find, as you already have the score. The line in the middle of my snippet contains the data you need, you may now display it as you please in an erb template.
Best!
HOORAY! I got it to work! This is the code I wrote:
And this is the result. Not bad, do you agree?
Does this look like it works okay?
Follow up question: If on this one page, I'd like to display four leaderboards: Today, Last 7 Days, Last 30 days, and Last 365 days, can I manually override that here in the view? Or do I have to do something in that initializer file?
I just looked at your documentation again. Would this work appropriately:
<% Merit::Score.top_scored(since_date: 1.week.ago,
limit: 25).map do |top_score_hash| %>
I wish we were closer so we could pair in a meetup, I think it will be way easier for you to grasp this in a collaborative space like that.
No need of another find, as you already have the score. The line in the middle of my snippet contains the data you need, you may now display it as you please in an erb template.
Best!
We shall meet one day in person! :smile:
And, it worked! Looks like this:
Is it okay that I have all that code in the erb template?
And (thanks for being so patient with all my questions), is there a way to show "This Month", "This Week", "This Year", etc that uses the calendar? And what exactly does 1.day.ago do? Does that show today, or the last 24 hours? It would be great to show 'Today' and 'Yesterday' based on clock time.
Glad you made it work! Check Rails' DateTime API:
Thank you very much! Shall start researching! ๐ ๐
Where do you live, incidentally? You are Argentinian?
Hello!
We are trying to add a leaderboard page, but this code:
This results in a 'undefined method top_score error.
We also tried to manually create a leaderboard by creating an array, i.e.
but that also resulted in an undefined method, this time for score_points
Do you happen to know what we are doing incorrectly? Thank you!