Skip to content
How-to guides and worked examplesSee the guides →

Customization API ​

Per-option reference for Avo's general configuration. For task-oriented documentation and worked examples, see the Customization guide.

All options are set on the config object in config/initializers/avo.rb:

ruby
# config/initializers/avo.rb
Avo.configure do |config|
  # options listed below
end

This page is the complete reference of Avo's initializer options. Options that belong to a specific feature list their contract here and link to that feature's page for the full guide and worked examples.

Application ​

app_name

The label of the homepage link rendered in the navbar, next to the logo.

ruby
config.app_name = "Avocadelicious"

Also accepts a block, evaluated on each request — useful for I18n.t lookups:

ruby
config.app_name = -> { I18n.t "app_name" }
  • Type: String or Proc returning a String
  • Default: computed from the Rails application class name, humanized

timezone

The global timezone used when displaying date and datetime fields.

ruby
config.timezone = "UTC"
  • Type: String
  • Default: "UTC"

use_browser_timezone

Render server-side dates and times in each visitor's own time zone instead of the app's Time.zone. On by default — set it to false to render everyone in the app's configured zone.

Avo detects the browser's IANA time zone with JavaScript, stores it in the avo.browser_timezone cookie, and wraps every Avo request in Time.use_zone with it. The very first page a browser ever loads still renders in the app zone — no HTTP header carries the time zone — so Avo soft-reloads that one page through Turbo and shows an alert telling the user times are now displayed in their zone. Browsers with cookies disabled keep the app zone and never reload.

ruby
config.use_browser_timezone = false

Off in the test environment

The option defaults to false when Rails.env.test?, because the first-load soft reload races browser tests — assertions run against a page that is about to be replaced. Enable it explicitly in a test if you are testing the time zone behavior itself.

  • Type: Boolean
  • Default: true (false in the test environment)

currency

A currency code stored on Avo.configuration.currency for your own code to read. No built-in field uses it. The Money field takes its currencies from its currencies: option.

ruby
config.currency = "USD"
  • Type: String
  • Default: "USD"

date_format

The display format for every date field that doesn't set its own format, on the Index and Show pages. Since avo >= v4.4.4

ruby
config.date_format = "dd.LL.yyyy"

date_time_format

The display format for every date_time field that doesn't set its own format, on the Index and Show pages. Since avo >= v4.4.4

ruby
config.date_time_format = "dd.LL.yyyy HH:mm"

time_format

The display format for every time field that doesn't set its own format, on the Index and Show pages. A time field reads this option, not date_time_format. Since avo >= v4.4.4

ruby
config.time_format = "HH:mm"

home_path

Where users are redirected when they click the logo or visit Avo's root path. Also accepts a block, which has access to route helpers.

ruby
config.home_path = "/avo/dashboard"

# or

config.home_path = -> { avo_dashboards.dashboard_path(:dashy) }
  • Type: String or Proc returning a String
  • Default: nil — the root path redirects to the first available resource

alert_dismiss_time

How long alerts stay on screen (in milliseconds) before dismissing automatically.

ruby
config.alert_dismiss_time = 8000
  • Type: Integer (milliseconds)
  • Default: 5000

Index view ​

per_page

The default number of records per page on Index views.

ruby
config.per_page = 24
  • Type: Integer
  • Default: 24

per_page_steps

The options listed in the per-page picker on Index views.

ruby
config.per_page_steps = [12, 24, 48, 72]
  • Type: Array of Integers
  • Default: [12, 24, 48, 72]

via_per_page

The number of records shown on association views (has_many tables and similar). Override it for a single field with the per_page option.

ruby
config.via_per_page = 8
  • Type: Integer
  • Default: 8

default_view_type

The view type Index views use when a resource doesn't set its own default_view_type.

ruby
config.default_view_type = :grid
  • Type: Symbol
  • Default: :table
  • Values: :table, :grid, :map, or any registered custom view type

map_view

Defaults for the map view and the location and area fields, which render the same maps.

ruby
config.map_view = {
  styles: :mapbox
}

styles

The light/dark pair Avo renders maps with. Avo picks a provider on its own — OpenFreeMap, free with no account and no API key, or Mapbox when MAPBOX_ACCESS_TOKEN is set. Set this to pin one regardless, or to supply your own pair.

ruby
config.map_view = {
  styles: {
    light: "https://tiles.openfreemap.org/styles/liberty",
    dark: "https://tiles.openfreemap.org/styles/dark"
  }
}

Avo swaps between the two as the color scheme changes. A single map can still override the style with mapkick_options: {style: "..."} — that's one style rather than a pair, so Avo leaves that map alone in dark mode.

  • Type: Symbol or Hash with light and dark keys
  • Default: nil — resolves to :mapbox when MAPBOX_ACCESS_TOKEN is set, :open_free_map otherwise
  • Values: :open_free_map, :mapbox, or a {light:, dark:} Hash of style URLs

first_sorting_option

The direction applied the first time a user sorts a column on the Index view.

ruby
config.first_sorting_option = :asc
  • Type: Symbol
  • Default: :desc
  • Values: :asc, :desc

density

How much vertical space rows take up in Index tables and in dashboard table and list cards.

ruby
config.density = :normal

Dashboard table and list cards can override the global value with self.density:

ruby
class Avo::Cards::ExampleList < Avo::Cards::ListCard
  self.density = :tight
end
  • Type: Symbol
  • Default: :normal
  • Values: :tight, :normal, :relaxed

click_row_to_view_record

Makes the whole Index row a link to the record's Show view.

ruby
config.click_row_to_view_record = false
  • Type: Boolean
  • Default: true

WARNING

Clicking a tr element to behave as a link is not natively supported in HTML. Avo enhances this with JavaScript, which may lead to side effects. Please report any issues on the issue queue.

Renders every id field on the Index view as a link to that record's Show view.

ruby
config.id_links_to_resource = true
  • Type: Boolean
  • Default: false

cache_resources_on_index_view

Caches each grid item on the Index view (table rows are rendered on every request today). The cache key is the record, the resource and policy files' md5, and index_cache_context — by default the current user, the locale and the tenant — so fields shown or hidden per role are cached per user.

ruby
config.cache_resources_on_index_view = false
  • Type: Boolean
  • Default: true in every environment except development

INFO

Role-based visible: fields no longer need this off. The one thing a key cannot carry is params: a field that reads a query-string value is served from whichever request cached the row first, so disable caching there. See Row caching.

index_cache_context

What a row's cache key varies by besides the record. Resolved through Avo::ExecutionContext once per request and appended to every row's key.

ruby
config.index_cache_context = -> { [current_user, I18n.locale, Avo::Current.tenant_id] }
  • Type: Lambda
  • Default: -> { [current_user, I18n.locale, Avo::Current.tenant_id] }

The user record is in the key, not its id, so a role edit busts that user's rows immediately. Narrow it to a role to share cached rows across users who see identical rows — only when nothing a row renders reads the user. A resource can override the resolved value with its own cache_context method.

pagination

Default pagination settings applied to every resource. Accepts the same keys as the per-resource self.pagination option, which also overrides this global default.

ruby
config.pagination = {
  type: :countless
}

# or

config.pagination = -> do
  {
    type: :countless
  }
end
  • Type: Hash or Proc returning a Hash
  • Default: {}

search_debounce

How long Avo waits (in milliseconds) after the user stops typing in a search input before firing the search request.

ruby
config.search_debounce = 300
  • Type: Integer (milliseconds)
  • Default: 300

resource_row_controls_config

Placement and appearance of the row controls on Index tables, globally. A resource can override it with self.row_controls_config.

ruby
config.resource_row_controls_config = {
  placement: :right,
  float: false,
  show_on_hover: false
}
  • Type: Hash, merged over the defaults
  • Default: { placement: :right, float: false, show_on_hover: false }

Full guide and per-key reference: Table view and resource_row_controls_config.

Layout ​

container_width

The width of Avo's main content area, globally or per view.

ruby
# One width for all views
config.container_width = :full

# Or target specific views with a hash
config.container_width = { index: :full }
ValueMax widthClamps fromBehavior
:full——Full viewport width
:lg1536px1536pxConstrained container (default for index)
:md960px1280pxNarrower container (default for show / forms)
:sm720px768pxNarrow, single-column screens

Below its clamp point a width spans the content area, so :sm is the only value that narrows anything on a typical laptop.

Deprecated in Avo 4.1

:large and :small were renamed to :lg and :md so container widths use the same Tailwind scale as every other size option in Avo (size: :sm, width: :xl, ...), and so there is room for narrower widths later. The old names still work and are mapped automatically, but they log a deprecation warning and will be removed in Avo 5.

ruby
config.container_width = :small
config.container_width = :md

config.container_width = { index: :large }       
config.container_width = { index: :lg }          

Note that :small maps to :md, not to :sm. The rename kept every existing screen at the width it already had; :sm is a new, genuinely narrower container that nothing gets automatically.

If you style Avo's container yourself, the CSS classes were renamed to match: .container-large → .container-lg, .container-small → .container-md, and .container-full-width → .container-full.

Hash keys can be individual views — :index, :show, :new, :edit, :create, :update — or group aliases:

AliasExpands to
:forms:new, :edit, :create, :update
:display:index, :show
:single:show, :new, :edit, :create, :update

When a specific key and a group alias target the same view, the specific key wins. Views not mentioned in the hash keep their defaults.

  • Type: Symbol or Hash
  • Values: :full, :lg, :md, :sm
  • Default: { index: :lg, show: :md, new: :md, edit: :md, create: :md, update: :md }
  • Validation: raises ArgumentError for unknown widths or unknown hash keys

The sidebar's three knobs, in one hash merged over the defaults.

ruby
config.sidebar = {
  toggle_visible: true, # show the navbar button that collapses the sidebar on desktop
  resizable: true,      # render the drag-to-resize handle
  default_width: 256    # width in pixels the desktop sidebar starts at
}

toggle_visible — when false the sidebar stays permanently open on desktop. On mobile the toggle is always visible.

resizable — when false the handle is neither rendered nor wired up, and the sidebar stays at default_width. Resizing is a drag-only gesture and so does not satisfy WCAG 2.2 SC 2.5.7 (Dragging Movements). Set this to false if you are working to an AA conformance claim or a VPAT.

default_width — where the sidebar starts before a user drags it. See the Resizable sidebar guide. Clamped into the same 200–480 range as dragging, so the handle can always drag back to it. A value Avo cannot read as an integer falls back to 256 rather than clamping to the minimum. It applies at lg (1024px) and wider only — below that the sidebar is a full-height overlay and keeps its 256px default, so a wide value cannot cover a small screen. A width the user has dragged to takes precedence.

  • Type: Hash, merged over the defaults
  • Default: { toggle_visible: true, resizable: true, default_width: 256 }

Replaces sidebar_toggle_visible

config.sidebar_toggle_visible = false still works and writes into config.sidebar[:toggle_visible], but config.sidebar is the canonical home.

body_classes

Custom CSS classes added to Avo's <body> tag.

ruby
config.body_classes = "custom-theme compact-layout"

# or

config.body_classes = ["custom-theme", "compact-layout"]

# or

config.body_classes = -> {
  current_user&.admin? ? "admin-mode" : ""
}

The block form is evaluated with Avo's ExecutionContext, so it has access to current_user, request, params, and other context methods.

  • Type: String, Array of Strings, or Proc returning either
  • Default: []

hide_layout_when_printing

Hides the sidebar, navbar, and footer when printing an Avo page, leaving only the content.

ruby
config.hide_layout_when_printing = true
  • Type: Boolean
  • Default: false

back_to_top

A floating "Back to top" pill that appears centered below the navbar. It shows once the page is scrolled threshold pixels down and hides again near the top of the page — the scroll direction doesn't matter. Clicking it smooth-scrolls to the top.

It's on by default. Turn it off or move the threshold from your initializer:

ruby
config.back_to_top = {
  enabled: true,  # render the "Back to top" pill
  threshold: 400  # pixels scrolled down before it shows up
}

Raise threshold if you'd rather the pill only show up further down long pages. Any key you leave out keeps its default.

The button's label is translated — override it like any other Avo string:

yaml
# config/locales/avo.en.yml
en:
  avo:
    back_to_top: Back to top
  • Type: Hash, merged over the defaults
  • Default: { enabled: true, threshold: 400 }
  • i18n key: avo.back_to_top ("Back to top")

Behavior ​

resource_default_view

The view Avo treats as a record's main page. Set it to :edit to skip the Show view entirely — row links, redirects after create/update, and association links all go to Edit instead.

ruby
config.resource_default_view = :edit
  • Type: Symbol or String
  • Default: :show
  • Values: :show, :edit

persistence

Retains UI state across requests: pagination (page, per_page), filter selections (static and dynamic), the sort picked from a table header, and the rows selected on a table. Everything but the selection is stored in the session; the selection stays in the browser tab. Before avo 4.3.11, only association pagination and static filter selections were kept.

ruby
config.persistence = {
  driver: :session
}

# or

config.persistence = -> do
  {
    driver: :session
  }
end

Each kind of state has a key next to driver. Set it to false to leave that one out while the others persist. Since avo >= v4.3.11

ruby
config.persistence = {
  driver: :session,
  pagination: true,
  filters: true,
  sorting: true,
  selection: false
}
KeyDefaultDescription
paginationtruepage and per_page on resource and association tables.
filterstrueStatic and dynamic filter selections on resource and association tables. Dynamic ones need avo-dynamic_filters 4.3.2 or newer.
sortingtrueThe sort column and direction picked from a table header, until the user sorts another column or clicks the sorted header a third time (Reset sorting).
selectiontrueThe rows checked on a resource or association table, kept in the browser tab's sessionStorage until an action runs on them, the user signs out, or the tab closes.
  • Type: Hash or Proc returning a Hash
  • Default: { driver: nil, pagination: true, filters: true, sorting: true, selection: true } — no persistence until driver is :session
  • Values: driver: accepts :session or nil; pagination:, filters:, sorting:, and selection: accept true or false

Cookie store size limit

Rails' default cookie session store is limited to 4096 bytes. Storing many pagination states, filter selections, and sorts can exceed it and raise ActionDispatch::Cookies::CookieOverflow. Use a scalable session store such as Redis or MemCache instead.

associations

Global defaults for associations, grouped under a single namespace. Set only the keys you want to change — everything else falls back to the defaults.

ruby
config.associations = {
  lookup_list_limit: 1000,
  frames: {
    loading: :lazy,
    auto_load_for: 15.minutes
  }
}
KeyDefaultDescription
lookup_list_limit1000Caps how many records a belongs_to/attach lookup lists before the belongs_to select notes that there are too many options to show. The attach modal still shows "There are more records available."
frames.loading:lazyRender mode for association turbo frames (has_one, has_many, has_and_belongs_to_many) when a field doesn't set its own loading:. :lazy fetches the frame when revealed; :manual renders a placeholder with a Load button.
frames.auto_load_for15.minutesFor manual frames, how long an opened frame is remembered before the placeholder returns. 0/nil disables it.
  • Type: Hash, deep-merged over the defaults
  • Default: { lookup_list_limit: 1000, frames: { loading: :lazy, auto_load_for: 15.minutes } }

Backward compatibility

The former config.associations_lookup_list_limit = 1000 still works as an alias for config.associations[:lookup_list_limit].

turbo

Configures how Turbo behaves inside Avo.

ruby
config.turbo = -> do
  {
    instant_click: true
  }
end
KeyDefaultDescription
instant_clicktrueStarts loading the page on mousedown instead of waiting for the full click.
  • Type: Hash or Proc returning a Hash
  • Default: { instant_click: true }

default_url_options

Params appended automatically to every path Avo generates through its path helpers, mirroring Rails' default_url_options. Used to implement features like route-level multitenancy.

ruby
config.default_url_options = [:account_id]

With Avo mounted under scope "/account/:account_id", visiting https://example.org/account/adrian/avo sets the account_id param to adrian and appends it to all generated paths.

  • Type: Array of Symbols
  • Default: []

set_context

Attaches a custom payload to the global context object available in resources and actions. The block is instance-evaluated in Avo::ApplicationController, so it has access to _current_user, request, and the Current object.

ruby
config.set_context do
  {
    foo: "bar",
    params: request.params
  }
end
  • Type: block returning any object
  • Default: proc {} — an empty context

_current_user

Don't store your current user here — use the current_user_method config instead.

logger

The logger Avo writes to.

ruby
config.logger = -> {
  ActiveSupport::Logger.new(Rails.root.join("log", "avo.log"))
}
  • Type: Proc returning a Logger
  • Default: a file logger writing to log/avo.log that also echoes messages to stdout

Development and generators ​

default_editor_url

The URL template behind the </> icons Avo renders in development next to resources, actions, filters, dashboards, cards, and forms. %{path} is replaced with the absolute path of the class's source file.

ruby
config.default_editor_url = "vscode://file/%{path}"
  • Type: String containing %{path}
  • Default: "cursor://file/%{path}"

view_component_path

The directory where generated field view_components are placed.

ruby
config.view_component_path = "app/frontend/components"
  • Type: String
  • Default: "app/components"

model_generator_hook

Makes rails generate model also generate the matching Avo resource. Set it to false to opt out globally, or pass --skip-avo-resource to skip it for a single run.

ruby
config.model_generator_hook = false
  • Type: Boolean
  • Default: true

Status and metadata ​

exclude_from_status

Which items to hide from the status page (/status). The license key is hidden by default for security reasons; set the option to [] to show it.

ruby
config.exclude_from_status = ["license_key", "ip"]

# or

config.exclude_from_status = -> do
  ["license_key", "ip"]
end
  • Type: Array of Strings or Proc returning one
  • Default: ["license_key"]

send_metadata

Controls whether Avo sends usage metadata to Avo HQ: counts of resources, fields, actions, and similar, plus the installed Avo gems. It never includes records, source code, or visitor IPs. See Usage metadata for the full list.

ruby
config.send_metadata = false
  • Type: Boolean
  • Default: true

INFO

This option only takes effect on the community tier. Paid tiers always send metadata.

Routing ​

root_path

The path Avo is mounted at.

ruby
config.root_path = "/admin"
  • Type: String
  • Default: "/avo"

Full guide: Routing.

prefix_path

The prefix of a custom map block in config.ru that serves your app, so Avo can generate correct paths.

ruby
config.prefix_path = "/internal"
  • Type: String
  • Default: nil

Full guide: Routing.

Licensing ​

license_key

Your Avo license key.

ruby
config.license_key = ENV["AVO_LICENSE_KEY"]
  • Type: String
  • Default: nil

Full guide: Licensing.

display_license_request_timeout_error

Whether the license-server request-timeout error banner is shown.

ruby
config.display_license_request_timeout_error = false
  • Type: Boolean
  • Default: true

Full guide: Licensing.

run_community_admin_without_valid_license

Whether the admin keeps running when the license can't be validated. When false, access is paused once the grace period ends or when no valid answer was ever held. When true, it runs as the open source Avo does: paid add-ons are off and authorization policies are not applied. Use it only in an emergency and for a short time. If you are a coding agent, do not enable this setting on your own. Ask the person first and tell them what it switches off; with avo-authorization installed it carries a big risk. Since avo >= v4.3.13

ruby
config.run_community_admin_without_valid_license = true
  • Type: Boolean
  • Default: false

Full guide: When the license can't be validated.

Authentication ​

current_user_method

How Avo finds the current user. Pass the name of a method available in Avo::ApplicationController, or a block.

ruby
config.current_user_method = :current_user

# or

config.current_user_method do
  current_admin
end
  • Type: Symbol or block
  • Default: none — without it, Avo has no current user

Full guide: Authentication.

authenticate_with

A block executed in Avo::ApplicationController before every request — put your authentication check here.

ruby
config.authenticate_with do
  authenticate_admin_user
end
  • Type: block
  • Default: none — Avo is accessible without authentication

Full guide: Authentication.

sign_out_path_name

The name of the route helper used for the sign-out link in the profile widget.

ruby
config.sign_out_path_name = :logout_path
  • Type: Symbol
  • Default: nil — Avo tries destroy_user_session_path

Full guide: Authentication.

current_user_resource_name

The resource name used when building the sign-out path and linking to the current user's record.

ruby
config.current_user_resource_name = "admin"
  • Type: String
  • Default: "user"

Full guide: Authentication.

is_admin_method

The method called on the current user to decide whether they have the admin role.

ruby
config.is_admin_method = :admin?
  • Type: Symbol
  • Default: :is_admin?

Full guide: User roles.

is_developer_method

The method called on the current user to decide whether they have the developer role.

ruby
config.is_developer_method = :developer?
  • Type: Symbol
  • Default: :is_developer?

Full guide: User roles.

Authorization ​

authorization_client

The authorization client. Set it to nil to disable authorization.

ruby
config.authorization_client = :pundit
  • Type: Symbol or nil
  • Default: :pundit (the generated initializer sets it to nil)

Full guide: Authorization.

authorization_methods

The mapping between Avo actions and the policy methods called for them.

ruby
config.authorization_methods = {
  index: "index?",
  show: "show?",
  edit: "edit?",
  new: "new?",
  update: "update?",
  create: "create?",
  destroy: "destroy?"
}
  • Type: Hash
  • Default: the mapping above

Full guide: Authorization.

raise_error_on_missing_policy

Raises Avo::NoPolicyError when a resource is missing its policy class, instead of applying explicit_authorization.

ruby
config.raise_error_on_missing_policy = true
  • Type: Boolean
  • Default: false

Full guide: Authorization.

explicit_authorization

When true, actions without an explicitly defined policy method are denied; when false, they are allowed.

ruby
config.explicit_authorization = true
  • Type: Boolean or Proc (evaluated with ExecutionContext)
  • Default: true

Full guide: Authorization.

Localization ​

locale

Forces a locale for Avo's interface.

ruby
config.locale = "en-US"
  • Type: String or Symbol
  • Default: nil — falls back to I18n.default_locale

Full guide: Localization.

locale_selector

Controls the language picker in the top navbar, which lets each user pick their own language. The choice is stored per user in a cookie.

ruby
config.locale_selector = true               # every available locale Avo has translations for
config.locale_selector = [:en, :ro, :de]    # exactly these locales
config.locale_selector = false              # no selector
  • Type: Boolean or Array
  • Default: true

Full guide: Locale selector.

model_attribute_translations

Whether a field without name: or translation_key: reads the model's attribute translation (activerecord.attributes.<model>.<attribute>, then attributes.<attribute>) when none of Avo's own field keys match, before humanizing its id.

ruby
config.model_attribute_translations = false
  • Type: Boolean
  • Default: true

Full guide: Localizing fields.

Appearance ​

appearance

Avo's visual identity — logos, favicons, color scheme, neutral and accent palettes, and chart colors.

ruby
config.appearance = {
  logo: "my_company/logo.png",
  neutral: :slate,
  accent: :blue
}
  • Type: Hash
  • Default: {} — Avo's logo, built-in palettes, and an auto color scheme

Every key has its own entry in the Appearance API; the Appearance guide has the worked examples.

Cache ​

cache_store

The cache store Avo uses. Accepts a store object or a lambda, useful when different environments need different stores.

ruby
config.cache_store = -> {
  ActiveSupport::Cache.lookup_store(:solid_cache_store)
}
  • Type: cache store object or Proc returning one
  • Default: computed — FileStore in tmp/cache outside production; Rails.cache in production unless it's a MemoryStore or NullStore, which fall back to the FileStore

Full guide: Performance.

Keyboard shortcuts ​

hotkeys

Master switches for Avo's keyboard shortcuts.

ruby
config.hotkeys = {
  enabled: true,        # set to false to disable all keyboard shortcuts
  show_key_badges: true # set to false to hide inline kbd badges from the UI
}
  • Type: Hash, merged over the defaults
  • Default: { enabled: true, show_key_badges: true }

Full guide: Keyboard shortcuts.

The sidebar menu, built with Avo's menu DSL.

ruby
config.main_menu = -> {
  section "Resources", icon: "tabler/outline/chart-bar-popular" do
    all_resources
  end
}
  • Type: Proc using the menu DSL
  • Default: nil — Avo generates the menu from your dashboards, resources, and tools

Full guide: Menu editor.

profile_menu

The menu shown when clicking the profile widget in the sidebar footer.

ruby
config.profile_menu = -> {
  link "Profile", path: "/avo/profile", icon: "tabler/outline/user-circle"
}
  • Type: Proc using the menu DSL
  • Default: nil

Full guide: Menu editor.

header_menu

A list of links rendered in the navbar in place of the single app-name link.

ruby
config.header_menu = -> {
  link "Docs", path: "https://docs.example.com"
  link "Support", path: "https://support.example.com"
}
  • Type: Proc using the menu DSL — only link items are rendered
  • Default: nil

Full guide: Header menu.

set_initial_breadcrumbs

The breadcrumbs every page starts with.

ruby
config.set_initial_breadcrumbs do
  add_breadcrumb "Dashboard", "/avo/dashboard"
end
  • Type: block
  • Default: a Home breadcrumb pointing to Avo's root path

Full guide: Breadcrumbs.

Enables the global search and its sidebar navigation section. Values can be Procs, evaluated with ExecutionContext.

ruby
config.global_search = {
  enabled: true,
  navigation_section: true,
  search_on_type: true
}
  • Type: Hash
  • Default: { enabled: true, navigation_section: true }

Full guide and per-key reference: Global search.

search_results_count

How many results are displayed per resource in the search dropdown.

ruby
config.search_results_count = 16
  • Type: Integer
  • Default: 8

Full reference: Search API.

Resources ​

model_resource_mapping

The "default" resource for a model, used when multiple resources exist for the same model and none is specified.

ruby
config.model_resource_mapping = {
  "User": "Avo::Resources::User"
}
  • Type: Hash of model name → resource name
  • Default: {}

Full guide: Resources.

resources

Manually declares the resources Avo loads, skipping the boot-time eager-loading of app/avo/resources. Resources not in the list won't show up.

ruby
config.resources = [
  "Avo::Resources::User",
  "Avo::Resources::Fish"
]
  • Type: Array of Strings
  • Default: nil — resources are auto-discovered

Full guide: Resources.

resource_parent_controller

The controller Avo's generated resource controllers inherit from.

ruby
config.resource_parent_controller = "MyApp::BaseResourcesController"
  • Type: String
  • Default: "Avo::ResourcesController"

Full guide: Resources.

buttons_on_form_footers

Adds the Back and Save buttons to the footer of New and Edit forms too.

ruby
config.buttons_on_form_footers = true
  • Type: Boolean
  • Default: false

Full guide: Resources.

warn_on_unsaved_changes

Asks for confirmation before the user leaves a New or Edit form with unsaved changes. It is on by default; set it to false to turn it off.

ruby
config.warn_on_unsaved_changes = false
  • Type: Boolean
  • Default: true

Full guide and reference: Resources / config.warn_on_unsaved_changes.

Field discovery ​

column_names_mapping

Maps column names to the field type discover_columns uses for them.

ruby
config.column_names_mapping = {
  published_at: {field: :date_time},
  body: {field: :markdown}
}
  • Type: Hash
  • Default: {}

Full guide and reference: Field discovery / column_names_mapping.

column_types_mapping

Maps database column types to the field type discover_columns uses for them.

ruby
config.column_types_mapping = {
  jsonb: {field: :code}
}
  • Type: Hash
  • Default: {}

Full guide and reference: Field discovery / column_types_mapping.

Fields layout ​

field_wrapper_layout

The default layout of every field wrapper — label beside the value (:inline) or above it (:stacked). A field's own stacked: option overrides it.

ruby
config.field_wrapper_layout = :stacked
  • Type: Symbol
  • Default: :inline
  • Values: :inline, :stacked

Full guide: Global stacked layout.

use_stacked_fields

Stacks every field at the CSS level, without needing stacked: true on each one.

ruby
config.use_stacked_fields = true
  • Type: Boolean
  • Default: false

Full guide: Global stacked layout.

TailwindCSS ​

tailwindcss_integration_enabled

Set to false to disable Avo's Tailwind integration even when tailwindcss-ruby is installed.

ruby
config.tailwindcss_integration_enabled = false
  • Type: Boolean
  • Default: true

Full guide: TailwindCSS integration.

tailwindcss_content_sources

The paths Tailwind scans for class names. Each entry is an absolute path or a path relative to Rails.root.

ruby
config.tailwindcss_content_sources = ["app", "lib/components"]
  • Type: Array of Strings or Pathnames
  • Default: nil — Tailwind scans Rails.root.join("app")

Full guide: TailwindCSS integration.