godmin 0.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +24 -0
- data/.hound.yml +2 -0
- data/.rubocop.yml +7 -0
- data/.travis.yml +7 -0
- data/Gemfile +11 -0
- data/MIT-LICENSE +20 -0
- data/README.md +523 -0
- data/Rakefile +34 -0
- data/app/assets/images/godmin/.keep +0 -0
- data/app/assets/javascripts/godmin/application.js +19 -0
- data/app/assets/javascripts/godmin/batch_actions.js +42 -0
- data/app/assets/javascripts/godmin/navigation.js +9 -0
- data/app/assets/javascripts/godmin/select_tags.js +8 -0
- data/app/assets/stylesheets/godmin/application.css.scss +62 -0
- data/app/views/godmin/application/welcome.html.erb +65 -0
- data/app/views/godmin/resource/_actions.html.erb +10 -0
- data/app/views/godmin/resource/_batch_actions.html.erb +12 -0
- data/app/views/godmin/resource/_breadcrumb.html.erb +21 -0
- data/app/views/godmin/resource/_errors.html.erb +9 -0
- data/app/views/godmin/resource/_filters.html.erb +23 -0
- data/app/views/godmin/resource/_form.html.erb +12 -0
- data/app/views/godmin/resource/_pagination.html.erb +6 -0
- data/app/views/godmin/resource/_scopes.html.erb +11 -0
- data/app/views/godmin/resource/_table.html.erb +36 -0
- data/app/views/godmin/resource/columns/_actions.html.erb +11 -0
- data/app/views/godmin/resource/edit.html.erb +5 -0
- data/app/views/godmin/resource/index.html.erb +17 -0
- data/app/views/godmin/resource/new.html.erb +5 -0
- data/app/views/godmin/resource/show.html.erb +1 -0
- data/app/views/godmin/sessions/new.html.erb +9 -0
- data/app/views/godmin/shared/_navigation.html.erb +29 -0
- data/app/views/kaminari/_first_page.html.erb +3 -0
- data/app/views/kaminari/_gap.html.erb +3 -0
- data/app/views/kaminari/_last_page.html.erb +3 -0
- data/app/views/kaminari/_next_page.html.erb +3 -0
- data/app/views/kaminari/_page.html.erb +3 -0
- data/app/views/kaminari/_paginator.html.erb +15 -0
- data/app/views/kaminari/_prev_page.html.erb +3 -0
- data/app/views/layouts/godmin/_content.html.erb +13 -0
- data/app/views/layouts/godmin/_layout.html.erb +13 -0
- data/app/views/layouts/godmin/application.html.erb +17 -0
- data/app/views/layouts/godmin/login.html.erb +18 -0
- data/bin/rails +8 -0
- data/config/locales/en.yml +41 -0
- data/config/locales/sv.yml +41 -0
- data/config/routes.rb +2 -0
- data/godmin.gemspec +32 -0
- data/lib/generators/godmin/authentication/authentication_generator.rb +61 -0
- data/lib/generators/godmin/install/install_generator.rb +34 -0
- data/lib/generators/godmin/policy/policy_generator.rb +29 -0
- data/lib/generators/godmin/resource/resource_generator.rb +56 -0
- data/lib/godmin.rb +24 -0
- data/lib/godmin/application.rb +37 -0
- data/lib/godmin/authentication.rb +35 -0
- data/lib/godmin/authentication/sessions.rb +45 -0
- data/lib/godmin/authentication/user.rb +27 -0
- data/lib/godmin/authorization.rb +30 -0
- data/lib/godmin/authorization/policy.rb +40 -0
- data/lib/godmin/authorization/policy_finder.rb +28 -0
- data/lib/godmin/engine.rb +4 -0
- data/lib/godmin/generators/base.rb +13 -0
- data/lib/godmin/helpers/application.rb +6 -0
- data/lib/godmin/helpers/batch_actions.rb +17 -0
- data/lib/godmin/helpers/filters.rb +108 -0
- data/lib/godmin/helpers/tables.rb +41 -0
- data/lib/godmin/helpers/translations.rb +19 -0
- data/lib/godmin/rails.rb +36 -0
- data/lib/godmin/resolver.rb +46 -0
- data/lib/godmin/resource.rb +126 -0
- data/lib/godmin/resource/batch_actions.rb +45 -0
- data/lib/godmin/resource/filters.rb +41 -0
- data/lib/godmin/resource/ordering.rb +25 -0
- data/lib/godmin/resource/pagination.rb +11 -0
- data/lib/godmin/resource/scopes.rb +49 -0
- data/lib/godmin/version.rb +3 -0
- data/lib/tasks/godmin_tasks.rake +4 -0
- data/test/dummy/README.rdoc +28 -0
- data/test/dummy/Rakefile +6 -0
- data/test/dummy/app/assets/images/.keep +0 -0
- data/test/dummy/app/assets/javascripts/application.js +13 -0
- data/test/dummy/app/assets/stylesheets/application.css +13 -0
- data/test/dummy/app/controllers/application_controller.rb +5 -0
- data/test/dummy/app/controllers/concerns/.keep +0 -0
- data/test/dummy/app/helpers/application_helper.rb +2 -0
- data/test/dummy/app/mailers/.keep +0 -0
- data/test/dummy/app/models/.keep +0 -0
- data/test/dummy/app/models/concerns/.keep +0 -0
- data/test/dummy/app/views/layouts/application.html.erb +14 -0
- data/test/dummy/bin/bundle +3 -0
- data/test/dummy/bin/rails +4 -0
- data/test/dummy/bin/rake +4 -0
- data/test/dummy/config.ru +4 -0
- data/test/dummy/config/application.rb +23 -0
- data/test/dummy/config/boot.rb +5 -0
- data/test/dummy/config/database.yml +25 -0
- data/test/dummy/config/environment.rb +5 -0
- data/test/dummy/config/environments/development.rb +29 -0
- data/test/dummy/config/environments/production.rb +80 -0
- data/test/dummy/config/environments/test.rb +36 -0
- data/test/dummy/config/initializers/backtrace_silencers.rb +7 -0
- data/test/dummy/config/initializers/filter_parameter_logging.rb +4 -0
- data/test/dummy/config/initializers/inflections.rb +16 -0
- data/test/dummy/config/initializers/mime_types.rb +5 -0
- data/test/dummy/config/initializers/secret_token.rb +12 -0
- data/test/dummy/config/initializers/session_store.rb +3 -0
- data/test/dummy/config/initializers/wrap_parameters.rb +14 -0
- data/test/dummy/config/locales/en.yml +23 -0
- data/test/dummy/config/routes.rb +4 -0
- data/test/dummy/db/test.sqlite3 +0 -0
- data/test/dummy/lib/assets/.keep +0 -0
- data/test/dummy/public/404.html +58 -0
- data/test/dummy/public/422.html +58 -0
- data/test/dummy/public/500.html +57 -0
- data/test/dummy/public/favicon.ico +0 -0
- data/test/godmin_test.rb +7 -0
- data/test/integration/navigation_test.rb +10 -0
- data/test/lib/godmin/policy_finder_test.rb +30 -0
- data/test/lib/godmin/resolver_test.rb +31 -0
- data/test/test_helper.rb +21 -0
- data/vendor/assets/images/godmin/chosen-sprite.png +0 -0
- data/vendor/assets/images/godmin/chosen-sprite@2x.png +0 -0
- data/vendor/assets/javascripts/.keep +0 -0
- data/vendor/assets/stylesheets/.keep +0 -0
- metadata +361 -0
data/lib/godmin.rb
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
require "bootstrap-sass"
|
|
2
|
+
require "kaminari"
|
|
3
|
+
require "select2-rails"
|
|
4
|
+
require "simple_form"
|
|
5
|
+
require "godmin/application"
|
|
6
|
+
require "godmin/authentication"
|
|
7
|
+
require "godmin/authorization"
|
|
8
|
+
require "godmin/engine"
|
|
9
|
+
require "godmin/rails"
|
|
10
|
+
require "godmin/resolver"
|
|
11
|
+
require "godmin/resource"
|
|
12
|
+
require "godmin/version"
|
|
13
|
+
|
|
14
|
+
module Godmin
|
|
15
|
+
mattr_accessor :namespace
|
|
16
|
+
self.namespace = nil
|
|
17
|
+
|
|
18
|
+
mattr_accessor :resources
|
|
19
|
+
self.resources = []
|
|
20
|
+
|
|
21
|
+
def self.configure
|
|
22
|
+
yield self
|
|
23
|
+
end
|
|
24
|
+
end
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
require "godmin/helpers/application"
|
|
2
|
+
require "godmin/helpers/translations"
|
|
3
|
+
|
|
4
|
+
module Godmin
|
|
5
|
+
module Application
|
|
6
|
+
extend ActiveSupport::Concern
|
|
7
|
+
|
|
8
|
+
included do
|
|
9
|
+
helper Godmin::Helpers::Application
|
|
10
|
+
helper Godmin::Helpers::Translations
|
|
11
|
+
|
|
12
|
+
helper_method :authentication_enabled?
|
|
13
|
+
helper_method :authorization_enabled?
|
|
14
|
+
|
|
15
|
+
before_action :append_view_paths
|
|
16
|
+
|
|
17
|
+
layout "godmin/application"
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
def welcome; end
|
|
21
|
+
|
|
22
|
+
private
|
|
23
|
+
|
|
24
|
+
def append_view_paths
|
|
25
|
+
append_view_path Godmin::EngineResolver.new(controller_name)
|
|
26
|
+
append_view_path Godmin::GodminResolver.new(controller_name)
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
def authentication_enabled?
|
|
30
|
+
singleton_class.include?(Godmin::Authentication)
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
def authorization_enabled?
|
|
34
|
+
singleton_class.include?(Godmin::Authorization)
|
|
35
|
+
end
|
|
36
|
+
end
|
|
37
|
+
end
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
require "godmin/authentication/sessions"
|
|
2
|
+
require "godmin/authentication/user"
|
|
3
|
+
|
|
4
|
+
module Godmin
|
|
5
|
+
module Authentication
|
|
6
|
+
extend ActiveSupport::Concern
|
|
7
|
+
|
|
8
|
+
included do
|
|
9
|
+
before_action :authenticate_admin_user
|
|
10
|
+
|
|
11
|
+
helper_method :admin_user
|
|
12
|
+
helper_method :admin_user_signed_in?
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
def authenticate_admin_user
|
|
16
|
+
unless admin_user_signed_in? || controller_name == "sessions"
|
|
17
|
+
redirect_to new_session_path, alert: "Authentication needed"
|
|
18
|
+
end
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def admin_user_class
|
|
22
|
+
raise NotImplementedError, "Must define the admin user class"
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
def admin_user
|
|
26
|
+
if session[:admin_user_id]
|
|
27
|
+
@admin_user ||= admin_user_class.find_by(id: session[:admin_user_id])
|
|
28
|
+
end
|
|
29
|
+
end
|
|
30
|
+
|
|
31
|
+
def admin_user_signed_in?
|
|
32
|
+
admin_user.present?
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
end
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
module Godmin
|
|
2
|
+
module Authentication
|
|
3
|
+
module Sessions
|
|
4
|
+
extend ActiveSupport::Concern
|
|
5
|
+
|
|
6
|
+
included do
|
|
7
|
+
layout "godmin/login"
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
def new
|
|
11
|
+
@admin_user = admin_user_class.new
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
def create
|
|
15
|
+
@admin_user = admin_user_class.find_by_login(admin_user_login)
|
|
16
|
+
|
|
17
|
+
if @admin_user && @admin_user.authenticate(admin_user_params[:password])
|
|
18
|
+
session[:admin_user_id] = @admin_user.id
|
|
19
|
+
redirect_to root_path, notice: t("godmin.sessions.signed_in")
|
|
20
|
+
else
|
|
21
|
+
redirect_to new_session_path, alert: t("godmin.sessions.failed_sign_in")
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
def destroy
|
|
26
|
+
session[:admin_user_id] = nil
|
|
27
|
+
redirect_to new_session_path, notice: t("godmin.sessions.signed_out")
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
private
|
|
31
|
+
|
|
32
|
+
def admin_user_login
|
|
33
|
+
admin_user_params[admin_user_class.login_column]
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
def admin_user_params
|
|
37
|
+
params.require(:admin_user).permit(
|
|
38
|
+
admin_user_class.login_column,
|
|
39
|
+
:password,
|
|
40
|
+
:password_confirm
|
|
41
|
+
)
|
|
42
|
+
end
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
end
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
module Godmin
|
|
2
|
+
module Authentication
|
|
3
|
+
module User
|
|
4
|
+
extend ActiveSupport::Concern
|
|
5
|
+
|
|
6
|
+
included do
|
|
7
|
+
has_secure_password
|
|
8
|
+
|
|
9
|
+
validates :password, length: { minimum: 8 }, allow_nil: true
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def login
|
|
13
|
+
send(self.class.login_column)
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
module ClassMethods
|
|
17
|
+
def find_by_login(login)
|
|
18
|
+
find_by(login_column => login)
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def login_column
|
|
22
|
+
raise NotImplementedError, "Must define the admin user login column"
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
end
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
require "godmin/authorization/policy"
|
|
2
|
+
require "godmin/authorization/policy_finder"
|
|
3
|
+
|
|
4
|
+
module Godmin
|
|
5
|
+
module Authorization
|
|
6
|
+
extend ActiveSupport::Concern
|
|
7
|
+
|
|
8
|
+
included do
|
|
9
|
+
helper_method :policy
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def authorize(record)
|
|
13
|
+
policy = policy(record)
|
|
14
|
+
|
|
15
|
+
unless policy.public_send(action_name + "?")
|
|
16
|
+
raise NotAuthorizedError
|
|
17
|
+
end
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
def policy(record)
|
|
21
|
+
policies[record] ||= PolicyFinder.find(record).constantize.new(admin_user, record)
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def policies
|
|
25
|
+
@_policies ||= {}
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
class NotAuthorizedError < StandardError; end
|
|
29
|
+
end
|
|
30
|
+
end
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
module Godmin
|
|
2
|
+
module Authorization
|
|
3
|
+
class Policy
|
|
4
|
+
attr_reader :user, :record
|
|
5
|
+
|
|
6
|
+
def initialize(user, record)
|
|
7
|
+
@user = user
|
|
8
|
+
@record = record
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def index?
|
|
12
|
+
false
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
def show?
|
|
16
|
+
false
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
def new?
|
|
20
|
+
create?
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def edit?
|
|
24
|
+
update?
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
def create?
|
|
28
|
+
false
|
|
29
|
+
end
|
|
30
|
+
|
|
31
|
+
def update?
|
|
32
|
+
false
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
def destroy?
|
|
36
|
+
false
|
|
37
|
+
end
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
end
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
module Godmin
|
|
2
|
+
module Authorization
|
|
3
|
+
class PolicyFinder
|
|
4
|
+
class << self
|
|
5
|
+
def find(object)
|
|
6
|
+
klass =
|
|
7
|
+
if object.respond_to?(:model_name)
|
|
8
|
+
object.model_name
|
|
9
|
+
elsif object.class.respond_to?(:model_name)
|
|
10
|
+
object.class.model_name
|
|
11
|
+
elsif object.is_a?(Class)
|
|
12
|
+
object
|
|
13
|
+
elsif object.is_a?(Symbol)
|
|
14
|
+
object.to_s.classify
|
|
15
|
+
else
|
|
16
|
+
object.class
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
if Godmin.namespace
|
|
20
|
+
"#{Godmin.namespace.classify}::#{klass}Policy"
|
|
21
|
+
else
|
|
22
|
+
"#{klass}Policy"
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
end
|
|
28
|
+
end
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
module Godmin
|
|
2
|
+
module Helpers
|
|
3
|
+
module BatchActions
|
|
4
|
+
def batch_action_link(name, options)
|
|
5
|
+
if (options[:only].nil? && options[:except].nil?) ||
|
|
6
|
+
(options[:only] && options[:only].include?(params[:scope].to_sym)) ||
|
|
7
|
+
(options[:except] && !options[:except].include?(params[:scope].to_sym))
|
|
8
|
+
|
|
9
|
+
link_to(translate_scoped("batch_actions.#{name}", default: name.to_s.titleize), "#", class: "btn btn-default batch-actions-action-link hidden", data: {
|
|
10
|
+
value: name,
|
|
11
|
+
confirm: options[:confirm] ? translate_scoped("batch_actions.confirm_message") : false
|
|
12
|
+
})
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
end
|
|
16
|
+
end
|
|
17
|
+
end
|
|
@@ -0,0 +1,108 @@
|
|
|
1
|
+
module Godmin
|
|
2
|
+
module Helpers
|
|
3
|
+
module Filters
|
|
4
|
+
def filter_input_tag(name, options)
|
|
5
|
+
case options[:as]
|
|
6
|
+
when :string
|
|
7
|
+
filter_string_tag(name, options)
|
|
8
|
+
when :select
|
|
9
|
+
filter_select_tag(name, options)
|
|
10
|
+
when :multiselect
|
|
11
|
+
filter_multiselect_tag(name, options)
|
|
12
|
+
when :checkboxes
|
|
13
|
+
filter_checkbox_tags(name, options)
|
|
14
|
+
end
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
private
|
|
18
|
+
|
|
19
|
+
def filter_string_tag(name, _options)
|
|
20
|
+
text_field_tag(
|
|
21
|
+
name,
|
|
22
|
+
default_filter_value(name),
|
|
23
|
+
name: "filter[#{name}]",
|
|
24
|
+
class: "form-control",
|
|
25
|
+
placeholder: translate_scoped("filters.labels.#{name}", default: name.to_s.titleize)
|
|
26
|
+
)
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
def filter_select_tag(name, options)
|
|
30
|
+
filter_select_tag_helper(
|
|
31
|
+
name,
|
|
32
|
+
options,
|
|
33
|
+
name: "filter[#{name}]",
|
|
34
|
+
include_blank: true,
|
|
35
|
+
class: "form-control select-tag",
|
|
36
|
+
data: {
|
|
37
|
+
placeholder: translate_scoped("filters.select.placeholder.one")
|
|
38
|
+
}
|
|
39
|
+
)
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
def filter_multiselect_tag(name, options)
|
|
43
|
+
filter_select_tag_helper(
|
|
44
|
+
name,
|
|
45
|
+
options,
|
|
46
|
+
name: "filter[#{name}][]",
|
|
47
|
+
multiple: true,
|
|
48
|
+
class: "form-control select-tag",
|
|
49
|
+
data: {
|
|
50
|
+
placeholder: translate_scoped("filters.select.placeholder.many")
|
|
51
|
+
}
|
|
52
|
+
)
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
def filter_select_tag_helper(name, options, html_options)
|
|
56
|
+
unless options[:collection].is_a? Proc
|
|
57
|
+
raise "A collection proc must be specified for select filters"
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
collection = options[:collection].call
|
|
61
|
+
|
|
62
|
+
if collection.is_a? ActiveRecord::Relation
|
|
63
|
+
choices = options_from_collection_for_select(
|
|
64
|
+
collection,
|
|
65
|
+
options[:option_value],
|
|
66
|
+
options[:option_text],
|
|
67
|
+
selected: default_filter_value(name)
|
|
68
|
+
)
|
|
69
|
+
else
|
|
70
|
+
choices = options_for_select(
|
|
71
|
+
collection,
|
|
72
|
+
selected: default_filter_value(name)
|
|
73
|
+
)
|
|
74
|
+
end
|
|
75
|
+
|
|
76
|
+
select_tag(name, choices, html_options)
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
def filter_checkbox_tags(name, options)
|
|
80
|
+
unless options[:collection].is_a? Proc
|
|
81
|
+
raise "A collection proc must be specified for checkbox filters"
|
|
82
|
+
end
|
|
83
|
+
|
|
84
|
+
collection = options[:collection].call
|
|
85
|
+
|
|
86
|
+
collection.map do |item|
|
|
87
|
+
text, value = if !item.is_a?(String) && item.respond_to?(:first) && item.respond_to?(:last)
|
|
88
|
+
[item.first.to_s, item.last.to_s]
|
|
89
|
+
else
|
|
90
|
+
[item.to_s, item.to_s]
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
is_checked = default_filter_value(name) ? default_filter_value(name).include?(value) : false
|
|
94
|
+
|
|
95
|
+
content_tag :div, class: "checkbox" do
|
|
96
|
+
label_tag("#{name}_#{value}") do
|
|
97
|
+
check_box_tag("filter[#{name}][]", value, is_checked, id: "#{name}_#{value}") << text
|
|
98
|
+
end
|
|
99
|
+
end
|
|
100
|
+
end.join("\n").html_safe
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
def default_filter_value(name)
|
|
104
|
+
params[:filter] ? params[:filter][name] : nil
|
|
105
|
+
end
|
|
106
|
+
end
|
|
107
|
+
end
|
|
108
|
+
end
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
module Godmin
|
|
2
|
+
module Helpers
|
|
3
|
+
module Tables
|
|
4
|
+
def column_header(attribute)
|
|
5
|
+
if @resource_class.column_names.include?(attribute.to_s)
|
|
6
|
+
direction =
|
|
7
|
+
if params[:order]
|
|
8
|
+
if params[:order].split("_").first == attribute.to_s
|
|
9
|
+
params[:order].split("_").last == "desc" ? "asc" : "desc"
|
|
10
|
+
else
|
|
11
|
+
params[:order].split("_").last
|
|
12
|
+
end
|
|
13
|
+
else
|
|
14
|
+
"desc"
|
|
15
|
+
end
|
|
16
|
+
link_to @resource_class.human_attribute_name(attribute.to_s), url_for(params.merge(order: "#{attribute}_#{direction}"))
|
|
17
|
+
else
|
|
18
|
+
@resource_class.human_attribute_name(attribute.to_s)
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
def column_value(resource, attribute)
|
|
23
|
+
if lookup_context.exists?("columns/#{attribute}", nil, true)
|
|
24
|
+
render partial: "columns/#{attribute}", locals: { resource: resource }
|
|
25
|
+
else
|
|
26
|
+
column_value = resource.send(attribute)
|
|
27
|
+
|
|
28
|
+
if column_value.is_a?(Date) || column_value.is_a?(Time)
|
|
29
|
+
column_value = l(column_value, format: :long)
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
if column_value.is_a?(TrueClass) || column_value.is_a?(FalseClass)
|
|
33
|
+
column_value = t(column_value.to_s)
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
column_value
|
|
37
|
+
end
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
end
|
|
41
|
+
end
|