Fields
The #fields method of your repository controls what fields you want to expose to your users, whether in the table on the index page, the overview on the show page, or the inputs on the edit or new pages.
def fields
[
Field::Id.new(:id),
Field::String.new(:name),
Field::Image.new(:logo),
Field::BelongsTo.new(:industry),
Field::HasMany.new(:people)
]
end
Field types
Uchi ships with a bunch of field types that you can use to build out your user interface. All fields support a set of customization methods that are chained together to provide the experience you want.
Field::BelongsToField::BooleanField::DateField::DateTimeField::FileField::HasAndBelongsToManyField::HasManyField::IdField::ImageField::NumberField::SelectField::StringField::Text
Visibility
Only show a field on specific pages
Use the on method to control what pages to show a field on. For example if your id field should only be visible on the index listing, you can configure it as
Field::Id.new(:id).on(Uchi::View::INDEX)
or you can use the symbol shorthand:
Field::Id.new(:id).on(:index)
See the Views documentation for possible values.
Only show a field for specific records
Giving the field a visible lambda gives you more control over when to render a field.
Field::Number.new(:discount).visible(->(record) { record.discountable? })
The lambda is passed the actual record and the field will be rendered if the lambda returns a truthy value.
Note that this is not usable for index pages. The index table header always shows all configured columns — since there’s no single record to evaluate visibility against. To remove a column from the index page use on([:edit, :new, :show]) instead.
Search
If a repository contains at least one searchable Field, a search field appears on the index page. Whether a field is searchable by default is described on each field’s page. See the Search documentation for more details.
Field::Text.new(:name).searchable(true)
Sorting
When a sortable field appears on the index page, it gets a link to toggle the order of the records based on the field. How to sort a specific field - or to disable it entirely - is configured using the sortable method.
Enable sorting
Most fields are sortable by default, but if you need to enable sortable for a given field you can set it to true:
Field::String.new(:name).sortable(true)
Customize sorting
To customize the query used to sort by a given field, pass a lambda to the sortable method:
Field::String.new(:name).sortable(lambda { |direction:, query:|
query.order(first_name: direction, last_names: direction)
})
The lambda receives the following arguments:
context: TheUchi::Contextwe’re currently processing.direction: A symbol indicating what order to sort; either:ascor:desc.query: TheActiveRecord::Relationthat makes up the current database query
The lambda should return an ActiveRecord::Relation with the desired sort order added.
You can even use this to sort by computed columns via SQL:
Field::Number.new(:users_count).sortable(lambda { |direction:, query:|
query.joins(:users).group(:id).order("COUNT(users.id) #{direction}")
})
Sorting by columns in another table
Thanks to ActiveRecord we can even sort by columns in other tables/models. If you have an Employee model that belongs to a Company and you want to allow your users to sort the employee list by company name, you can configure the field like this:
Field::BelongsTo.new(:company).sortable(lambda { |direction:, query:|
query.joins(:company).order(companies: {name: direction})
})
Disable sorting
To disable sorting a specific field:
Field::Number.new(:calculated_sum).sortable(false)