on master help sign in
add permissions doc
commit2cc6a2c02afc0d72941a70597acaca257a172346 authortinnus-napbus <admin@tinnus-napbus.xyz> dateFri 7 May 2021, 22:46 (5 years ago) parent22ba120
3 files changed+320
arvo/clay/_index.md+4 arvo/clay/clay.md+4 arvo/clay/permissions.md+312
arvo/clay/_index.md+4
@@ -42,3 +42,7 @@ How to manage clay unix mounts programmatically.
4242[Merge Desks](@/docs/arvo/clay/merge.md)
4343
4444How to merge desks programmatically.
45+
46+[Permissions](@/docs/arvo/clay/permissions.md)
47+
48+How to manage file permissions in clay.
arvo/clay/clay.md+4
@@ -71,3 +71,7 @@ How to manage clay unix mounts programmatically.
7171[Merge Desks](@/docs/arvo/clay/merge.md)
7272
7373How to merge desks programmatically.
74+
75+[Permissions](@/docs/arvo/clay/permissions.md)
76+
77+How to manage file permissions in clay.
arvo/clay/permissions.mdnew file+312
@@ -0,0 +1,312 @@
1++++
2+title = "Permissions"
3+weight = 10
4+template = "doc.html"
5++++
6+
7+Here we'll look at file permissions.
8+
9+## Contents
10+- [Introduction](#introduction)
11+- [%perm](#perm) - Set file permissions.
12+- [%cred](#cred) - Add permission group.
13+- [%crew](#crew) - Get permission groups.
14+- [%crow](#crow) - Get group usage.
15+
16+## Introduction
17+
18+For each file or directory, there is both a read permission and a write permission. Each may be set separately and is either a whitelist or a blacklist (but not both). The whitelist/blacklist contains a `set` of ships and/or groups which are allowed or banned respectively. If it's an empty whitelist it means all foreign ships are denied. If it's an empty blacklist it means all foreign ships are allowed.
19+
20+If permissions are not set for a particular file, they will be inherited from the directory in which it resides. If *that* directory has no permissions set, they will be inherited from another level up, and so on to the desk's root directory. If the root directory has no permissions set, it will have the default permissions of an empty whitelist, meaning "deny all".
21+
22+A group is called a `crew` and is just a `set` of ships with a `@ta` name.
23+
24+The permissions for each file or directory are a pair of `dict:clay` where the head is read permissions and the tail is write permissions.
25+
26+A `dict:clay` is this structure:
27+
28+```hoon
29++$ dict [src=path rul=real] :: effective permission
30+```
31+
32+The `src` path is where the permissions were inherited from and the `real` is this structure:
33+
34+```hoon
35+ +$ real :: resolved permissions
36+ $: mod=?(%black %white) ::
37+ who=(pair (set ship) (map @ta crew)) ::
38+ == ::
39+```
40+
41+So if we scry for permissions with a `%p` care, it'll look like:
42+
43+```hoon
44+> .^([r=dict:clay w=dict:clay] %cp /===/lib/strandio/hoon)
45+[r=[src=/ rul=[mod=%white who=[p={} q={}]]] w=[src=/ rul=[mod=%white who=[p={} q={}]]]]
46+```
47+
48+There are four permission-related tasks which you can pass to clay.
49+
50+A `%perm` task is for setting permissions, and the other three are for managing groups:
51+
52+- `%cred` - add permission group
53+- `%crew` - get permission groups
54+- `%crow` - get group usage
55+
56+We'll look at each of these in turn.
57+
58+## %perm
59+
60+This sets permissions for the target file or directory.
61+
62+Note this will replace existing permissions rather than add to them, so if you want to add a ship to an existing whitelist or whatever you'll have to first read the existing permissions, add the ship, then send the whole lot back.
63+
64+A `%perm` tagged `task:clay` looks like:
65+
66+```hoon
67+[%perm des=desk pax=path rit=rite] :: change permissions
68+```
69+
70+The `pax` path is the file or directory whose permissions you want to change, and the `rite` is this structure:
71+
72+```hoon
73++$ rite :: new permissions
74+ $% [%r red=(unit rule)] :: for read
75+ [%w wit=(unit rule)] :: for write
76+ [%rw red=(unit rule) wit=(unit rule)] :: for read and write
77+```
78+
79+Where a `rule` is this structure:
80+
81+```hoon
82++$ rule [mod=?(%black %white) who=(set whom)] :: node permission
83+```
84+
85+...and finally `whom` is this:
86+
87+```hoon
88++$ whom (each ship @ta) :: ship or named crew
89+```
90+
91+As the comment suggests, the `@ta` is the name of a `crew` (group).
92+
93+Example:
94+
95+Here's a generic thread that just sends the given `task:clay` to clay so we can try a few different things:
96+
97+**`send-clay-task.hoon`**
98+
99+```hoon
100+/- spider
101+/+ strandio
102+=, strand=strand:spider
103+^- thread:spider
104+|= arg=vase
105+=/ m (strand ,vase)
106+^- form:m
107+=/ uarg !< (unit task:clay) arg
108+?~ uarg
109+ (strand-fail:strand %no-arg ~)
110+=/ =task:clay u.uarg
111+=/ =card:agent:gall [%pass /foo %arvo %c task]
112+;< ~ bind:m (send-raw-card:strandio card)
113+(pure:m !>(~))
114+```
115+
116+Save it to `ted/send-clay-task.hoon` and `|commit %home`. Now, let's allow `~nes` to read `/gen/hood/hi/hoon`:
117+
118+```hoon
119+> -send-clay-task [%perm %home /gen/hood/hi/hoon %r ~ %white (sy [%.y ~nes]~)]
120+```
121+
122+...and we'll do a `%p` scry to see that the permission was set:
123+
124+```hood
125+> .^([r=dict:clay w=dict:clay] %cp /===/gen/hood/hi/hoon)
126+[r=[src=/gen/hood/hi/hoon rul=[mod=%white who=[p={~nes} q={}]]] w=[src=/ rul=[mod=%white who=[p={} q={}]]]]
127+```
128+
129+You can see that `~nes` is now in the read whitelist. Next, let's try a write permission:
130+
131+```hoon
132+> -send-clay-task [%perm %home /ted %w ~ %white (sy [%.y ~nes]~)]
133+```
134+
135+You can see `~nes` can now write to `/ted`:
136+
137+```hoon
138+> .^([r=dict:clay w=dict:clay] %cp /===/ted)
139+[r=[src=/ rul=[mod=%white who=[p={} q={}]]] w=[src=/ted rul=[mod=%white who=[p={~nes} q={}]]]]
140+```
141+
142+Since we've set it for the whole `/ted` directory, if we check a file inside it we'll see it also has this permission:
143+
144+```hoon
145+> .^([r=dict:clay w=dict:clay] %cp /===/ted/aqua/ames/hoon)
146+[r=[src=/ rul=[mod=%white who=[p={} q={}]]] w=[src=/ted rul=[mod=%white who=[p={~nes} q={}]]]]
147+```
148+
149+...and you'll notice that `src` tells us it's inherited the rule from `/ted`.
150+
151+Now let's try setting both read and write permissions:
152+
153+```hoon
154+> -send-clay-task [%perm %home /gen/help/hoon %rw `[%black (sy [%.y ~nes]~)] `[%white (sy [%.y ~nes]~)]]
155+```
156+
157+```hoon
158+ .^([r=dict:clay w=dict:clay] %cp /===/gen/help/hoon)
159+[r=[src=/gen/help/hoon rul=[mod=%black who=[p={~nes} q={}]]] w=[src=/gen/help/hoon rul=[mod=%white who=[p={~nes} q={}]]]]
160+```
161+
162+Lastly, let's look at deleting a permission rule we've previously set. To do that, we just send a null `(unit rule)` in the `rite`.
163+
164+For example, to remove a read permission (or write if you specify `%w`):
165+
166+```hoon
167+> -send-clay-task [%perm %home /gen/help/hoon %r ~]
168+```
169+
170+```hoon
171+> .^([r=dict:clay w=dict:clay] %cp /===/gen/help/hoon)
172+[r=[src=/ rul=[mod=%white who=[p={} q={}]]] w=[src=/gen/help/hoon rul=[mod=%white who=[p={~nes} q={}]]]]
173+```
174+
175+...and to remove both read and write at the same time:
176+
177+```hoon
178+> -send-clay-task [%perm %home /gen/help/hoon %rw ~ ~]
179+```
180+
181+```hood
182+> .^([r=dict:clay w=dict:clay] %cp /===/gen/help/hoon)
183+[r=[src=/ rul=[mod=%white who=[p={} q={}]]] w=[src=/ rul=[mod=%white who=[p={} q={}]]]]
184+```
185+
186+As you can see it's back to the default inherited from `/`.
187+
188+Here's a breakdown of a `%perm` task:
189+
190+![perm diagram](https://pub.m.tinnus-napbus.xyz/perm-diagram.png)
191+
192+## %cred
193+
194+This simply creates a permission group. The task looks like this:
195+
196+```hoon
197+[%cred nom=@ta cew=crew] :: set permission group
198+```
199+
200+The `nom` is a name for the group and the `crew` is just a `(set ship)`:
201+
202+```hoon
203++$ crew (set ship) :: permissions group
204+```
205+
206+Example:
207+
208+We'll use the same thread from the [%perm](#perm) example. Try:
209+
210+```hoon
211+-send-clay-task [%crew 'foo' (sy ~[~zod ~nec ~bud ~wes ~sev])]
212+```
213+
214+We'll check it with the next kind of task: [%crew](#crew).
215+
216+## %crew
217+
218+This retrieves all permission groups. It looks like:
219+
220+```hoon
221+[%crew ~] :: permission groups
222+```
223+
224+Clay wil return a sign containing a `gift:clay` with a `%cruz` tag. It looks like:
225+
226+```hoon
227+[%cruz cez=(map @ta crew)] :: permission groups
228+```
229+
230+The `cez` is just a map from group name to `crew` which is just a `(set ship)`.
231+
232+Example:
233+
234+Here's a generic thread that sends the given `task:clay` and receives a gift which it just prints to the dojo.
235+
236+**`send-task-take-gift.hoon`**
237+
238+```hoon
239+/- spider
240+/+ strandio
241+=, strand=strand:spider
242+^- thread:spider
243+|= arg=vase
244+=/ m (strand ,vase)
245+^- form:m
246+=/ uarg !< (unit task:clay) arg
247+?~ uarg
248+ (strand-fail:strand %no-arg ~)
249+=/ =task:clay u.uarg
250+=/ =card:agent:gall [%pass /foo %arvo %c task]
251+;< ~ bind:m (send-raw-card:strandio card)
252+;< res=[wire sign-arvo] bind:m take-sign-arvo:strandio
253+~& +>:res
254+(pure:m !>(~))
255+```
256+
257+Save the above to `ted/send-task-take-gift.hoon` and `|commit %home`. Now we'll check for the permission group we created in the [%cred](#cred) example:
258+
259+```hoon
260+> -send-task-take-gift [%crew ~]
261+[%cruz cez={[p=~.foo q={~nec ~bud ~wes ~zod ~sev}]}]
262+```
263+
264+## %crow
265+
266+This is the last group task. It retrieves all files and directories in all desks which have permissions set for the group in question. It will not return inherited permissions, only those explicitly set. It looks like:
267+
268+```hoon
269+[%crow nom=@ta] :: group usage
270+```
271+
272+The `gift:clay` you get back is a `%croz` which looks like:
273+
274+```hoon
275+[%croz rus=(map desk [r=regs w=regs])] :: rules for group
276+```
277+
278+...where `regs` is this structure:
279+
280+```hoon
281++$ regs (map path rule) :: rules for paths
282+```
283+
284+Example:
285+
286+First we'll set a couple of permissions for the `foo` group we created in the [%cred](#cred) section using the `send-clay-task.hoon` thread from the [%perm](#perm) section:
287+
288+```hoon
289+> -send-clay-task [%perm %home /gen/hood/hi/hoon %w ~ %white (sy [%.n 'foo']~)]
290+> -send-clay-task [%perm %home /ted %w ~ %white (sy [%.n 'foo']~)]
291+```
292+
293+Notice we use a `%.n` in the `whom:clay` to indicate a group rather than the `%.y` of a group.
294+
295+Now we'll use the `send-task-take-gift.hoon` thread from the [%crew](#crew) section to try `%crow`:
296+
297+```hoon
298+> -send-receive-task [%crow 'foo']
299+[ %croz
300+ rus
301+ { [ p=%home
302+ q
303+ [ r={}
304+ w
305+ { [p=/gen/hood/hi/hoon q=[mod=%white who={[%.n p=~.foo]}]]
306+ [p=/ted q=[mod=%white who={[%.n p=~.foo]}]]
307+ }
308+ ]
309+ ]
310+ }
311+]
312+```