-1

I'm building a website where people can buy & watch video online. Paid users will see video, others will see only description & buy now button.

There is an "Order" model, with "LineItems" pointing to videos.

I am using "Video" resource, devise authentication along with CanCan. Those who buy videos have "Customer" role.

When user completes payment, the status of order changes to completed. So I need a method to check if the current user has purchased the video, and display it. While this can be done in Controller, is there a way to do it in CanCan?

  • This question is too general for people on stack overflow to be able to help you, I think. – heartpunk Dec 30 '12 at 11:35
  • Added some more details. I hope these details are good enough for providing an answer (or telling that it is not possible). – Prabhakar Bhat Dec 30 '12 at 13:36
  • It's closer to being a question that can get an answer on here, but I am unable to help you, as I'm not familiar with these plugins. Also, I still don't fully understand the problem. – heartpunk Dec 30 '12 at 20:52

1 Answers1

0

This is how I solved it:

Added a "purchased_videos" method to User model, with following code.

def purchased_videos
  Video.joins(:line_items => {:order => :user}).where(:orders => {:user_id => self, :status => 'successful'})
end

In ability.rb, added the following code:

# Free videos can be watched by anyone
can :watch, Video do |video|
  video.price == 0 || user.purchased_videos.exists?(video.id)
end

Now I can do something like this in Video views:

# Show video if user can watch it
render 'video_partial' if can?(:watch, @video)

# Show preview otherwise
render 'preview_partial' if cannot?(:watch, @video)