clerk-rails 0.1.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/MIT-LICENSE +20 -0
- data/README.md +28 -0
- data/Rakefile +32 -0
- data/app/assets/config/clerk_manifest.js +2 -0
- data/app/assets/javascripts/clerk/application.js +15 -0
- data/app/assets/stylesheets/clerk/application.css +15 -0
- data/app/controllers/clerk/application_controller.rb +15 -0
- data/app/helpers/clerk/application_helper.rb +47 -0
- data/app/jobs/clerk/application_job.rb +4 -0
- data/app/mailers/clerk/application_mailer.rb +6 -0
- data/app/models/clerk/account.rb +107 -0
- data/app/models/clerk/application_record.rb +15 -0
- data/app/models/clerk/client.rb +6 -0
- data/app/models/clerk/plan.rb +6 -0
- data/app/models/clerk/role.rb +83 -0
- data/app/models/concerns/clerk/clerked.rb +66 -0
- data/app/models/concerns/clerk/errors.rb +18 -0
- data/app/views/layouts/clerk/application.html.erb +16 -0
- data/config/routes.rb +3 -0
- data/lib/clerk-rails.rb +30 -0
- data/lib/clerk/engine.rb +60 -0
- data/lib/clerk/version.rb +3 -0
- data/lib/tasks/clerk_tasks.rake +4 -0
- metadata +95 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: 8a7fdb8c57b025d5d0f123c73a89229562f25707d4db95131607f8d2a829001a
|
4
|
+
data.tar.gz: 3d9d1f1bfc333e8097c94e730ba6abd7ed94b3fc697ce9f616c0bc40a017d7cf
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: df4a42eccb6c30f65d354b94141e38c3235879526b4f81ed097d5919487a34d349d1824cbaa8f552af73a9d76fab52ab0a9781f0902ab6a289cbb88a1fb46d26
|
7
|
+
data.tar.gz: c5c25f85ea49646387a75c23b2b02eb26dad51d205847b2753a89415a5ec963cdebf69ed577b885b067d34ebda5b4dcad9f475dcda0f456be2f3c88ced6db624
|
data/MIT-LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright 2018 Colin Sidoti
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,28 @@
|
|
1
|
+
# Clerk
|
2
|
+
Short description and motivation.
|
3
|
+
|
4
|
+
## Usage
|
5
|
+
How to use my plugin.
|
6
|
+
|
7
|
+
## Installation
|
8
|
+
Add this line to your application's Gemfile:
|
9
|
+
|
10
|
+
```ruby
|
11
|
+
gem 'clerk'
|
12
|
+
```
|
13
|
+
|
14
|
+
And then execute:
|
15
|
+
```bash
|
16
|
+
$ bundle
|
17
|
+
```
|
18
|
+
|
19
|
+
Or install it yourself as:
|
20
|
+
```bash
|
21
|
+
$ gem install clerk
|
22
|
+
```
|
23
|
+
|
24
|
+
## Contributing
|
25
|
+
Contribution directions go here.
|
26
|
+
|
27
|
+
## License
|
28
|
+
The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
|
data/Rakefile
ADDED
@@ -0,0 +1,32 @@
|
|
1
|
+
begin
|
2
|
+
require 'bundler/setup'
|
3
|
+
rescue LoadError
|
4
|
+
puts 'You must `gem install bundler` and `bundle install` to run rake tasks'
|
5
|
+
end
|
6
|
+
|
7
|
+
require 'rdoc/task'
|
8
|
+
|
9
|
+
RDoc::Task.new(:rdoc) do |rdoc|
|
10
|
+
rdoc.rdoc_dir = 'rdoc'
|
11
|
+
rdoc.title = 'Clerk'
|
12
|
+
rdoc.options << '--line-numbers'
|
13
|
+
rdoc.rdoc_files.include('README.md')
|
14
|
+
rdoc.rdoc_files.include('lib/**/*.rb')
|
15
|
+
end
|
16
|
+
|
17
|
+
APP_RAKEFILE = File.expand_path("test/dummy/Rakefile", __dir__)
|
18
|
+
load 'rails/tasks/engine.rake'
|
19
|
+
|
20
|
+
load 'rails/tasks/statistics.rake'
|
21
|
+
|
22
|
+
require 'bundler/gem_tasks'
|
23
|
+
|
24
|
+
require 'rake/testtask'
|
25
|
+
|
26
|
+
Rake::TestTask.new(:test) do |t|
|
27
|
+
t.libs << 'test'
|
28
|
+
t.pattern = 'test/**/*_test.rb'
|
29
|
+
t.verbose = false
|
30
|
+
end
|
31
|
+
|
32
|
+
task default: :test
|
@@ -0,0 +1,15 @@
|
|
1
|
+
// This is a manifest file that'll be compiled into application.js, which will include all the files
|
2
|
+
// listed below.
|
3
|
+
//
|
4
|
+
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
|
5
|
+
// or any plugin's vendor/assets/javascripts directory can be referenced here using a relative path.
|
6
|
+
//
|
7
|
+
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
|
8
|
+
// compiled file. JavaScript code in this file should be added after the last require_* statement.
|
9
|
+
//
|
10
|
+
// Read Sprockets README (https://github.com/rails/sprockets#sprockets-directives) for details
|
11
|
+
// about supported directives.
|
12
|
+
//
|
13
|
+
//= require rails-ujs
|
14
|
+
//= require activestorage
|
15
|
+
//= require_tree .
|
@@ -0,0 +1,15 @@
|
|
1
|
+
/*
|
2
|
+
* This is a manifest file that'll be compiled into application.css, which will include all the files
|
3
|
+
* listed below.
|
4
|
+
*
|
5
|
+
* Any CSS and SCSS file within this directory, lib/assets/stylesheets, vendor/assets/stylesheets,
|
6
|
+
* or any plugin's vendor/assets/stylesheets directory can be referenced here using a relative path.
|
7
|
+
*
|
8
|
+
* You're free to add application-wide styles to this file and they'll appear at the bottom of the
|
9
|
+
* compiled file so the styles you add here take precedence over styles defined in any other CSS/SCSS
|
10
|
+
* files in this directory. Styles in this file should be added after the last require_* statement.
|
11
|
+
* It is generally better to create a new file per style scope.
|
12
|
+
*
|
13
|
+
*= require_tree .
|
14
|
+
*= require_self
|
15
|
+
*/
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module Clerk
|
2
|
+
class ApplicationController < ActionController::Base
|
3
|
+
def remote_cookie_accessor
|
4
|
+
# TODO: Only drop cookie if signature verifies
|
5
|
+
# TODO: Hide route entirely if client doesn't use remote cookies
|
6
|
+
cookie_domain = (request.host.include?(".") ? ".#{request.host}" : nil)
|
7
|
+
if params[:value].blank?
|
8
|
+
cookies.delete :clerk_session, domain: cookie_domain
|
9
|
+
else
|
10
|
+
cookies[:clerk_session] = {value: params[:value], domain: cookie_domain, expires: 20.years}
|
11
|
+
end
|
12
|
+
redirect_to params[:redirect]
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
module Clerk
|
2
|
+
module ApplicationHelper
|
3
|
+
def current_account
|
4
|
+
return @clerk_current_account if defined?(@clerk_current_account)
|
5
|
+
@clerk_current_account ||= begin
|
6
|
+
if Clerk.config.session_mode==:database_session
|
7
|
+
raise "TODO"
|
8
|
+
elsif Clerk.config.session_mode==:cookie_session
|
9
|
+
Clerk::Account.find_by(id: current_account_id)
|
10
|
+
end
|
11
|
+
rescue => e
|
12
|
+
nil
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
def current_account_id
|
17
|
+
return @clerk_current_account_id if defined?(@clerk_current_account_id)
|
18
|
+
@clerk_current_account_id ||= begin
|
19
|
+
if Clerk.config.session_mode==:database_session
|
20
|
+
current_account.id
|
21
|
+
elsif Clerk.config.session_mode==:cookie_session
|
22
|
+
session_cookie = JSON.parse(cookies[:clerk_session])
|
23
|
+
nil if session_cookie.nil?
|
24
|
+
JSON.parse(session_cookie["d"])["k"]
|
25
|
+
end
|
26
|
+
rescue => e
|
27
|
+
nil
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
def clerk_sign_out_path
|
32
|
+
"#{Clerk.config.accounts_url}/sign_out"
|
33
|
+
end
|
34
|
+
|
35
|
+
def clerk_sign_in_path
|
36
|
+
"#{Clerk.config.accounts_url}"
|
37
|
+
end
|
38
|
+
|
39
|
+
def clerk_sign_up_path
|
40
|
+
"#{Clerk.config.accounts_url}/sign_up"
|
41
|
+
end
|
42
|
+
|
43
|
+
def clerk_add_card_path(account_id:, redirect_path:)
|
44
|
+
"#{Clerk.config.accounts_url}/add_card?account_id=#{account_id}&redirect_path=#{redirect_path}"
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
@@ -0,0 +1,107 @@
|
|
1
|
+
module Clerk
|
2
|
+
class Account < Clerk::ApplicationRecord
|
3
|
+
self.table_name = self.clerk_table_name("accounts")
|
4
|
+
self.primary_key = 'id'
|
5
|
+
|
6
|
+
has_many :roles, class_name: "Clerk::Role"
|
7
|
+
|
8
|
+
def add_clerk_role(role_type_symbol, instance = nil)
|
9
|
+
json = { }
|
10
|
+
json[:name] = role_type_symbol.to_s
|
11
|
+
json[:account_id] = self.id
|
12
|
+
|
13
|
+
if not instance.nil?
|
14
|
+
json[:scope_class] = instance.class.name
|
15
|
+
json[:scope_id] = instance.id
|
16
|
+
end
|
17
|
+
|
18
|
+
server_url = "#{ENV['CLERK_ACCOUNTS_URL']}/roles"
|
19
|
+
HTTP.auth("Bearer #{ENV['CLERK_SECRET_KEY']}").post(server_url, :json => json)
|
20
|
+
end
|
21
|
+
|
22
|
+
def has_role?(role, scope)
|
23
|
+
roles.where(name: role, scope_class: scope.class.name, scope_id: scope.id).exists?
|
24
|
+
end
|
25
|
+
|
26
|
+
def roles_for(scope)
|
27
|
+
roles.where(scope_class: scope.class.name, scope_id: scope.id).pluck(:name).map(&:to_sym)
|
28
|
+
end
|
29
|
+
|
30
|
+
def has_permission?(permission, scope)
|
31
|
+
has_role?(scope.class.roles_with_permission(permission), scope)
|
32
|
+
end
|
33
|
+
|
34
|
+
def permissions_for(scope)
|
35
|
+
permissions = Set.new
|
36
|
+
|
37
|
+
roles = roles_for(scope)
|
38
|
+
roles.each do |role|
|
39
|
+
role_permissions = scope.class.clerk_permissions_map[role]
|
40
|
+
|
41
|
+
unless role_permissions.nil?
|
42
|
+
permissions.merge(role_permissions)
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
return permissions.to_a
|
47
|
+
end
|
48
|
+
|
49
|
+
private
|
50
|
+
|
51
|
+
def method_missing(method_name, *args, &block)
|
52
|
+
# Rails lazy loads modules. If an object hasn't been loaded yet, any inverse association
|
53
|
+
# will not be here yet. Just in case, load the constant here and re-call the method to
|
54
|
+
# before raising an error
|
55
|
+
@miss_test ||= {}
|
56
|
+
if @miss_test.has_key? method_name.to_sym
|
57
|
+
super
|
58
|
+
else
|
59
|
+
@miss_test[method_name.to_sym] = true
|
60
|
+
scope_class = method_name.to_s.classify.constantize
|
61
|
+
send(method_name, *args, &block)
|
62
|
+
end
|
63
|
+
rescue => e
|
64
|
+
super
|
65
|
+
end
|
66
|
+
|
67
|
+
class RolesWrapper
|
68
|
+
def initialize(instance, target)
|
69
|
+
@instance = instance
|
70
|
+
@target_class = target.to_s.classify.constantize
|
71
|
+
end
|
72
|
+
|
73
|
+
def with(role: nil, permission: nil)
|
74
|
+
if (role.nil? and permission.nil?) or (not role.nil? and not permission.nil?)
|
75
|
+
raise ArgumentError.new("Invalid argument, must supply either a role or permission")
|
76
|
+
end
|
77
|
+
|
78
|
+
if not role.nil?
|
79
|
+
return @target_class.where(
|
80
|
+
id: @instance.roles.where(scope_class: @target_class.name, name: role).pluck(:scope_id)
|
81
|
+
)
|
82
|
+
end
|
83
|
+
|
84
|
+
if not permission.nil?
|
85
|
+
roles = @target_class.roles_with_permission(permission)
|
86
|
+
return @target_class.where(
|
87
|
+
id: @instance.roles.where(scope_class: @target_class.name, name: roles).pluck(:scope_id)
|
88
|
+
)
|
89
|
+
end
|
90
|
+
end
|
91
|
+
|
92
|
+
def no_with
|
93
|
+
@target_class.where(
|
94
|
+
id: @instance.roles.where(scope_class: @target_class.name).pluck(:scope_id)
|
95
|
+
)
|
96
|
+
end
|
97
|
+
|
98
|
+
def method_missing(m, *args, &block)
|
99
|
+
no_with.send(m, *args, &block)
|
100
|
+
end
|
101
|
+
|
102
|
+
def inspect
|
103
|
+
no_with.inspect
|
104
|
+
end
|
105
|
+
end
|
106
|
+
end
|
107
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module Clerk
|
2
|
+
class ApplicationRecord < ActiveRecord::Base
|
3
|
+
self.abstract_class = true
|
4
|
+
establish_connection Clerk.database_connection_url
|
5
|
+
def self.clerk_table_name(table_name)
|
6
|
+
version = Clerk::VERSION.split(".").map{|x| x.rjust(2, '0')}.join
|
7
|
+
"client.#{table_name}_#{version}_#{Clerk.config.secret_key}"
|
8
|
+
end
|
9
|
+
|
10
|
+
def self.clerk_table_name_nc(table_name)
|
11
|
+
version = Clerk::VERSION.split(".").map{|x| x.rjust(2, '0')}.join
|
12
|
+
"#{table_name}_#{version}_#{Clerk.config.secret_key}"
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,83 @@
|
|
1
|
+
module Clerk
|
2
|
+
class Role < Clerk::ApplicationRecord
|
3
|
+
self.table_name = self.clerk_table_name("roles")
|
4
|
+
self.primary_key = 'id'
|
5
|
+
|
6
|
+
belongs_to :account, class_name: "Clerk::Account"
|
7
|
+
|
8
|
+
def self._insert_record(values)
|
9
|
+
server_url = "#{ENV['CLERK_ACCOUNTS_URL']}/roles"
|
10
|
+
begin
|
11
|
+
response = HTTP.auth("Bearer #{ENV['CLERK_SECRET_KEY']}").post(server_url, :json => values)
|
12
|
+
id = JSON.parse(response.body)["id"]
|
13
|
+
rescue
|
14
|
+
raise Clerk::Errors::ClerkServerError.new("Failed to save the role", self)
|
15
|
+
end
|
16
|
+
|
17
|
+
if response.status.code != 200 or id.nil?
|
18
|
+
raise Clerk::Errors::ClerkServerError.new("Failed to save the role", self)
|
19
|
+
end
|
20
|
+
|
21
|
+
return id
|
22
|
+
end
|
23
|
+
|
24
|
+
def self._update_record(values, constraints)
|
25
|
+
update_id = constraints["id"]
|
26
|
+
if update_id.nil?
|
27
|
+
raise ActiveRecord::RecordNotFound.new("Must pass an id to update a role", self)
|
28
|
+
end
|
29
|
+
|
30
|
+
server_url = "#{ENV['CLERK_ACCOUNTS_URL']}/roles/#{update_id}"
|
31
|
+
begin
|
32
|
+
response = HTTP.auth("Bearer #{ENV['CLERK_SECRET_KEY']}").patch(server_url, :json => values.merge!(constraints))
|
33
|
+
rescue
|
34
|
+
raise Clerk::Errors::ClerkServerError.new("Failed to update the role", self)
|
35
|
+
end
|
36
|
+
|
37
|
+
if response.status.code != 200
|
38
|
+
raise Clerk::Errors::ClerkServerError.new("Failed to update the role", self)
|
39
|
+
end
|
40
|
+
|
41
|
+
# overriden function returns the number of rows affected
|
42
|
+
return 1
|
43
|
+
end
|
44
|
+
|
45
|
+
def self._delete_record(constraints)
|
46
|
+
delete_id = constraints["id"]
|
47
|
+
if delete_id.nil?
|
48
|
+
raise ActiveRecord::RecordNotFound.new("Must pass an id to delete a role", self)
|
49
|
+
end
|
50
|
+
|
51
|
+
server_url = "#{ENV['CLERK_ACCOUNTS_URL']}/roles/#{delete_id}"
|
52
|
+
|
53
|
+
begin
|
54
|
+
response = HTTP.auth("Bearer #{ENV['CLERK_SECRET_KEY']}").delete(server_url)
|
55
|
+
rescue
|
56
|
+
raise Clerk::Errors::ClerkServerError.new("Failed to delete the role", self)
|
57
|
+
end
|
58
|
+
|
59
|
+
|
60
|
+
if response.status.code != 200
|
61
|
+
raise Clerk::Errors::ClerkServerError.new("Failed to delete the role", self)
|
62
|
+
end
|
63
|
+
|
64
|
+
# overriden function returns the number of rows affected
|
65
|
+
return 1
|
66
|
+
end
|
67
|
+
|
68
|
+
|
69
|
+
# disable bulk calls
|
70
|
+
def self.update_all(updates)
|
71
|
+
raise Clerk::Errors::MethodDisabled.new("update_all is disabled for Clerk::Role")
|
72
|
+
end
|
73
|
+
|
74
|
+
def self.delete_all
|
75
|
+
raise Clerk::Errors::MethodDisabled.new("delete_all is disabled for Clerk::Role")
|
76
|
+
end
|
77
|
+
|
78
|
+
def self.destroy_all
|
79
|
+
raise Clerk::Errors::MethodDisabled.new("destroy_all is disabled for Clerk::Role")
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
83
|
+
|
@@ -0,0 +1,66 @@
|
|
1
|
+
module Clerk
|
2
|
+
module Clerked
|
3
|
+
extend ActiveSupport::Concern
|
4
|
+
|
5
|
+
included do
|
6
|
+
@@clerk_permissions_map = {}
|
7
|
+
@@clerk_roles_map = {}
|
8
|
+
|
9
|
+
has_many :clerk_roles, clerk_roles_scope, class_name: "Clerk::Role", foreign_key: :scope_id
|
10
|
+
|
11
|
+
has_many :accounts, through: :clerk_roles, source: :account do
|
12
|
+
|
13
|
+
def with(role: nil, permission: nil)
|
14
|
+
if (role.nil? and permission.nil?) or (not role.nil? and not permission.nil?)
|
15
|
+
raise ArgumentError.new("Invalid argument, must supply either a role or permission")
|
16
|
+
end
|
17
|
+
|
18
|
+
if not role.nil?
|
19
|
+
return where(Clerk::Role.table_name=>{name: role})
|
20
|
+
elsif not permission.nil?
|
21
|
+
all_roles = self.proxy_association.owner.class.roles_with_permission(permission)
|
22
|
+
return where(Clerk::Role.table_name=>{name: all_roles})
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
def has_role?(role, account)
|
30
|
+
account.has_role?(role, self)
|
31
|
+
end
|
32
|
+
|
33
|
+
def roles_for(account)
|
34
|
+
account.roles_for(self)
|
35
|
+
end
|
36
|
+
|
37
|
+
class_methods do
|
38
|
+
def clerk_permissions_map
|
39
|
+
@@clerk_permissions_map
|
40
|
+
end
|
41
|
+
|
42
|
+
def clerk_roles_map
|
43
|
+
@@clerk_roles_map
|
44
|
+
end
|
45
|
+
|
46
|
+
def roles_with_permission(permission)
|
47
|
+
@@clerk_roles_map[permission] ||= begin
|
48
|
+
roles_with_permission = []
|
49
|
+
|
50
|
+
clerk_permissions_map.keys.each do |key|
|
51
|
+
if clerk_permissions_map[key].include?(permission)
|
52
|
+
roles_with_permission << key
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
roles_with_permission
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
def clerk_roles_scope
|
61
|
+
class_name = self.name
|
62
|
+
->{ where(scope_class: class_name) }
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
module Clerk
|
2
|
+
module Errors
|
3
|
+
class ClerkError < StandardError; end
|
4
|
+
|
5
|
+
class ClerkServerError < ClerkError
|
6
|
+
def initialize(message = nil, model = nil)
|
7
|
+
@model = model
|
8
|
+
super(message)
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
class MethodDisabled < ClerkError
|
13
|
+
def initialize(message = nil)
|
14
|
+
super(message)
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
<!DOCTYPE html>
|
2
|
+
<html>
|
3
|
+
<head>
|
4
|
+
<title>Clerk</title>
|
5
|
+
<%= csrf_meta_tags %>
|
6
|
+
<%= csp_meta_tag %>
|
7
|
+
|
8
|
+
<%= stylesheet_link_tag "clerk/application", media: "all" %>
|
9
|
+
<%= javascript_include_tag "clerk/application" %>
|
10
|
+
</head>
|
11
|
+
<body>
|
12
|
+
|
13
|
+
<%= yield %>
|
14
|
+
|
15
|
+
</body>
|
16
|
+
</html>
|
data/config/routes.rb
ADDED
data/lib/clerk-rails.rb
ADDED
@@ -0,0 +1,30 @@
|
|
1
|
+
require "clerk/engine"
|
2
|
+
|
3
|
+
module Clerk
|
4
|
+
class << self
|
5
|
+
attr_reader :config
|
6
|
+
|
7
|
+
def configure
|
8
|
+
@config = Configuration.new
|
9
|
+
yield config
|
10
|
+
if Rails.env.development?
|
11
|
+
config.environment = :development
|
12
|
+
config.session_mode = :cookie_session
|
13
|
+
config.cookie_host = nil
|
14
|
+
else
|
15
|
+
client = Clerk::Client.first
|
16
|
+
config.environment = client.environment.to_sym
|
17
|
+
config.session_mode = client.session_mode.to_sym
|
18
|
+
config.cookie_host = client.cookie_host
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
def database_connection_url
|
23
|
+
@database_connection_url ||= "#{Clerk.config.database_url.dup.insert(11,"#{Clerk.config.secret_key}@")}/clerk?prepared_statements=false"
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
class Configuration
|
28
|
+
attr_accessor :accounts_url, :database_url, :secret_key, :public_key, :environment, :session_mode, :last_account, :cookie_host
|
29
|
+
end
|
30
|
+
end
|
data/lib/clerk/engine.rb
ADDED
@@ -0,0 +1,60 @@
|
|
1
|
+
module Clerk
|
2
|
+
class Engine < ::Rails::Engine
|
3
|
+
initializer "clerk.load_helpers" do |app|
|
4
|
+
::ActionController::Base.send :include, Clerk::ApplicationHelper
|
5
|
+
::ActiveRecord::Base.class_eval do
|
6
|
+
|
7
|
+
def self.clerk(association_name, permissions: [])
|
8
|
+
plural_role = association_name.to_s.pluralize.to_sym
|
9
|
+
singular_role = association_name.to_s.singularize.to_sym
|
10
|
+
|
11
|
+
roles_association = :"clerk_roles_#{association_name}"
|
12
|
+
|
13
|
+
remote_class = self.name
|
14
|
+
|
15
|
+
unless self.respond_to? :clerk_roles
|
16
|
+
self.class_eval do
|
17
|
+
include Clerk::Clerked
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
has_many roles_association,
|
22
|
+
->{ where(scope_class: remote_class, name: singular_role) },
|
23
|
+
class_name: "Clerk::Role",
|
24
|
+
foreign_key: :scope_id
|
25
|
+
|
26
|
+
plural_role = association_name.to_s.pluralize.to_sym
|
27
|
+
singular_role = association_name.to_s.singularize.to_sym
|
28
|
+
|
29
|
+
account_accessor = self.name.underscore.pluralize.to_sym
|
30
|
+
|
31
|
+
# Add clerk permissions to `self` the associated class
|
32
|
+
self.clerk_permissions_map[singular_role] = permissions
|
33
|
+
|
34
|
+
# Add magic methods to Clerk::Acount
|
35
|
+
Clerk::Account.class_eval do
|
36
|
+
define_method account_accessor do
|
37
|
+
self.class::RolesWrapper.new(self, account_accessor)
|
38
|
+
end
|
39
|
+
|
40
|
+
define_method :"is_#{singular_role}?" do |*args|
|
41
|
+
has_role?(singular_role, *args)
|
42
|
+
end
|
43
|
+
|
44
|
+
permissions.each do |permission|
|
45
|
+
define_method :"can_#{permission}?" do |*args|
|
46
|
+
has_permission?(permission, *args)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
[
|
52
|
+
association_name.to_sym,
|
53
|
+
through: roles_association,
|
54
|
+
source: :account
|
55
|
+
]
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
metadata
ADDED
@@ -0,0 +1,95 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: clerk-rails
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.2
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Clerk
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2018-12-09 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: rails
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: 5.2.0
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: 5.2.0
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: pg
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - ">="
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '0'
|
34
|
+
type: :runtime
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - ">="
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '0'
|
41
|
+
description: Clerk is the easiest way to manage accounts.
|
42
|
+
email:
|
43
|
+
- bsidoti@gmail.com
|
44
|
+
executables: []
|
45
|
+
extensions: []
|
46
|
+
extra_rdoc_files: []
|
47
|
+
files:
|
48
|
+
- MIT-LICENSE
|
49
|
+
- README.md
|
50
|
+
- Rakefile
|
51
|
+
- app/assets/config/clerk_manifest.js
|
52
|
+
- app/assets/javascripts/clerk/application.js
|
53
|
+
- app/assets/stylesheets/clerk/application.css
|
54
|
+
- app/controllers/clerk/application_controller.rb
|
55
|
+
- app/helpers/clerk/application_helper.rb
|
56
|
+
- app/jobs/clerk/application_job.rb
|
57
|
+
- app/mailers/clerk/application_mailer.rb
|
58
|
+
- app/models/clerk/account.rb
|
59
|
+
- app/models/clerk/application_record.rb
|
60
|
+
- app/models/clerk/client.rb
|
61
|
+
- app/models/clerk/plan.rb
|
62
|
+
- app/models/clerk/role.rb
|
63
|
+
- app/models/concerns/clerk/clerked.rb
|
64
|
+
- app/models/concerns/clerk/errors.rb
|
65
|
+
- app/views/layouts/clerk/application.html.erb
|
66
|
+
- config/routes.rb
|
67
|
+
- lib/clerk-rails.rb
|
68
|
+
- lib/clerk/engine.rb
|
69
|
+
- lib/clerk/version.rb
|
70
|
+
- lib/tasks/clerk_tasks.rake
|
71
|
+
homepage:
|
72
|
+
licenses:
|
73
|
+
- MIT
|
74
|
+
metadata: {}
|
75
|
+
post_install_message:
|
76
|
+
rdoc_options: []
|
77
|
+
require_paths:
|
78
|
+
- lib
|
79
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
80
|
+
requirements:
|
81
|
+
- - ">="
|
82
|
+
- !ruby/object:Gem::Version
|
83
|
+
version: '0'
|
84
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
85
|
+
requirements:
|
86
|
+
- - ">="
|
87
|
+
- !ruby/object:Gem::Version
|
88
|
+
version: '0'
|
89
|
+
requirements: []
|
90
|
+
rubyforge_project:
|
91
|
+
rubygems_version: 2.7.8
|
92
|
+
signing_key:
|
93
|
+
specification_version: 4
|
94
|
+
summary: Rails Engine for Clerk
|
95
|
+
test_files: []
|