plutonium 0.23.4 → 0.23.5
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 +4 -4
- data/app/assets/plutonium.css +2 -2
- data/config/initializers/sqlite_json_alias.rb +1 -1
- data/docs/.vitepress/config.ts +60 -19
- data/docs/guide/cursor-rules.md +75 -0
- data/docs/guide/deep-dive/authorization.md +189 -0
- data/docs/guide/{getting-started → deep-dive}/resources.md +137 -0
- data/docs/guide/getting-started/{installation.md → 01-installation.md} +0 -105
- data/docs/guide/index.md +28 -0
- data/docs/guide/introduction/02-core-concepts.md +440 -0
- data/docs/guide/tutorial/01-project-setup.md +75 -0
- data/docs/guide/tutorial/02-creating-a-feature-package.md +45 -0
- data/docs/guide/tutorial/03-defining-resources.md +90 -0
- data/docs/guide/tutorial/04-creating-a-portal.md +101 -0
- data/docs/guide/tutorial/05-customizing-the-ui.md +128 -0
- data/docs/guide/tutorial/06-adding-custom-actions.md +101 -0
- data/docs/guide/tutorial/07-implementing-authorization.md +90 -0
- data/docs/index.md +24 -31
- data/docs/modules/action.md +190 -0
- data/docs/modules/authentication.md +236 -0
- data/docs/modules/configuration.md +599 -0
- data/docs/modules/controller.md +398 -0
- data/docs/modules/core.md +316 -0
- data/docs/modules/definition.md +876 -0
- data/docs/modules/display.md +759 -0
- data/docs/modules/form.md +605 -0
- data/docs/modules/generator.md +288 -0
- data/docs/modules/index.md +167 -0
- data/docs/modules/interaction.md +470 -0
- data/docs/modules/package.md +151 -0
- data/docs/modules/policy.md +176 -0
- data/docs/modules/portal.md +710 -0
- data/docs/modules/query.md +287 -0
- data/docs/modules/resource_record.md +618 -0
- data/docs/modules/routing.md +641 -0
- data/docs/modules/table.md +293 -0
- data/docs/modules/ui.md +631 -0
- data/docs/public/plutonium.mdc +667 -0
- data/lib/generators/pu/core/assets/assets_generator.rb +0 -5
- data/lib/plutonium/ui/display/resource.rb +7 -2
- data/lib/plutonium/ui/table/resource.rb +8 -3
- data/lib/plutonium/version.rb +1 -1
- metadata +36 -9
- data/docs/guide/getting-started/authorization.md +0 -296
- data/docs/guide/getting-started/core-concepts.md +0 -432
- data/docs/guide/getting-started/index.md +0 -21
- data/docs/guide/tutorial.md +0 -401
- /data/docs/guide/{what-is-plutonium.md → introduction/01-what-is-plutonium.md} +0 -0
@@ -0,0 +1,176 @@
|
|
1
|
+
---
|
2
|
+
title: Policy Module
|
3
|
+
---
|
4
|
+
|
5
|
+
# Policy Module
|
6
|
+
|
7
|
+
The Policy module provides comprehensive authorization and access control for Plutonium applications. Built on top of [ActionPolicy](https://actionpolicy.evilmartians.io/), it offers fine-grained permissions, resource scoping, and entity-based authorization with a secure-by-default approach.
|
8
|
+
|
9
|
+
::: tip
|
10
|
+
The base policy class is `Plutonium::Resource::Policy`. Resource policies are typically located in `app/policies/`.
|
11
|
+
:::
|
12
|
+
|
13
|
+
## Overview
|
14
|
+
|
15
|
+
- **Resource-Level Authorization**: Control access to CRUD operations and custom actions.
|
16
|
+
- **Attribute-Level Permissions**: Fine-grained control over which fields a user can see or edit.
|
17
|
+
- **Association Control**: Manage access to related resources.
|
18
|
+
- **Entity Scoping**: Built-in support for multi-tenant authorization.
|
19
|
+
- **Secure Defaults**: Policies default to denying access, requiring explicit permission.
|
20
|
+
|
21
|
+
## Basic Policy Structure
|
22
|
+
|
23
|
+
Resource policies inherit from `Plutonium::Resource::Policy` and define methods to control access.
|
24
|
+
|
25
|
+
::: code-group
|
26
|
+
```ruby [app/policies/post_policy.rb]
|
27
|
+
class PostPolicy < Plutonium::Resource::Policy
|
28
|
+
# Who can see a list of posts?
|
29
|
+
def index?
|
30
|
+
true # Everyone can see the list
|
31
|
+
end
|
32
|
+
|
33
|
+
# Who can see a single post?
|
34
|
+
def show?
|
35
|
+
record.published? || user == record.author || user.admin?
|
36
|
+
end
|
37
|
+
|
38
|
+
# Who can create a post?
|
39
|
+
def create?
|
40
|
+
user.present? # Any signed-in user
|
41
|
+
end
|
42
|
+
|
43
|
+
# Who can update a post?
|
44
|
+
def update?
|
45
|
+
user == record.author || user.admin?
|
46
|
+
end
|
47
|
+
|
48
|
+
# Who can destroy a post?
|
49
|
+
def destroy?
|
50
|
+
user.admin? # Only admins
|
51
|
+
end
|
52
|
+
|
53
|
+
# Who can run the custom 'publish' action?
|
54
|
+
def publish?
|
55
|
+
update? && record.draft? # Can only publish if you can update
|
56
|
+
end
|
57
|
+
end
|
58
|
+
```
|
59
|
+
```ruby [Authorization Context]
|
60
|
+
# Policies automatically receive context from the controller.
|
61
|
+
class Plutonium::Resource::Policy < ActionPolicy::Base
|
62
|
+
# `user` is the current authenticated user. It is required.
|
63
|
+
authorize :user, allow_nil: false
|
64
|
+
|
65
|
+
# `entity_scope` is the current portal's scoping entity (e.g., Organization).
|
66
|
+
# It is optional.
|
67
|
+
authorize :entity_scope, allow_nil: true
|
68
|
+
end
|
69
|
+
```
|
70
|
+
:::
|
71
|
+
|
72
|
+
::: danger Secure by Default
|
73
|
+
If a permission method (like `create?` or `publish?`) is not defined in your policy, it will default to `false`. You must explicitly grant permissions.
|
74
|
+
:::
|
75
|
+
|
76
|
+
## Attribute Permissions
|
77
|
+
|
78
|
+
You can control which attributes (fields) are visible or editable based on the action and user.
|
79
|
+
|
80
|
+
::: code-group
|
81
|
+
```ruby [Read Permissions]
|
82
|
+
class PostPolicy < Plutonium::Resource::Policy
|
83
|
+
# Defines which attributes are visible on `show` and `index` pages.
|
84
|
+
def permitted_attributes_for_read
|
85
|
+
# Start with a base set of attributes
|
86
|
+
attrs = [:title, :content, :category, :published_at]
|
87
|
+
# Add admin-only attributes conditionally
|
88
|
+
attrs << :internal_notes if user.admin?
|
89
|
+
attrs
|
90
|
+
end
|
91
|
+
end
|
92
|
+
```
|
93
|
+
```ruby [Create/Update Permissions]
|
94
|
+
class PostPolicy < Plutonium::Resource::Policy
|
95
|
+
# Defines which attributes can be submitted in `new` and `edit` forms.
|
96
|
+
def permitted_attributes_for_create
|
97
|
+
[:title, :content, :category]
|
98
|
+
end
|
99
|
+
|
100
|
+
def permitted_attributes_for_update
|
101
|
+
# Inherits from create by default, but can be customized.
|
102
|
+
attrs = permitted_attributes_for_create
|
103
|
+
attrs << :slug if user.admin? # Only admins can edit the slug
|
104
|
+
attrs
|
105
|
+
end
|
106
|
+
end
|
107
|
+
```
|
108
|
+
:::
|
109
|
+
|
110
|
+
::: details Full Permission Hierarchy
|
111
|
+
Plutonium uses a hierarchical permission system. Defining a core action permission (like `read?` or `create?`) automatically grants permission for related actions unless you override them.
|
112
|
+
|
113
|
+
**Action Permissions:**
|
114
|
+
- `index?` and `show?` inherit from `read?`
|
115
|
+
- `new?` inherits from `create?`
|
116
|
+
- `edit?` inherits from `update?`
|
117
|
+
- `update?` and `destroy?` inherit from `create?` by default.
|
118
|
+
|
119
|
+
**Attribute Permissions:**
|
120
|
+
- `_for_show` and `_for_index` inherit from `_for_read`.
|
121
|
+
- `_for_new` inherits from `_for_create`.
|
122
|
+
- `_for_edit` inherits from `_for_update`.
|
123
|
+
:::
|
124
|
+
|
125
|
+
## Scoping Collections
|
126
|
+
|
127
|
+
Use `relation_scope` to filter which records appear in a collection (e.g., on the `index` page).
|
128
|
+
|
129
|
+
::: code-group
|
130
|
+
```ruby [Simple Scope]
|
131
|
+
class PostPolicy < Plutonium::Resource::Policy
|
132
|
+
relation_scope do |relation|
|
133
|
+
# make sure to call super unless you want to bypass the default behavior
|
134
|
+
# plutonium offers
|
135
|
+
relation = super(relation)
|
136
|
+
|
137
|
+
if user.admin?
|
138
|
+
relation # Admins see all posts
|
139
|
+
else
|
140
|
+
# Other users only see their own posts or published posts
|
141
|
+
relation.where(author: user).or(relation.where(published: true))
|
142
|
+
end
|
143
|
+
end
|
144
|
+
end
|
145
|
+
```
|
146
|
+
```ruby [Multi-Tenant Scope]
|
147
|
+
class PostPolicy < Plutonium::Resource::Policy
|
148
|
+
relation_scope do |relation|
|
149
|
+
# `super` applies the portal's entity scoping first.
|
150
|
+
# e.g., `relation.associated_with(current_organization)`
|
151
|
+
relation = super(relation)
|
152
|
+
|
153
|
+
# Then, apply additional logic.
|
154
|
+
if user.admin?
|
155
|
+
relation
|
156
|
+
else
|
157
|
+
relation.where(published: true)
|
158
|
+
end
|
159
|
+
end
|
160
|
+
end
|
161
|
+
```
|
162
|
+
:::
|
163
|
+
|
164
|
+
## Association Permissions
|
165
|
+
|
166
|
+
Control which associated resources can be accessed or rendered.
|
167
|
+
|
168
|
+
```ruby
|
169
|
+
class PostPolicy < Plutonium::Resource::Policy
|
170
|
+
# This determines which associations can be rendered in the UI,
|
171
|
+
# especially for nested forms or displays.
|
172
|
+
def permitted_associations
|
173
|
+
[:comments, :author, :tags]
|
174
|
+
end
|
175
|
+
end
|
176
|
+
```
|