Activity
I think you should define some roles upfront and let the user choose from those.
Either you do a simple hierarchy based like user < admin < superadmin
etc. Where the admin
has the same rights like user
and some extra and superadmin
has the same right like admin
and some extra. Here you define all the action and the superadmin
for instance can alter the user
to superuser
and vice versa.
Other way would be to grant the user to choose action based roles like can_edit_post
. In this case though you still should have some hierarchy otherwise any user can override any other user's role.
Regarding the database it also can be tricky in more complex cases you have to define joint_tables between roles and users. Although in most cases it's perfectly enough to create a role field on the users table.
Posted in Can Anyone explain me these ruby codes?
This code is pretty dirty. Basically the @notification instance variable gets set to true or false if the notification is due. It also sets to other instance vars for formatting reasons but it's not a great way coding this. Somewhere else those instance vars used to check if notification should be sent and to show the formatted dates. If you just started learning make sure you find nice materials to learn from. This is definitely not one of those.
You have to define the foreign key to on the belongs_to
side. https://apidock.com/rails/ActiveRecord/Associations/ClassMethods/belongs_to
Class Foo
has_many :bars
end
class Bar
belongs_to :custom, class_name: 'Foo', foreign_key: "custom_id", primary_key: 'custom'
end
In this case Foo has to have a custom
as primary key.
Posted in Use Multiple Checkboxes on a Rails Form
Your profile table is not linked to the user which seems to be weird.
What you could do is sth like:
<%= form_for @user, html: { multipart: true } do |f| %>
<div class="form-group">
<%= f.label :role_ids, "User roles" %>
<%= f.collection_select :role_ids, Role.all.order(name: :asc), :id, :name, {}, { multiple: true, class: "form-control" } %>
<div class="explanation">Choose one or more roles</div>
</div>
</div>
....
<% end %>
Users controller
def new
@user = User.new
@user.user_roles.build
end
def create
@user = User.new(user_params)
if @user.save
........
end
def user_params
params.require(:product).permit(:name, ...., role_ids: [])
end
This is kinda the Rails convention. But all you have to do basically is showing the roles on the form to choose from. So you have to query those. In the code I added it to the view. If you like it more you can puy in the controller too. Then you have to send over the role ids that are chosen in the form. Of course you have to whitelist them. Then you can just save it to the db when user is saved. Nothing fancy.
Posted in Use Multiple Checkboxes on a Rails Form
Can you telll us a bit more about your database schema?
Posted in API low-level caching
Hey Chris,
I am a bit confused regarding API caching. I am using JSONAPI spec and fast_jsonapi gem and trying to cache the vehicle itself on show action and if there are params coming over like include=service_notes,service_alerts
then I would like to cache those too. This is my initial approach but not sure if it is right.
I have 2 main issues:
For the vehicle caching itself is there a better approach than my
vehicle = Vehicle.find_cached(params[:id])
. This is not usingupdated_at
but an after save callback to update the cache if vehicle has been updated. I just don't see if I could somehow use sth likeRails.cache.fetch(["vehicles", vehicle], version: vehicle.updated_at)
as it is proposed here: https://github.com/rails/rails/pull/29092 since this needs thevehicle
instance. As you see theset_vehicle
controller method is pretty awkward.Does this
Rails.cache.fetch(['vehicles', vehicle, include_params], version: vehicle.updated_at)
make any sense? I am trying to cache the query based on the different include params. Maybe it is overkill and I could just include everything and cache it that way like:Rails.cache.fetch(['vehicles', vehicle, 'with_includes'], version: vehicle.updated_at) do Vehicle.includes(:vehicle_alerts, :service_notes, :service_intervals).find(params[:id]) end
What do you think?
I hope you can help me out! Thanks in advance!
Code is below:
class ServiceNote < ApplicationRecord
belongs_to :vehicle, touch: true
end
same with (ServiceAlert and ServiceInterval)
class Vehicle < ApplicationRecord
after_save :update_cache
has_many :vehicle_alerts, dependent: :delete_all
has_many :service_notes, dependent: :delete_all
has_many :service_intervals, dependent: :delete_all
def update_cache
Rails.cache.write(['vehicles', vehicle_id], self)
end
def self.find_cached(vehicle_id)
Rails.cache.fetch(['vehicles', vehicle_id]) { find(vehicle_id) }
end
end
vehicles_controller
before_action :set_vehicle, only: [:show]
def show
render json: VehicleSerializer.new(@vehicle, options).serialized_json
end
private
def set_vehicle
vehicle = Vehicle.find_cached(params[:id])
@vehicle = Rails.cache.fetch(['vehicles', vehicle, include_params], version: vehicle.updated_at) do
Vehicle.includes(include_params).find(params[:id])
end
authorize @vehicle
end
vehicle_serializer (with fast_jsonapi gem), (same for vehicle_alerts and service_notes)
has_many :service_intervals do |vehicle, params|
if params[:include] && params[:include].include?(:service_intervals)
vehicle.service_intervals
end
end
Posted in How do I implement nested comments
class Post < ActiveRecord::Base
has_many :comments, as: :commentable, dependent: :destroy
end
class Comment < ActiveRecord::Base
belongs_to :commentable, polymorphic: true
has_many :comment_replies, dependent: :destroy
end
class CommentReply < ActiveRecord::Base
belongs_to :comment, touch: true
end
Sure, it's better with React or Vue as with jQuery this can get pretty messy.
You can use act as votable but it might be an overkill and I am not sure how it works with FE frameworks but shouldn't make a difference. It's just a many to many on User and Comment. If you wanna wanna vote on sth else too then just make it polymorphic like the example above (The comment is polymorphic here but the idea is the same).
There is no magic behind this. You just have to set the foreign keys properly with the request params.
Btw. Chris made a bunch of episodes on this. You should look for them and watch them.
Posted in Analytics with Segment Discussion
Would be great to see more details on how/why to choose client/server/mixed solutions and keep them in sync (I guess for some of the actions only FE can be used, but for others BE would be safer). How to build a bit more robust analytics tracking system with a bunch of analytics events without polluting/slowing down your code. (For instance creating a wrapper class for all analytics events, when to use BG jobs or when to use promises on FE, etc.). So basically a system design for a more complex segment implementation. I think this is also a great opportunity to show how to structure 3rd party code (as there can be many events in different places) and still writing clean ruby code.
Posted in Analytics with Segment Discussion
Great episode Chris! Would be awesome to see some more detailed episodes both for client and server side implementations.
Hey Chris! What would you recommend for pagination? Using some gems or doing it from scratch? Could you also point out some great resources on the topic? Thx
Check Gorails courses on multitenancy or this book: https://leanpub.com/multi-tenancy-rails-2
Posted in ReactJS with Rails
I also did that one (it's the best probably), but it only has smaller apps.
Posted in ReactJS with Rails
Chris, you could also use some react+redux apps that are available on some of the MOOC platforms, like these:
https://www.udemy.com/reactjs-building-production-ready-apps-start-to-finish/
https://www.udemy.com/the-complete-react-web-app-developer-course/
So you could focus on the rails API and how to connect the rails API to react apps instead of explaining react and redux.
Those courses only cost around $10-15, but since your screencast would be free ad for them, I guess they would provide the source code for free.
Thanks Chris! Yeah, I got it after this explanation.
Hey Chris,
Thanks for the great episode. There is a thing though that I don't understand. There can be many tokens for the same user (for instance the user logs in again --> everything is the same except secret signature OR a fake one that has the same payload). According to my understanding, to make sure everything goes fine you should check against the secret signature, but I don't see it in the video. When you create a token and send it back to the user, shouldn't you also save the token or at least the secret signature part of the token? Then when the client sends over the token you can check if the secret signature in the db is the same as in the request.
What you do in the video is only checking the payload part, and I don't really understand how that could work securely.
Posted in has_and_belongs_to_many associations
You shouldn't. You just say user.projects or project.users anywhere.
Posted in has_and_belongs_to_many associations
You only wrote that a user needs to be connected to several projects. If you also wanna connect a project to more than one user then this is the way to go, otherwise you could just say user has_many projects.
+1