easy-admin-rails 0.1.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.
Files changed (203) hide show
  1. checksums.yaml +7 -0
  2. data/MIT-LICENSE +20 -0
  3. data/README.md +28 -0
  4. data/Rakefile +8 -0
  5. data/app/assets/builds/easy_admin.base.js +43505 -0
  6. data/app/assets/builds/easy_admin.base.js.map +7 -0
  7. data/app/assets/builds/easy_admin.css +6141 -0
  8. data/app/assets/config/easy_admin_manifest.js +1 -0
  9. data/app/assets/images/jsoneditor-icons.svg +749 -0
  10. data/app/assets/stylesheets/easy_admin/application.tailwind.css +390 -0
  11. data/app/components/easy_admin/base_component.rb +35 -0
  12. data/app/components/easy_admin/batch_action_bar_component.rb +125 -0
  13. data/app/components/easy_admin/batch_action_form_component.rb +124 -0
  14. data/app/components/easy_admin/combined_filters_component.rb +232 -0
  15. data/app/components/easy_admin/confirmation_modal_component.rb +61 -0
  16. data/app/components/easy_admin/context_menu_component.rb +161 -0
  17. data/app/components/easy_admin/dashboards/base_card_component.rb +152 -0
  18. data/app/components/easy_admin/dashboards/card_error_component.rb +23 -0
  19. data/app/components/easy_admin/dashboards/card_factory.rb +90 -0
  20. data/app/components/easy_admin/dashboards/card_stream_component.rb +22 -0
  21. data/app/components/easy_admin/dashboards/cards/base_card_component.rb +54 -0
  22. data/app/components/easy_admin/dashboards/cards/chart_card_component.rb +175 -0
  23. data/app/components/easy_admin/dashboards/cards/custom_card_component.rb +50 -0
  24. data/app/components/easy_admin/dashboards/cards/metric_card_component.rb +164 -0
  25. data/app/components/easy_admin/dashboards/cards/table_card_component.rb +148 -0
  26. data/app/components/easy_admin/dashboards/chart_card_component.rb +44 -0
  27. data/app/components/easy_admin/dashboards/metric_card_component.rb +56 -0
  28. data/app/components/easy_admin/dashboards/refresh_stream_component.rb +279 -0
  29. data/app/components/easy_admin/dashboards/show_component.rb +163 -0
  30. data/app/components/easy_admin/dashboards/table_card_component.rb +52 -0
  31. data/app/components/easy_admin/date_picker_component.rb +188 -0
  32. data/app/components/easy_admin/fields/base_component.rb +101 -0
  33. data/app/components/easy_admin/fields/belongs_to_edit_modal_component.rb +117 -0
  34. data/app/components/easy_admin/fields/form/belongs_to_component.rb +82 -0
  35. data/app/components/easy_admin/fields/form/boolean_component.rb +100 -0
  36. data/app/components/easy_admin/fields/form/date_component.rb +55 -0
  37. data/app/components/easy_admin/fields/form/datetime_component.rb +55 -0
  38. data/app/components/easy_admin/fields/form/email_component.rb +55 -0
  39. data/app/components/easy_admin/fields/form/file_component.rb +190 -0
  40. data/app/components/easy_admin/fields/form/has_many_component.rb +416 -0
  41. data/app/components/easy_admin/fields/form/json_component.rb +81 -0
  42. data/app/components/easy_admin/fields/form/number_component.rb +55 -0
  43. data/app/components/easy_admin/fields/form/select_component.rb +326 -0
  44. data/app/components/easy_admin/fields/form/text_component.rb +55 -0
  45. data/app/components/easy_admin/fields/form/textarea_component.rb +54 -0
  46. data/app/components/easy_admin/fields/index/belongs_to_component.rb +93 -0
  47. data/app/components/easy_admin/fields/index/boolean_component.rb +29 -0
  48. data/app/components/easy_admin/fields/index/date_component.rb +13 -0
  49. data/app/components/easy_admin/fields/index/datetime_component.rb +13 -0
  50. data/app/components/easy_admin/fields/index/email_component.rb +24 -0
  51. data/app/components/easy_admin/fields/index/filters/base_component.rb +48 -0
  52. data/app/components/easy_admin/fields/index/filters/boolean_component.rb +96 -0
  53. data/app/components/easy_admin/fields/index/filters/date_component.rb +182 -0
  54. data/app/components/easy_admin/fields/index/filters/number_component.rb +30 -0
  55. data/app/components/easy_admin/fields/index/filters/select_component.rb +101 -0
  56. data/app/components/easy_admin/fields/index/filters/string_component.rb +32 -0
  57. data/app/components/easy_admin/fields/index/json_component.rb +23 -0
  58. data/app/components/easy_admin/fields/index/number_component.rb +20 -0
  59. data/app/components/easy_admin/fields/index/select_component.rb +25 -0
  60. data/app/components/easy_admin/fields/index/text_component.rb +20 -0
  61. data/app/components/easy_admin/fields/inline_edit_modal_component.rb +135 -0
  62. data/app/components/easy_admin/fields/inline_edit_trigger_component.rb +144 -0
  63. data/app/components/easy_admin/fields/show/belongs_to_component.rb +93 -0
  64. data/app/components/easy_admin/fields/show/boolean_component.rb +21 -0
  65. data/app/components/easy_admin/fields/show/date_component.rb +13 -0
  66. data/app/components/easy_admin/fields/show/datetime_component.rb +13 -0
  67. data/app/components/easy_admin/fields/show/email_component.rb +19 -0
  68. data/app/components/easy_admin/fields/show/file_component.rb +304 -0
  69. data/app/components/easy_admin/fields/show/has_many_component.rb +192 -0
  70. data/app/components/easy_admin/fields/show/json_component.rb +45 -0
  71. data/app/components/easy_admin/fields/show/number_component.rb +20 -0
  72. data/app/components/easy_admin/fields/show/select_component.rb +25 -0
  73. data/app/components/easy_admin/fields/show/text_component.rb +17 -0
  74. data/app/components/easy_admin/fields/show/textarea_component.rb +26 -0
  75. data/app/components/easy_admin/filters_component.rb +120 -0
  76. data/app/components/easy_admin/form_tabs_component.rb +166 -0
  77. data/app/components/easy_admin/infinite_scroll_component.rb +82 -0
  78. data/app/components/easy_admin/lazy_chart_card_component.rb +128 -0
  79. data/app/components/easy_admin/lazy_metric_card_component.rb +76 -0
  80. data/app/components/easy_admin/modal_frame_component.rb +26 -0
  81. data/app/components/easy_admin/navbar_component.rb +226 -0
  82. data/app/components/easy_admin/notification_component.rb +83 -0
  83. data/app/components/easy_admin/pagination_component.rb +188 -0
  84. data/app/components/easy_admin/quick_filters_component.rb +65 -0
  85. data/app/components/easy_admin/resource_pagination_component.rb +14 -0
  86. data/app/components/easy_admin/resources/index_component.rb +211 -0
  87. data/app/components/easy_admin/resources/index_frame_component.rb +88 -0
  88. data/app/components/easy_admin/resources/show_page_actions_component.rb +324 -0
  89. data/app/components/easy_admin/resources/table_cell_component.rb +145 -0
  90. data/app/components/easy_admin/resources/table_component.rb +206 -0
  91. data/app/components/easy_admin/resources/table_row_component.rb +160 -0
  92. data/app/components/easy_admin/row_action_form_component.rb +127 -0
  93. data/app/components/easy_admin/scopes_component.rb +224 -0
  94. data/app/components/easy_admin/settings_sidebar_component.rb +140 -0
  95. data/app/components/easy_admin/show_layout_component.rb +600 -0
  96. data/app/components/easy_admin/sidebar_component.rb +174 -0
  97. data/app/components/easy_admin/turbo/response_component.rb +40 -0
  98. data/app/components/easy_admin/turbo/stream_component.rb +28 -0
  99. data/app/controllers/easy_admin/application_controller.rb +66 -0
  100. data/app/controllers/easy_admin/batch_actions_controller.rb +166 -0
  101. data/app/controllers/easy_admin/confirmation_modal_controller.rb +20 -0
  102. data/app/controllers/easy_admin/dashboard_controller.rb +6 -0
  103. data/app/controllers/easy_admin/dashboards_controller.rb +123 -0
  104. data/app/controllers/easy_admin/passwords_controller.rb +15 -0
  105. data/app/controllers/easy_admin/registrations_controller.rb +52 -0
  106. data/app/controllers/easy_admin/resources_controller.rb +907 -0
  107. data/app/controllers/easy_admin/row_actions_controller.rb +216 -0
  108. data/app/controllers/easy_admin/sessions_controller.rb +32 -0
  109. data/app/controllers/easy_admin/settings_controller.rb +94 -0
  110. data/app/helpers/easy_admin/application_helper.rb +4 -0
  111. data/app/helpers/easy_admin/dashboards_helper.rb +121 -0
  112. data/app/helpers/easy_admin/fields_helper.rb +27 -0
  113. data/app/helpers/easy_admin/pagy_helper.rb +30 -0
  114. data/app/helpers/easy_admin/resources_helper.rb +39 -0
  115. data/app/javascript/easy_admin/application.js +12 -0
  116. data/app/javascript/easy_admin/controllers/batch_modal_controller.js +66 -0
  117. data/app/javascript/easy_admin/controllers/batch_selection_controller.js +223 -0
  118. data/app/javascript/easy_admin/controllers/chart_controller.js +216 -0
  119. data/app/javascript/easy_admin/controllers/collapsible_filters_controller.js +118 -0
  120. data/app/javascript/easy_admin/controllers/confirmation_modal_controller.js +64 -0
  121. data/app/javascript/easy_admin/controllers/context_menu_controller.js +227 -0
  122. data/app/javascript/easy_admin/controllers/date_picker_controller.js +309 -0
  123. data/app/javascript/easy_admin/controllers/dropdown_controller.js +63 -0
  124. data/app/javascript/easy_admin/controllers/event_emitter_controller.js +19 -0
  125. data/app/javascript/easy_admin/controllers/file_controller.js +121 -0
  126. data/app/javascript/easy_admin/controllers/form_tabs_controller.js +100 -0
  127. data/app/javascript/easy_admin/controllers/has_many_search_controller.js +76 -0
  128. data/app/javascript/easy_admin/controllers/infinite_scroll_controller.js +174 -0
  129. data/app/javascript/easy_admin/controllers/ios_alert_controller.js +195 -0
  130. data/app/javascript/easy_admin/controllers/jsoneditor_controller.js +88 -0
  131. data/app/javascript/easy_admin/controllers/modal_controller.js +75 -0
  132. data/app/javascript/easy_admin/controllers/navbar_scroll_controller.js +76 -0
  133. data/app/javascript/easy_admin/controllers/notification_controller.js +48 -0
  134. data/app/javascript/easy_admin/controllers/row_action_controller.js +124 -0
  135. data/app/javascript/easy_admin/controllers/row_modal_controller.js +59 -0
  136. data/app/javascript/easy_admin/controllers/select_field_controller.js +618 -0
  137. data/app/javascript/easy_admin/controllers/settings_button_controller.js +8 -0
  138. data/app/javascript/easy_admin/controllers/settings_sidebar_controller.js +186 -0
  139. data/app/javascript/easy_admin/controllers/sidebar_controller.js +102 -0
  140. data/app/javascript/easy_admin/controllers/sidebar_mobile_controller.js +23 -0
  141. data/app/javascript/easy_admin/controllers/sidebar_nav_controller.js +96 -0
  142. data/app/javascript/easy_admin/controllers/table_controller.js +28 -0
  143. data/app/javascript/easy_admin/controllers/table_row_controller.js +16 -0
  144. data/app/javascript/easy_admin/controllers/toggle_switch_controller.js +22 -0
  145. data/app/javascript/easy_admin/controllers/turbo_stream_redirect.js +9 -0
  146. data/app/javascript/easy_admin/controllers.js +54 -0
  147. data/app/javascript/easy_admin.base.js +4 -0
  148. data/app/models/easy_admin/admin_user.rb +53 -0
  149. data/app/models/easy_admin/application_record.rb +5 -0
  150. data/app/views/easy_admin/dashboard/index.html.erb +3 -0
  151. data/app/views/easy_admin/dashboards/show.html.erb +7 -0
  152. data/app/views/easy_admin/passwords/edit.html.erb +42 -0
  153. data/app/views/easy_admin/passwords/new.html.erb +41 -0
  154. data/app/views/easy_admin/registrations/new.html.erb +65 -0
  155. data/app/views/easy_admin/resources/_redirect.turbo_stream.erb +3 -0
  156. data/app/views/easy_admin/resources/_table_rows.html.erb +46 -0
  157. data/app/views/easy_admin/resources/edit.html.erb +151 -0
  158. data/app/views/easy_admin/resources/index.html.erb +12 -0
  159. data/app/views/easy_admin/resources/index.turbo_stream.erb +139 -0
  160. data/app/views/easy_admin/resources/index_frame.html.erb +142 -0
  161. data/app/views/easy_admin/resources/new.html.erb +100 -0
  162. data/app/views/easy_admin/resources/show.html.erb +31 -0
  163. data/app/views/easy_admin/sessions/new.html.erb +55 -0
  164. data/app/views/easy_admin/settings/_form.html.erb +51 -0
  165. data/app/views/easy_admin/settings/index.html.erb +53 -0
  166. data/app/views/layouts/easy_admin/application.html.erb +48 -0
  167. data/app/views/layouts/easy_admin/auth.html.erb +34 -0
  168. data/config/initializers/easy_admin_card_factory.rb +27 -0
  169. data/config/initializers/pagy.rb +15 -0
  170. data/config/initializers/rack_mini_profiler.rb +67 -0
  171. data/config/routes.rb +70 -0
  172. data/db/migrate/20250101000001_create_easy_admin_admin_users.rb +45 -0
  173. data/lib/easy-admin.rb +32 -0
  174. data/lib/easy_admin/action.rb +159 -0
  175. data/lib/easy_admin/batch_action.rb +134 -0
  176. data/lib/easy_admin/configuration.rb +75 -0
  177. data/lib/easy_admin/dashboard.rb +110 -0
  178. data/lib/easy_admin/dashboard_registry.rb +30 -0
  179. data/lib/easy_admin/delete_action.rb +22 -0
  180. data/lib/easy_admin/engine.rb +54 -0
  181. data/lib/easy_admin/field.rb +118 -0
  182. data/lib/easy_admin/resource.rb +806 -0
  183. data/lib/easy_admin/resource_registry.rb +22 -0
  184. data/lib/easy_admin/types/json_type.rb +25 -0
  185. data/lib/easy_admin/version.rb +3 -0
  186. data/lib/generators/easy_admin/auth_generator.rb +69 -0
  187. data/lib/generators/easy_admin/card/card_generator.rb +94 -0
  188. data/lib/generators/easy_admin/card/templates/card_component.rb.erb +127 -0
  189. data/lib/generators/easy_admin/card/templates/card_component_spec.rb.erb +122 -0
  190. data/lib/generators/easy_admin/install/templates/easy_admin.rb +31 -0
  191. data/lib/generators/easy_admin/install_generator.rb +25 -0
  192. data/lib/generators/easy_admin/rbac/rbac_generator.rb +244 -0
  193. data/lib/generators/easy_admin/rbac/templates/add_rbac_to_admin_users.rb +23 -0
  194. data/lib/generators/easy_admin/rbac/templates/super_admin.rb +34 -0
  195. data/lib/generators/easy_admin/resource_generator.rb +43 -0
  196. data/lib/generators/easy_admin/templates/AUTH_README +35 -0
  197. data/lib/generators/easy_admin/templates/README +27 -0
  198. data/lib/generators/easy_admin/templates/create_easy_admin_admin_users.rb +45 -0
  199. data/lib/generators/easy_admin/templates/devise.rb +267 -0
  200. data/lib/generators/easy_admin/templates/easy_admin.rb +24 -0
  201. data/lib/generators/easy_admin/templates/resource.rb +29 -0
  202. data/lib/tasks/easy_admin_tasks.rake +4 -0
  203. metadata +445 -0
@@ -0,0 +1,244 @@
1
+ require 'rails/generators'
2
+ require 'rails/generators/migration'
3
+
4
+ module EasyAdmin
5
+ module Generators
6
+ class RbacGenerator < Rails::Generators::Base
7
+ include Rails::Generators::Migration
8
+
9
+ source_root File.expand_path('../templates', __FILE__)
10
+
11
+ desc 'Generate EasyAdmin Role-Based Access Control setup'
12
+
13
+ def self.next_migration_number(path)
14
+ Time.current.utc.strftime("%Y%m%d%H%M%S")
15
+ end
16
+
17
+ def copy_migration
18
+ migration_template(
19
+ 'add_rbac_to_admin_users.rb',
20
+ 'db/migrate/add_rbac_to_admin_users.rb',
21
+ migration_version: migration_version
22
+ )
23
+ end
24
+
25
+ def create_role_models
26
+ template 'super_admin.rb', 'app/models/easy_admin/super_admin.rb'
27
+ template 'admin.rb', 'app/models/easy_admin/admin.rb'
28
+ template 'editor.rb', 'app/models/easy_admin/editor.rb'
29
+ template 'viewer.rb', 'app/models/easy_admin/viewer.rb'
30
+ end
31
+
32
+ def update_admin_user_model
33
+ inject_into_file 'app/models/easy_admin/admin_user.rb', after: "self.table_name = \"easy_admin_admin_users\"\n" do
34
+ <<-RUBY
35
+
36
+ # STI configuration for role-based access
37
+ self.inheritance_column = :type
38
+
39
+ # Associations
40
+ has_many :audit_logs, class_name: 'EasyAdmin::AuditLog', foreign_key: :admin_user_id, dependent: :destroy
41
+
42
+ # Scopes
43
+ scope :by_role, ->(role) { where(type: "EasyAdmin::\#{role}") }
44
+
45
+ # Cache permissions per request
46
+ def permissions_cache
47
+ @permissions_cache ||= {}
48
+ end
49
+
50
+ # Core authorization methods (to be overridden by subclasses)
51
+ def can_access_resource?(resource_name)
52
+ accessible_resources.include?(resource_name.to_s)
53
+ end
54
+
55
+ def can_perform_action?(resource_name, action)
56
+ return false unless can_access_resource?(resource_name)
57
+ allowed_actions_for(resource_name).include?(action.to_s)
58
+ end
59
+
60
+ def can_access_field?(resource_name, field_name, action = :read)
61
+ return false unless can_access_resource?(resource_name)
62
+ !restricted_fields_for(resource_name, action).include?(field_name.to_s)
63
+ end
64
+
65
+ # Override in subclasses
66
+ def accessible_resources
67
+ []
68
+ end
69
+
70
+ def allowed_actions_for(resource_name)
71
+ [:index, :show]
72
+ end
73
+
74
+ def restricted_fields_for(resource_name, action)
75
+ []
76
+ end
77
+
78
+ def apply_resource_scope(resource_name, scope)
79
+ scope
80
+ end
81
+
82
+ # Helper for caching expensive operations
83
+ def cached_permission(key, &block)
84
+ permissions_cache[key] ||= block.call
85
+ end
86
+ RUBY
87
+ end
88
+ end
89
+
90
+ def create_permission_cache
91
+ template 'permission_cache.rb', 'lib/easy_admin/permission_cache.rb'
92
+ end
93
+
94
+ def create_audit_log_model
95
+ template 'audit_log.rb', 'app/models/easy_admin/audit_log.rb'
96
+
97
+ migration_template(
98
+ 'create_audit_logs.rb',
99
+ 'db/migrate/create_easy_admin_audit_logs.rb',
100
+ migration_version: migration_version
101
+ )
102
+ end
103
+
104
+ def update_application_controller
105
+ inject_into_file 'app/controllers/easy_admin/application_controller.rb',
106
+ before: "include Pagy::Backend" do
107
+ <<-RUBY
108
+ class UnauthorizedError < StandardError; end
109
+
110
+ RUBY
111
+ end
112
+
113
+ inject_into_file 'app/controllers/easy_admin/application_controller.rb',
114
+ after: "before_action :authenticate_easy_admin_admin_user!\n" do
115
+ <<-RUBY
116
+ before_action :check_resource_access!, except: [:index]
117
+
118
+ rescue_from UnauthorizedError do |exception|
119
+ respond_to do |format|
120
+ format.html { redirect_to easy_admin.root_path, alert: 'You are not authorized to access this resource.' }
121
+ format.turbo_stream do
122
+ render turbo_stream: turbo_stream.replace("notifications",
123
+ EasyAdmin::NotificationComponent.new(
124
+ message: 'You are not authorized to access this resource',
125
+ type: :error
126
+ ).call
127
+ )
128
+ end
129
+ end
130
+ end
131
+ RUBY
132
+ end
133
+
134
+ inject_into_file 'app/controllers/easy_admin/application_controller.rb',
135
+ before: "def authenticate_admin_user!" do
136
+ <<-RUBY
137
+ def check_resource_access!
138
+ return unless defined?(@resource_class)
139
+
140
+ unless current_admin_user.can_access_resource?(@resource_class.resource_name)
141
+ raise UnauthorizedError, "Access denied to \#{@resource_class.resource_name}"
142
+ end
143
+
144
+ check_action_permission!
145
+ end
146
+
147
+ def check_action_permission!
148
+ action_map = {
149
+ 'index' => :index,
150
+ 'show' => :show,
151
+ 'new' => :new,
152
+ 'create' => :create,
153
+ 'edit' => :edit,
154
+ 'update' => :update,
155
+ 'destroy' => :destroy,
156
+ 'execute' => :batch_action
157
+ }
158
+
159
+ mapped_action = action_map[action_name] || action_name.to_sym
160
+
161
+ unless current_admin_user.can_perform_action?(@resource_class.resource_name, mapped_action)
162
+ raise UnauthorizedError, "Cannot perform \#{mapped_action} on \#{@resource_class.resource_name}"
163
+ end
164
+ end
165
+
166
+ def apply_role_scoping(scope)
167
+ current_admin_user.apply_resource_scope(@resource_class.resource_name, scope)
168
+ end
169
+
170
+ def permission_cache
171
+ @permission_cache ||= EasyAdmin::PermissionCache.new(current_admin_user)
172
+ end
173
+
174
+ RUBY
175
+ end
176
+
177
+ inject_into_file 'app/controllers/easy_admin/application_controller.rb',
178
+ after: "helper_method :current_admin_user, :admin_user_signed_in?" do
179
+ ", :permission_cache"
180
+ end
181
+ end
182
+
183
+ def create_seeds
184
+ create_file 'db/seeds/easy_admin_rbac.rb', <<~RUBY
185
+ # Create default admin users with different roles
186
+ if Rails.env.development?
187
+ # Super Admin - full access
188
+ EasyAdmin::SuperAdmin.find_or_create_by(email: 'super@example.com') do |admin|
189
+ admin.password = 'password'
190
+ admin.password_confirmation = 'password'
191
+ admin.first_name = 'Super'
192
+ admin.last_name = 'Admin'
193
+ admin.confirmed_at = Time.current
194
+ end
195
+
196
+ # Standard Admin - most access except system settings
197
+ EasyAdmin::Admin.find_or_create_by(email: 'admin@example.com') do |admin|
198
+ admin.password = 'password'
199
+ admin.password_confirmation = 'password'
200
+ admin.first_name = 'Admin'
201
+ admin.last_name = 'User'
202
+ admin.confirmed_at = Time.current
203
+ end
204
+
205
+ # Editor - content management only
206
+ EasyAdmin::Editor.find_or_create_by(email: 'editor@example.com') do |admin|
207
+ admin.password = 'password'
208
+ admin.password_confirmation = 'password'
209
+ admin.first_name = 'Content'
210
+ admin.last_name = 'Editor'
211
+ admin.confirmed_at = Time.current
212
+ end
213
+
214
+ # Viewer - read-only access
215
+ EasyAdmin::Viewer.find_or_create_by(email: 'viewer@example.com') do |admin|
216
+ admin.password = 'password'
217
+ admin.password_confirmation = 'password'
218
+ admin.first_name = 'Read'
219
+ admin.last_name = 'Only'
220
+ admin.confirmed_at = Time.current
221
+ end
222
+
223
+ puts "EasyAdmin RBAC users created!"
224
+ puts "Roles available:"
225
+ puts " SuperAdmin - super@example.com / password (full access)"
226
+ puts " Admin - admin@example.com / password (standard admin)"
227
+ puts " Editor - editor@example.com / password (content only)"
228
+ puts " Viewer - viewer@example.com / password (read-only)"
229
+ end
230
+ RUBY
231
+ end
232
+
233
+ def show_readme
234
+ readme 'RBAC_README'
235
+ end
236
+
237
+ private
238
+
239
+ def migration_version
240
+ "[#{ActiveRecord::VERSION::MAJOR}.#{ActiveRecord::VERSION::MINOR}]"
241
+ end
242
+ end
243
+ end
244
+ end
@@ -0,0 +1,23 @@
1
+ class AddRbacToAdminUsers < ActiveRecord::Migration<%= migration_version %>
2
+ def change
3
+ # Add type column for STI
4
+ add_column :easy_admin_admin_users, :type, :string
5
+ add_column :easy_admin_admin_users, :permissions, :json, default: {}
6
+ add_column :easy_admin_admin_users, :resource_access, :json, default: {}
7
+
8
+ # Add indexes for performance
9
+ add_index :easy_admin_admin_users, :type
10
+ add_index :easy_admin_admin_users, [:type, :locked_at]
11
+
12
+ # Migrate existing users to Admin type
13
+ reversible do |dir|
14
+ dir.up do
15
+ execute <<-SQL
16
+ UPDATE easy_admin_admin_users
17
+ SET type = 'EasyAdmin::Admin'
18
+ WHERE type IS NULL
19
+ SQL
20
+ end
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,34 @@
1
+ module EasyAdmin
2
+ class SuperAdmin < AdminUser
3
+ def accessible_resources
4
+ cached_permission(:resources) do
5
+ EasyAdmin::ResourceRegistry.all_resources.map(&:resource_name)
6
+ end
7
+ end
8
+
9
+ def allowed_actions_for(resource_name)
10
+ [:index, :show, :new, :create, :edit, :update, :destroy, :batch_action, :row_action].map(&:to_s)
11
+ end
12
+
13
+ def restricted_fields_for(resource_name, action)
14
+ [] # No restrictions for super admin
15
+ end
16
+
17
+ def apply_resource_scope(resource_name, scope)
18
+ scope # No filtering for super admin
19
+ end
20
+
21
+ # Super admin specific methods
22
+ def super_admin?
23
+ true
24
+ end
25
+
26
+ def role_name
27
+ 'Super Admin'
28
+ end
29
+
30
+ def role_badge_color
31
+ 'red'
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,43 @@
1
+ module EasyAdmin
2
+ module Generators
3
+ class ResourceGenerator < Rails::Generators::NamedBase
4
+ desc "Creates EasyAdmin resource for a model"
5
+
6
+ def self.source_root
7
+ @source_root ||= File.expand_path("templates", __dir__)
8
+ end
9
+
10
+ def create_resource
11
+ template "resource.rb", "app/easy_admin/resources/#{file_name}_resource.rb"
12
+ end
13
+
14
+ def show_usage
15
+ say "\nResource created! Add it to your EasyAdmin configuration:", :green
16
+ say "\n # config/initializers/easy_admin.rb"
17
+ say " EasyAdmin.configure do |config|"
18
+ say " config.sidebar do"
19
+ say " item \"#{human_name.pluralize}\", easy_admin.#{route_key}_path, icon: \"📄\""
20
+ say " end"
21
+ say " end\n"
22
+ end
23
+
24
+ private
25
+
26
+ def model_class_name
27
+ class_name
28
+ end
29
+
30
+ def route_key
31
+ file_name.pluralize
32
+ end
33
+
34
+ def resource_class_name
35
+ "#{class_name}Resource"
36
+ end
37
+
38
+ def human_name
39
+ class_name.humanize
40
+ end
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,35 @@
1
+ ===============================================================================
2
+
3
+ EasyAdmin Authentication Setup Complete!
4
+
5
+ ===============================================================================
6
+
7
+ The EasyAdmin authentication system has been successfully installed.
8
+
9
+ What was added:
10
+ - Admin users migration (creates easy_admin_admin_users table)
11
+ - Devise configuration for EasyAdmin (config/initializers/easy_admin_devise.rb)
12
+ - EasyAdmin routes mounted at /admin
13
+ - Default admin user seeds (db/seeds/easy_admin.rb)
14
+
15
+ Next steps:
16
+
17
+ 1. Run the migration:
18
+ rails db:migrate
19
+
20
+ 2. Load the default admin user:
21
+ rails db:seed
22
+
23
+ 3. Start your server and visit:
24
+ http://localhost:3000/admin
25
+
26
+ 4. Sign in with the default credentials:
27
+ Email: admin@example.com
28
+ Password: password
29
+
30
+ 5. (Optional) Configure email settings in config/initializers/easy_admin_devise.rb
31
+ for password reset functionality.
32
+
33
+ For more information, visit: https://github.com/your-username/easy_admin
34
+
35
+ ===============================================================================
@@ -0,0 +1,27 @@
1
+ ===============================================================================
2
+
3
+ EasyAdmin has been installed! 🎉
4
+
5
+ Next steps:
6
+
7
+ 1. Configure your sidebar navigation in config/initializers/easy_admin.rb
8
+ 2. Build the JavaScript assets: npm run build:js
9
+ 3. Visit /easy_admin in your browser
10
+
11
+ Documentation:
12
+ - Sidebar DSL: Use `item` for navigation links and `group` for expandable sections
13
+ - Icons: Use emoji or any text-based icons
14
+ - Paths: Relative paths will be prefixed with your app's base URL
15
+
16
+ Example configuration:
17
+
18
+ config.sidebar do
19
+ item "Dashboard", dashboard_path, icon: "📊", active: current_page?(dashboard_path)
20
+
21
+ group "Content", icon: "📝" do
22
+ item "Posts", posts_path, icon: "📄"
23
+ item "Categories", categories_path, icon: "🏷️"
24
+ end
25
+ end
26
+
27
+ ===============================================================================
@@ -0,0 +1,45 @@
1
+ class CreateEasyAdminAdminUsers < ActiveRecord::Migration<%= migration_version %>
2
+ def change
3
+ create_table :easy_admin_admin_users do |t|
4
+ ## Database authenticatable
5
+ t.string :email, null: false, default: ""
6
+ t.string :encrypted_password, null: false, default: ""
7
+
8
+ ## Personal Info
9
+ t.string :first_name
10
+ t.string :last_name
11
+
12
+ ## Recoverable
13
+ t.string :reset_password_token
14
+ t.datetime :reset_password_sent_at
15
+
16
+ ## Rememberable
17
+ t.datetime :remember_created_at
18
+
19
+ ## Trackable
20
+ t.integer :sign_in_count, default: 0, null: false
21
+ t.datetime :current_sign_in_at
22
+ t.datetime :last_sign_in_at
23
+ t.string :current_sign_in_ip
24
+ t.string :last_sign_in_ip
25
+
26
+ ## Confirmable
27
+ t.string :confirmation_token
28
+ t.datetime :confirmed_at
29
+ t.datetime :confirmation_sent_at
30
+ t.string :unconfirmed_email # Only if using reconfirmable
31
+
32
+ ## Lockable
33
+ t.integer :failed_attempts, default: 0, null: false # Only if lock strategy is :failed_attempts
34
+ t.string :unlock_token # Only if unlock strategy is :email or :both
35
+ t.datetime :locked_at
36
+
37
+ t.timestamps null: false
38
+ end
39
+
40
+ add_index :easy_admin_admin_users, :email, unique: true
41
+ add_index :easy_admin_admin_users, :reset_password_token, unique: true
42
+ add_index :easy_admin_admin_users, :confirmation_token, unique: true
43
+ add_index :easy_admin_admin_users, :unlock_token, unique: true
44
+ end
45
+ end