Recourse

Records and forms

The card

A record’s pages sit in a card with one tab per page: a look, a change, then one per resource nested under it, in routes order, counted where the record keeps a counter cache. Tabs are links, each with its own address. A nested page sits in the parent’s card. The card is the layout’s, drawn around whatever template answers, so a host’s own template is its body alone; @recourse_card = false takes it away.

The record’s page

One heading and one value per editable column, two to a row, then Created and Updated. Each value reads as what it is of, the way a cell does, and a missing one reads as a dash. JSON is pretty-printed in a bounded block, a list opens behind 3 items, and an attached file is its picture inside a link to the whole file. An encrypted value is masked, one asterisk per character, with a Show beside it.

The form

new and edit render one form, a field per editable column by its kind — see Models — then one per attachment, two to a row. A column the database generates is never offered. An encrypted value is in the clear, in the field its kind earns.

The browser is told what the validators say, never what the schema does: a length becomes maxlength, a format becomes pattern with a title showing the shape, a numericality a numeric keyboard, a required attribute a required field. An optional field says Optional; a required one shows the shape it expects, michael@example.com.

A foreign key is a combobox with a search box. It becomes a typed field where the other model’s label has a length validator or its table holds over 200 rows — Country code — looked up on the way in, and Must exist where nothing matches.

A rejected write redraws the form with the errors beside the fields, bare and sentence-cased: Can't be blank. Under a field, the column’s comment where the database has one, and on an edit form what a file field is holding now.

What a write leaves

A write goes back to the index — or to the record’s page where no index is routed — with a toast naming the record and leading to its page, Ada was created., and the row tinted while the toast stands. A delete names the model: Comment was deleted.

The delete

The button stands beside the breadcrumb on the record’s page, where destroy is routed, and asks first:

Delete Acme?

12 projects and 3 invoices will be deleted with it.
40 comments will be kept, without its account.
Anything under those goes too.

This cannot be undone.

Counted one level down, one COUNT per has_many. A row a before_destroy refuses stays, and the page says Category could not be deleted. A model may word its own button; see Models.