Exclude certain users (e.g. `is_admin?`) from ahoy tracking - ahoy

I'm trying to create a rule using ahoy's exclude method to exclude admin users from tracking as suggested here.
But I can't figure out how to get the User object when I only have the controller and request. Any ideas?

From the documentation, in your controller, (or ApplicationController), you can skip the action used to track a visit:
skip_before_action :track_ahoy_visit, if: :your_method_here?

Related

Do I need to use "Marking extra actions for routing" in this REST Django API?

I'm currently having this issue. I have to set up an URL like this:
.../users/<user_id>/user_action/
There are many users and when I pick one user (with user_id), I will be able to see the user's information. Then, go to /user_action, I will be able to POST actions for that specific user.
In this case, do I have to use the Marking extra actions for routing or do I just need to make a separate Viewset for user_action (then link it to users/<user_id>/ in the urls.py)?

How to activate users manually

Django 1.11.2
django-registration-redux==1.6
I'm building an intranet website. And I'd like to control myself whether users are active or not. In Django admin there is such a possibility. But "Active" attribute is set to True automatically when a newly registered user confirms his/her email.
In other words what I'd like to do:
1) Let users register and reset passwords.
2) Admin of the site assigns the new user to a group. Users with the minimum permissions can only view. Special permissions allow edit, delete etc. But the user must be unable even to view anything without approval by the admin.
Now I'm planning to organize can_view permission for every model. The two above conditions will be performed by assigning the user to a group.
Well, this seems to be rather cumbersome. That "Active" attribute in admin is much more elegant. But "Active" is automatically set to True when the user confirms his/her email.
Could you give me a piece of advice here?
While it's tempting, never use is_active to deny permissions. The flag is meant to be equivalent to "deleting a user". That also means the user cannot login (with default authentication backend). So it's not an authorization guard, but an authentication guard.
That said, if you don't grant permissions, users don't have them. So if you implement can_view and set it to guard the relevant models and views, then the user can log in, but cannot see anything you don't want them to (it's convenient for a user to see that she successfully logged in though :) ).
Follow-up question from comments
It's fine to use one global permission that is checked per view. When using class based views, I recommend extending LoginRequiredMixin, tuck a few other goodies in a IntranetCommonMixin and have each view combine it with one of the generic base views. See also my answer here.
The only reason you don't want to do it, is that it's tough to code exceptions on the rule, because the first "object" that says "yes", wins.

Field level permissions using CanCanCan or Pundit

I am currently using Rails 4.1.14 with CanCanCan 1.13.1 and defined granular permissions on model/record level. Admins can manage all articles but users can edit only articles they authored.
To prevent regular users for editing specific fields I make fields visible in rails_admin depending on role.
visible do
bindings[:object].id == bindings[:view].current_user.roles.include? :admin
end
I am also using https://github.com/aasm/aasm gem and created custom actions so user can move records into new states.
But what I really want is to enable field level permissions depending on user's role / record. I can't find any docs on CanCanCan or https://github.com/elabs/pundit pages.
Does anyone have experience with that?
You mean that an admin should be allowed to edit all fields of a record, but an editor is only allowed to change the fields x and y?
Yes, this is possible in pundit, since it integrates with strong parameters (which you should be using anyway). There's also an example in the pundit readme (see: Strong parameters). I simplified example from the readme:
# post_policy.rb
def permitted_attributes
if user.admin?
[:title, :body, :tag_list]
else
[:tag_list]
end
# posts_controller.rb
#post.update_attributes(permitted_attributes(#post))
the permitted_attributes helper in the controller is provided by pundit and automagically calls the permitted_attributes method of the infered policy.

Does Django store information about who has edited and/or created a record, and if so, where?

Django has an authentication and authorization scheme baked in ('django.contrib.auth') as well as modelforms to generate forms for easy input of data into the database.
I'd like to be able to record who created a record, leveraging django.contrib.auth, with the explicit purpose of limiting editing of that same record to just that user and/or people with an "edit" permission. I know that I could use the #user_passes_test decorator to restrict access to editing my record in some fashion, but I don't know what I would compare the request.user.name to in order to determine if the current user originally created that record.
How much of this do I need to roll on my own? Do I need to capture the name author, save it to the model, and then read it - or is there something already in the framework that would do this for me?
And, if I was to attempt to save the author in a field, how would I go about doing that in such a way as to not let the user edit their own credentials?
There are a couple of apps to do something similar, please check https://www.djangopackages.com/grids/g/model-audit/
About the last questions, to prevent the user not to edit its own credentials, you can mark the field with editable=False so it wont appear in the admin or ModelForms.

Tastypie - How can authorize only the owner to edit a resource

I am creating my first API with tastypie and I would like to know how can I set that only owners can edit it's own resources.
Should I?
create a basic authentication like in this example
check if the request.user is the same of the resource.owner
check if the request is a PUT
Is this the best way to fo it?
Thanks!
Yes, what you described is an ok way to do it. Alternatively you could manipulate methods involved in updates: put_detail() and obj_update() but your idea is probably a bit cleaner as after all what you try to do is obviosuly authorization. Therefore the code belongs in the Authorization class not in the methods which actually update the objects as those shouldn't even be called when the user is not authorized to update given resource.
You may also want to look at Tastypie Cookbok which now has a "recipe" for creating "per-user" resoures which also describes how to list resources belonging to a given user only.