Configuring Horizon
coollabsio/coolify
A skill your agent uses whenever the user mentions Horizon by name in a Laravel context.
Inspect and change navigation profiles in MDL — home pages, menus, login and not-found pages, and role-based routing.
$ npx skills add mendixlabs/mxcli --skill manage-navigation -a claude-codeProject install by default; add -g for ~/.claude/skills/.
$ gh skill install mendixlabs/mxcli manage-navigation --agent claude-codeProject scope by default; add --scope user for a personal install. Needs GitHub CLI 2.90.0 or later (public preview).
$ git clone --depth 1 https://github.com/mendixlabs/mxcli.git skills-src && mkdir -p .claude/skills && cp -r skills-src/.claude/skills/mendix/manage-navigation .claude/skills/manage-navigation && rm -rf skills-srcUse ~/.claude/skills/ instead of .claude/skills for a personal install. The folder must contain SKILL.md.
Claude Code skills documentation · loads skills from .claude/skills/
Install the "manage-navigation" agent skill from https://github.com/mendixlabs/mxcli/tree/main/.claude/skills/mendix/manage-navigation into .claude/skills/manage-navigation/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "manage-navigation", then confirm the skill loads.Claude Code copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$skill-installer install https://github.com/mendixlabs/mxcli/tree/main/.claude/skills/mendix/manage-navigationType this inside Codex. $skill-installer <name> installs a curated skill from openai/skills. The installer writes to $CODEX_HOME/skills (default ~/.codex/skills). Restart Codex if the skill does not show up.
$ npx skills add mendixlabs/mxcli --skill manage-navigation -a codexProject install goes to .agents/skills/; add -g for ~/.codex/skills/.
$ gh skill install mendixlabs/mxcli manage-navigation --agent codexProject scope by default (.agents/skills/); add --scope user for a personal install.
$ git clone --depth 1 https://github.com/mendixlabs/mxcli.git skills-src && mkdir -p .agents/skills && cp -r skills-src/.claude/skills/mendix/manage-navigation .agents/skills/manage-navigation && rm -rf skills-srcUse ~/.agents/skills/ instead of .agents/skills for a personal install.
Codex skills documentation · loads skills from .agents/skills/
Install the "manage-navigation" agent skill from https://github.com/mendixlabs/mxcli/tree/main/.claude/skills/mendix/manage-navigation into .agents/skills/manage-navigation/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "manage-navigation", then confirm the skill loads.Codex copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$ npx skills add mendixlabs/mxcli --skill manage-navigation -a cursorProject install goes to .agents/skills/; add -g for ~/.cursor/skills/.
$ gh skill install mendixlabs/mxcli manage-navigation --agent cursorProject scope by default (.agents/skills/); add --scope user for a personal install.
$ git clone --depth 1 https://github.com/mendixlabs/mxcli.git skills-src && mkdir -p .cursor/skills && cp -r skills-src/.claude/skills/mendix/manage-navigation .cursor/skills/manage-navigation && rm -rf skills-srcUse ~/.cursor/skills/ instead of .cursor/skills for a personal install.
Cursor skills documentation · loads skills from .cursor/skills/, .agents/skills/, .claude/skills/, .codex/skills/
Install the "manage-navigation" agent skill from https://github.com/mendixlabs/mxcli/tree/main/.claude/skills/mendix/manage-navigation into .cursor/skills/manage-navigation/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "manage-navigation", then confirm the skill loads.Cursor copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$ gemini skills install https://github.com/mendixlabs/mxcli.git --path .claude/skills/mendix/manage-navigation--scope user (default) or --scope workspace; --path is the subfolder of the repo that holds the skill; --consent skips the security confirmation prompt.
$ npx skills add mendixlabs/mxcli --skill manage-navigation -a gemini-cliProject install goes to .agents/skills/; add -g for ~/.gemini/skills/.
$ gh skill install mendixlabs/mxcli manage-navigation --agent gemini-cliProject scope by default (.agents/skills/); add --scope user for a personal install.
$ git clone --depth 1 https://github.com/mendixlabs/mxcli.git skills-src && mkdir -p .gemini/skills && cp -r skills-src/.claude/skills/mendix/manage-navigation .gemini/skills/manage-navigation && rm -rf skills-srcUse ~/.gemini/skills/ instead of .gemini/skills for a personal install, then run /skills reload.
Gemini CLI skills documentation · loads skills from .gemini/skills/, .agents/skills/
Install the "manage-navigation" agent skill from https://github.com/mendixlabs/mxcli/tree/main/.claude/skills/mendix/manage-navigation into .gemini/skills/manage-navigation/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "manage-navigation", then confirm the skill loads.Gemini CLI copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$ gh skill install mendixlabs/mxcli manage-navigationInstalls for Copilot at project scope by default; add --scope user for a personal install. Preview a skill first with gh skill preview. Needs GitHub CLI 2.90.0 or later (public preview).
$ npx skills add mendixlabs/mxcli --skill manage-navigation -a github-copilotProject install goes to .agents/skills/; add -g for ~/.copilot/skills/.
$ git clone --depth 1 https://github.com/mendixlabs/mxcli.git skills-src && mkdir -p .github/skills && cp -r skills-src/.claude/skills/mendix/manage-navigation .github/skills/manage-navigation && rm -rf skills-srcUse ~/.copilot/skills/ instead of .github/skills for a personal install. Commit .github/skills so cloud agent and code review can use it.
GitHub Copilot skills documentation · loads skills from .github/skills/, .claude/skills/, .agents/skills/
Install the "manage-navigation" agent skill from https://github.com/mendixlabs/mxcli/tree/main/.claude/skills/mendix/manage-navigation into .github/skills/manage-navigation/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "manage-navigation", then confirm the skill loads.GitHub Copilot copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$ npx skills add mendixlabs/mxcli --skill manage-navigation -a opencodeOpenCode documents no install command of its own. Project install goes to .agents/skills/; add -g for ~/.config/opencode/skills/.
$ gh skill install mendixlabs/mxcli manage-navigation --agent opencodeProject scope by default (.agents/skills/); add --scope user for a personal install.
$ git clone --depth 1 https://github.com/mendixlabs/mxcli.git skills-src && mkdir -p .opencode/skills && cp -r skills-src/.claude/skills/mendix/manage-navigation .opencode/skills/manage-navigation && rm -rf skills-srcUse ~/.config/opencode/skills/ instead of .opencode/skills for a personal install.
OpenCode skills documentation · loads skills from .opencode/skills/, .claude/skills/, .agents/skills/
Install the "manage-navigation" agent skill from https://github.com/mendixlabs/mxcli/tree/main/.claude/skills/mendix/manage-navigation into .opencode/skills/manage-navigation/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "manage-navigation", then confirm the skill loads.OpenCode copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
manage-navigationInspect and change navigation profiles in MDL — home pages, menus, login and not-found pages, and role-based routing.
Manage Navigation is an agent skill from mendixlabs/mxcli. Inspect and change navigation profiles in MDL — home pages, menus, login and not-found pages, and role-based routing. Use when asked to change where the app opens, restructure the menu, or route roles to different home pages.
Its SKILL.md is about 6.5k tokens, which your agent loads only when the skill is triggered. It is a single SKILL.md file with no bundled scripts.
It sits in Backend & APIs, covering Authorization and RBAC. The repository describes itself as: Mendix cli tool, a headless way to work with Mendix projects. Enables Mendix projects for use with 3rd party agentic coding tools like Claude Code and Copilot. Includes a… The licence is Apache-2.0.
Read from SKILL.md and the folder at commit 20a6c89. It shows what the files ask for, not the result of running them.
Pre-approves nothing: there is no allowed-tools line, so your agent's usual permission prompts apply.
From allowed-tools in the SKILL.md frontmatter.
No scripts in the folder and no shell commands in SKILL.md (its code samples are sql).
From the folder's file list and the shell code blocks in SKILL.md.
Hosts in commands or code, which the agent is likely to contact:
docs.mendix.comFrom URLs in SKILL.md, links to its own repository left out.
Names no API keys, tokens, secrets or passwords.
From names ending in _API_KEY, _TOKEN, _SECRET, _KEY or _PASSWORD in SKILL.md.
Manage Navigation loads about 6.5k tokens when it runs. Until then it costs about 61 tokens; SKILL.md has 2,844 words of instructions outside code blocks.
Estimates: characters ÷ 4, the usual rule of thumb; real counts depend on the model's tokenizer. Scripts and assets cost tokens only if the agent reads them.
The automated check found no risky patterns in SKILL.md.
Automated static check — not a guarantee. Review scripts before installing. It scans the text of SKILL.md for risky patterns (piping downloads into a shell, reading credential files, hidden Unicode, destructive commands); files beside SKILL.md are not scanned.
The full file from mendixlabs/mxcli at commit 20a6c89, republished under its Apache-2.0 licence (© mendixlabs). 2,844 words, ~6,504 tokens.
.claude/skills/manage-navigation/SKILL.md (or your agent's skills folder).This skill covers inspecting and modifying Mendix navigation profiles via MDL: home pages, menu items, login pages, role-based routing, and navigation catalog queries.
Use when the user asks to:
Navigation Profiles — Every Mendix project has navigation profiles: Responsive, Phone, Tablet, and optionally Native. Each profile has its own home page, menu, and login page. The web kinds are a closed set and create or replace navigation will create one that does not exist yet:
| Online | Offline twin |
|---|---|
Responsive | ResponsiveOffline |
Phone | PhoneOffline |
Tablet | TabletOffline |
An invented name (Mobile, Desktop) is an error, not a new profile: Mendix routes on User-Agent to its own kinds, so a profile the platform does not define can never be reached. Native profiles are a different document type and are not creatable from MDL.
Offline Profiles — An offline profile makes the app work without a connection (a PWA with a local database that syncs). It is not a different document — same properties as its online twin — but it constrains every page it can reach, see below.
Home Page — The default page shown after login. Can be a PAGE or MICROFLOW.
Role-Based Home Pages — Override the default home page per user role (e.g., admins see a dashboard, users see a task list).
Menu Items — Hierarchical menu tree. Each item has a caption and optionally targets a PAGE or MICROFLOW. Sub-menus nest with menu 'caption' { ... }.
Menu Documents — A separate document type (Menus$MenuDocument) holding a reusable menu that a menu widget points at, e.g. Atlas_Core's Phone_Menu. Not the same thing as a profile's menu, though both are built from the same items, so the item syntax is identical. Managed with create/describe/drop menu — see below.
Login Page — Custom login page (optional; Mendix provides a default).
Not-Found Page — Custom 404 page (optional).
-- Summary of all navigation profiles (home pages, menu counts)
list navigation;
-- Full MDL description of a profile (round-trippable output)
describe navigation Responsive;
describe navigation; -- all profiles
-- Menu tree for a specific profile
list navigation menu Responsive;
list navigation menu; -- all profiles
-- Home page assignments across all profiles and roles
list navigation homes;This command fully replaces a navigation profile's configuration. All clauses are optional — omitted clauses clear that section. The output from describe navigation can be pasted back directly.
mdl 1;
create or modify navigation Responsive
home page MyModule.Home_Web
login page Administration.Login;Add for <UserRole> to override the home page for specific user roles. The
role is a bare name — user roles are project-level and have no module part:
mdl 1;
create or modify navigation Responsive
home page MyModule.Home_Web
home page MyModule.AdminDashboard for Administrator
home page MyModule.CustomerPortal for Customer
login page Administration.Login;Never write a module-qualified role here. for Administration.Administrator
is a module role, and Mendix cannot load a project containing one in this
position:
StorageLoadException: Role based home page has an invalid value '' for property
UserRole. The text 'Administration.Administrator' is not a valid UserRoleIdentifier.That is worse than a build error — it happens before checking runs, so there is
no error code and no line number, and mx check exits non-zero without the
"The app contains: N errors" line. The two role kinds are easy to confuse
because they share names: a blank app has a user role Administrator and module
roles called Administrator in three modules. List the real ones with
list user roles; mxcli check --references refuses the wrong form.
The menu items are the profile's children, in { ... } after its clauses, like a page's widgets — no ; between them. The block replaces the entire menu. Use menu item 'Caption' ( OnClick: … ) for leaf items and menu 'caption' { ... } for sub-menus. OnClick: takes the action expression a button's Action: takes, limited to what a menu item can do: show page M.P, call microflow M.F, call nanoflow M.N, open link 'https://…', create object M.E then show page M.E_New, sign out or nothing — each with the button's with ( … ) settings (ProgressBar, ProgressMessage, Confirmation/ProceedCaption/CancelCaption, Asynchronous and FormValidations for a microflow, DisabledDuringExecution). Save, delete, close page and complete task act on a page's object and are refused on a menu item:
mdl 1;
create or modify navigation Responsive
home page MyModule.Home_Web
login page Administration.Login
{
menu item 'Home' ( OnClick: show page MyModule.Home_Web )
menu 'Orders' {
menu item 'All Orders' ( OnClick: show page Orders.Order_Overview )
menu item 'New Order' ( OnClick: show page Orders.Order_New )
}
menu 'Admin' {
menu item 'Users' ( OnClick: show page Administration.Account_Overview )
menu item 'Run Report' ( OnClick: call microflow Reports.ACT_GenerateReport with (ProgressBar: Blocking, ProgressMessage: 'Generating…') )
}
menu item 'Reports' ( OnClick: call nanoflow Reports.NAV_ShowReports )
menu item 'Docs' ( OnClick: open link 'https://docs.mendix.com' )
menu item 'New order' ( OnClick: create object Orders.Order then show page Orders.Order_New )
};Describe prints every stored action this way, so describe → exec writes nothing. What
the expression cannot spell — a show page's page title override, an open link's
link type other than Web — is flagged with a -- comment; a rewrite keeps it
while the item's action is unchanged (same caption, same action), and loses it if
the item is renamed or its action changed. An action describe cannot print at all
is flagged too, and an item that states no OnClick keeps it.
The old spelling — menu ( menu item 'Home' page M.Home; menu 'Admin' ( … ); ),
the action and icon as clauses and ; after each item — still parses and warns
(MDL-DEPR121, MDL-DEPR122); mxcli fmt --upgrade rewrites it.
Give every menu item an icon. It is optional in the grammar and mxcli check
warns when it is missing (MDL077), because the navigation sidebar collapses
to an icon rail and that is the state most users leave it in: a collapsed item
shows its icon, and one without falls back to the first few characters of its
caption — rarely enough to tell Orders from Order lines. Nothing else catches
it. The model builds, mx check passes, and the menu is simply hard to use.
Both menu item and menu 'caption' { ... } take an Icon: in their property
list, in one of three forms — Mendix stores three different icon elements, not
three spellings of one value:
menu item 'Home' ( OnClick: show page M.Home, Icon: Atlas_Core.Atlas.home ) -- icon collection
menu item 'Close' ( OnClick: show page M.Close, Icon: glyph 57377 ) -- numeric glyph code
menu item 'Logo' ( OnClick: show page M.Logo, Icon: image M.Images.logo ) -- image collection
menu 'Admin' ( Icon: Atlas_Core.Atlas.user ) { … } -- a sub-menu's iconThe bare form is the icon-collection icon and is what you normally want. Use
glyph only to reproduce a legacy icon a project already has — describe navigation emits it for you — and image for a picture from an image
collection, which is a different document from an icon collection.
Do not invent a glyph code. It is a bare integer that nothing resolves, so a
code the Mendix font does not define passes mxcli check AND mx check at 0
errors and then breaks mxbuild --target=deploy with "An exception occurred
while exporting layout '<some layout>'" — a message naming a document that is
not the cause. mxcli check now warns (MDL078) against the 247 codes the
shipped font defines, but a glyph is still an unchecked number where an icon
collection reference is a resolved model reference. Browse the codes with list glyphs
(list glyphs like 'star' searches by name, describe glyph 57350 goes the
other way), or use Icon: Atlas_Core.Atlas.<name> and list the names with
describe icon collection Atlas_Core.Atlas.
The icon-collection form is a qualified name — a model reference, written like every other reference in MDL, not a string:
mdl 1;
create or modify navigation Responsive
home page MyModule.Home_Web
{
menu item 'Home' ( OnClick: show page MyModule.Home_Web, Icon: Atlas_Core.Atlas.home )
menu 'Orders' ( Icon: Atlas_Core.Atlas."shopping-cart" ) {
menu item 'All Orders' ( OnClick: show page Orders.Order_Overview,
Icon: Atlas_Core.Atlas."list-bullets" )
}
};Hyphenated names are double-quoted (Atlas_Core.Atlas."align-center") —
a hyphen does not lex as an identifier, so the segment is quoted exactly as a
keyword-colliding name would be. Plain names need no quotes, including ones that
happen to be MDL keywords (home, user, add). Atlas_Core ships three
collections: Atlas (outline), Atlas_Filled, and Atlas_Styling. List what
is actually available in your project rather than guessing a name:
list icon collections;
describe icon collection Atlas_Core.Atlas;Only the icon-collection form is writable. Studio Pro can also attach a
glyph icon (a numeric character code) or an image icon (pointing into an
image collection). Those are different elements with different fields, so MDL
does not write them — and describe navigation reports them as a comment rather
than emitting an Icon: that would silently convert one into the other on
replay:
menu item 'Close' ( OnClick: show page MyModule.Close )
-- icon System.Images.Close (Forms$ImageIcon) is not reproducible by CREATE NAVIGATION; set it in Studio ProAn offline profile downloads nothing until its entities are given a sync
mode. Without a SYNC block the app builds, routes and installs as a PWA — and
shows an empty screen. That is the single most common way an offline profile
looks broken while every check passes.
mdl 1;
create or modify navigation PhoneOffline
home page MyModule.Mobile_Dashboard
sync (
sync MyModule.Setting online;
sync MyModule.Vehicle all;
sync MyModule.Trip where [Distance > 0];
sync MyModule.AuditEntry never;
sync MyModule.Lookup none;
sync MyModule.Draft none preserve data;
);| MDL | Meaning |
|---|---|
online | fetched from the server, never held on the device |
all | every object downloaded |
where [<xpath>] | only the objects the XPath selects |
never | not synchronized |
none | not downloaded; anything already on the device is dropped |
none preserve data | not downloaded; what is on the device stays |
The words are not Studio Pro's captions. Its dialog shows "All Objects" and
"By XPath"; neither is a value Mendix stores. all and where are. Copying a
caption out of the UI gives a parse error rather than a broken document, which
is deliberate.
where implies the constrained mode rather than naming it, so a constraint
without a mode and a mode without a constraint are both unspellable.
Use the bracket form. It takes the XPath verbatim — nothing inside is escaped, so quoted literals stay readable:
sync MyModule.Team where [contains(Name, 'abc')];A quoted where '<xpath>' still parses, but every quote inside it must be
doubled — and a stored constraint already carries Mendix's own escaping, so the
two compose into runs of six quotes. describe navigation emits the bracket
form. This is the general problem tracked as mendixlabs/mxcli#750.
The block replaces the stored list, the way the { ... } menu block replaces the menu.
Omitting it leaves the stored configuration alone.
Ask the catalog which entities sync, rather than reading the profile.
select EntityQualifiedName, SyncMode, XPathConstraint
from CATALOG.OFFLINE_ENTITY_CONFIGS where ProfileName = 'PhoneOffline';And before changing an entity, ask which profiles download it — an offline change reaches every device that already synced:
list references to MyModule.Order;The sync row names the profile. Every mode produces one, including the
modes that download nothing: a profile with sync X never still names X,
so renaming or dropping it leaves the configuration dangling.
Errors when the server rejects an object. Studio Pro's "Throw error when server rejects objects during synchronization" checkbox:
mdl 1;
create or modify navigation PhoneOffline
home page MyModule.Mobile_Dashboard
on sync error continue; -- default is `throw`It uses the phrase MDL already has for failure handling — a microflow's
on error continue — rather than a keyword of its own. Omitting the clause
leaves the stored value alone; describe navigation emits it only when it is
not the default, so existing scripts stay quiet.
Compatibility mode has no syntax. mxcli reads it, preserves it across a
rewrite, and describe navigation flags any entity that has it on — it is never
silently dropped.
An empty { } menu block removes all menu items:
mdl 1;
create or modify navigation Responsive
home page MyModule.Home_Web
{};mdl 1;
create or modify navigation Responsive
home page MyModule.Home_Web
not found page MyModule.Custom404;Use home microflow instead of home page to run a microflow on login:
mdl 1;
create or modify navigation Responsive
home microflow MyModule.ACT_ShowHome;A native profile's flow home is a nanoflow: home nanoflow MyModule.NAV_Home
(home nanoflow on a web profile is refused). On a native profile mxcli writes the
home pages and the sync ( … ) block only — a { } menu block (the bottom bar),
login page, not found page and on sync error are refused, and describe lists
the bottom bar as comments.
The DESCRIBE output is directly executable. Use this pattern to inspect, modify, and re-apply:
mdl 1;
-- Step 1: Inspect current state
describe navigation Responsive;
-- Step 2: Copy the output, modify as needed, paste back
create or modify navigation Responsive
home page MyModule.Home_Web
login page Administration.Login
{
menu item 'Home' ( OnClick: show page MyModule.Home_Web )
menu item 'New Feature' ( OnClick: show page MyModule.NewFeature )
};
-- Step 3: Verify
describe navigation Responsive;After refresh catalog full, navigation references appear in the REFS table:
refresh catalog full;
-- Find all pages that are navigation entry points
select SourceName, TargetName, RefKind
from CATALOG.REFS
where RefKind in ('home_page', 'menu_item', 'login_page');
-- What references point to a specific page?
list references to MyModule.Home_Web;
-- Impact analysis: what breaks if I change this page?
list impact of MyModule.Home_Web;
-- Full context for a page (includes navigation references)
describe context of MyModule.Home_Web;Set up navigation for a freshly created project:
mdl 1;
-- Create home page
create page MyModule.Home_Web
(
title: 'Home',
layout: Atlas_Core.Atlas_Default
)
{
container ctnMain {
dynamictext txtWelcome (content: 'Welcome!')
}
};
-- Configure navigation
create or modify navigation Responsive
home page MyModule.Home_Web
{
menu item 'Home' ( OnClick: show page MyModule.Home_Web )
};After creating a new page, add it to the menu:
mdl 1;
-- First inspect current menu
describe navigation Responsive;
-- Then re-apply with the new item added (copy existing + add new)
create or modify navigation Responsive
home page MyModule.Home_Web
login page Administration.Login
{
menu item 'Home' ( OnClick: show page MyModule.Home_Web )
menu item 'Customers' ( OnClick: show page MyModule.Customer_Overview ) -- new
menu 'Admin' {
menu item 'Users' ( OnClick: show page Administration.Account_Overview )
}
};A profile menu lives inside a navigation profile and is edited with
create or modify navigation. A menu document is its own document, and a
menu widget on a page points at it. Atlas_Core ships Phone_Menu and
Tablet_Menu.
Tell them apart by which command reads them:
list navigation menu; -- the menu inside each profile
describe menu Atlas_Core.Phone_Menu; -- a standalone menu documentMenu documents use the same item syntax as the profile's { ... } menu block:
mdl 1;
create or modify menu MyModule.Main_Menu {
menu item 'Home' ( OnClick: show page MyModule.Home_Web, Icon: Atlas_Core.Atlas.home )
menu item 'Run' ( OnClick: call microflow MyModule.DoThing )
menu 'Admin' {
menu item 'Accounts' ( OnClick: show page Administration.Account_Overview )
}
menu item 'Plain'
};
drop menu MyModule.Main_Menu;describe menu emits a re-executable create or modify statement, so
describe → edit → exec is the normal editing loop for a menu your MDL scripts own.
Menus and navigation have no patch statement, so for one maintained in Studio Pro
keep the edit to the items you mean to change, then describe it again after
exec and compare with the original; a difference you did not make is a loss (see
choose-edit-mode).
or modify replaces the whole item list. An omitted item is a removed item,
exactly as with create or modify navigation. The document's identity and
export level are preserved, so menu widgets pointing at it keep working.
Menu item. Point the item at a
parameterless page, or call a microflow that opens the page.describe flags those on their own
comment line rather than dropping them silently, so re-running the output
loses that icon visibly.An offline profile is created the same way as any other:
mdl 1;
create or modify navigation TabletOffline
home page Maintenance.Request_Overview
{
menu item 'Requests' ( OnClick: show page Maintenance.Request_Overview )
};Two things about it are worth knowing before you do.
It breaks pages the statement never mentions. Mendix restricts every page an offline profile can reach: an attribute may be bound across at most one association hop. A longer path is CE6206 — "Attribute paths with multiple steps cannot be used on pages that are accessible through an offline-based navigation."
Request_Asset/AssetName one hop fine
Request_Asset/Asset_Site/SiteName two hops CE6206Those pages were valid before. Adding the profile is what invalidated them, and the build fails somewhere with no obvious connection to the statement you ran. mxcli reports them when it creates the profile:
Navigation profile 'TabletOffline' created.
Warning: TabletOffline is an offline profile, and 3 documents in this project bind
an attribute across more than one association.
Mendix rejects a multi-step attribute path with CE6206 on any page reachable from
an offline profile — one hop is allowed, two are not.
page Maintenance.Request_Overview: Maintenance.Site.SiteName (2 steps)
...It is a warning, not a refusal: whether a page is actually reachable from the profile takes the whole page graph, which mxcli does not walk. The fix is either to keep the page off the offline profile, or to bring the value one hop closer — add an attribute to the intermediate entity and keep it in step.
The synchronization config is derived, not authored. offlineEntityConfigs
starts empty and Studio Pro fills it from the entities the reachable pages use;
only rows that differ from the defaults (syncMode: Online, no constraint) are
stored. MDL does not author per-entity sync modes — set those in Studio Pro.
Responsive/Phone/Tablet, or their *Offline twins) — an invented name is an error, not a new profileModule.Name)for clauses are fully qualified (Module.Role){ } with no ; between them; sub-menu items in menu 'caption' { ... }( OnClick: … ) with show page, call microflow, call nanoflow, open link, create object, sign out or nothing — not save / delete / close pageIcon: is a qualified name (not a string); hyphenated segments are double-quoteddescribe icon collection Module.Name, do not guessdescribe navigation to verify changes after applyingcreate menu and not a profile menu — list navigation menu vs describe menu tells them apartCREATE NAVIGATION … SYNC (…))an offline navigation profile downloads nothing until each entity has a sync mode, so a profile mxcli created built, routed and installed as a PWA and showed an empty app — with mxcli check, exec and mx check all clean. The six mode words are the members Mendix stores, not Studio Pro's captions (its "All Objects" is ALL, its "By XPath" is WHERE), and a caption is refused rather than written — the CE0463 gallery defect wearing a different hat. WHERE takes the XPath in brackets, verbatim: the quoted form doubles every quote, and a stored constraint already carries Mendix's own escaping, so the two compose into runs of six (mendixlabs/mxcli#750, and PROPOSAL_first_class_expressions.md). The write is an overlay keyed by entity, so CompatibilityMode — stored, unauthorable — survives a rewrite; every reference config carries false, so only a synthetic true case distinguishes a correct writer from one that always emits false. DownloadMode/ShouldDownload are deliberately not written though gen declares them: zero occurrences in ako/TestApp, and a property Studio Pro fills in on load is one whose emission makes a document Studio Pro cannot open. Creating the profile stays modelsdk-only (a fourteen-key document pinned to a Studio Pro reference); the SYNC block works on both engines. ON SYNC ERROR THROW|CONTINUE writes ThrowPartialSyncError, a property neither generated source declares (zero occurrences in gen and in generated/metamodel), so it is read from element.Base.Raw() and written as a raw key. The spec field is a pointer: the property is a bare bool with no unset value, so a non-pointer would reset it on every rewrite that never mentions the clause. Absent reads as true, matching every reference profile and Studio Pro's checked-by-default box. Both halves are in the catalog: CATALOG.OFFLINE_ENTITY_CONFIGS holds one row per configured entity (the profile's OfflineEntityCount said how many and nothing else), and a configured entity emits a sync edge into CATALOG.REFS so list references to Mod.Entity names the profiles that download it. Every mode gets an edge, including the ones that download nothing — a profile with sync X never still names X, so renaming or dropping it leaves the config dangling, which is exactly what the edge exists to reveal. and docs/11-proposals/PROPOSAL_offline_sync_configuration.md
standalone Menus$MenuDocument, the reusable menu a menu widget points at (Atlas_Core's Phone_Menu/Tablet_Menu) — not the menu inside a navigation profile, though both are built from the same items, so the item syntax is shared with CREATE NAVIGATION's { ... } menu block. DESCRIBE is round-trippable. Written through gen+codec, which is load-bearing: Studio Pro's menu documents carry typed-array marker 3 on the item collection and each item's sub-items (the codec default), while the navigation writers hand-build items with marker 1 — unverified whether that is a latent navigation bug or a real difference, so navigation is left alone. Authoring is modelsdk-only; legacy refuses. A menu item cannot open a page with required parameters (CE1571). Its actions and icons (all three kinds) round-trip as a navigation menu's do
© mendixlabs, Apache-2.0. Rendered from Markdown: HTML in the file is shown as text, images as links, and headings moved down two levels. Raw file
Just SKILL.md in .claude/skills/mendix/manage-navigation of mendixlabs/mxcli.
Open the folder on GitHubat commit 20a6c89
Manage Navigation next to the 5 skills that share the most tags, products or categories with it. Stars are the repository's; “used in” counts other GitHub owners with a copy.
| Skill | Stars | Used in | Tokens | Auto-check | Licence | Repo updated |
|---|---|---|---|---|---|---|
| Manage Navigation this skillmendixlabs/mxcli | 128 | — | ~6.5k | Automated safety check: Pass | Apache-2.0 | |
| Configuring Horizoncoollabsio/coolify | 63k | 4 repos | ~898 | Automated safety check: Pass | MIT | |
| K8s Security PoliciesCybereason-Public/owLSM | 280 | 12 repos | ~2k | Automated safety check: Pass | GPL-2.0 | |
| Payloadpayloadcms/payload | 45k | 5 repos | ~6.2k | Automated safety check: Pass | MIT | |
| Convex Setup Authspokvulcan/poker-planning | 114 | 8 repos | ~1.8k | Automated safety check: Pass | MIT | |
| Abp Authorizationabpframework/abp | 14k | — | ~1.3k | Automated safety check: Pass | LGPL-3.0 |
coollabsio/coolify
A skill your agent uses whenever the user mentions Horizon by name in a Laravel context.
Cybereason-Public/owLSM
Comprehensive guide for implementing NetworkPolicy, PodSecurityPolicy, RBAC, and Pod Security Standards in Kubernetes.
payloadcms/payload
A skill your agent uses when working with Payload projects (payload.config.ts, collections, fields, hooks, access control, Payload API).
spokvulcan/poker-planning
Sets up Convex auth, identity mapping, and access control. An agent skill from spokvulcan/poker-planning.
abpframework/abp
ABP permission system - PermissionDefinitionProvider, [Authorize] attribute, CheckPolicyAsync, IsGrantedAsync, ICurrentUser, IPermissionManager, multi-tenancy side.
bagofwords1/bagofwords
Exhaustively audit the UI control by control and role by role — enumerate every button, link, and input on a set of pages, write down what each is supposed to do (derived from the handler code and…
mendixlabs/mxcli
Push OData query options into the SQL of a Mendix resource served by a read microflow, so $filter, $orderby, $top, $skip, $count and the key lookup reach the database instead of being silently…
mendixlabs/mxcli
Chart a Mendix app with Vega-Lite through a pluggable widget that takes the specification and the data as separate properties, so the model emits rows and never assembles a chart payload.
mendixlabs/mxcli
Author Mendix AI agent documents in MDL — Model, Knowledge Base, Consumed MCP Service and Agent, with variables, tools and multi-line prompts.
mendixlabs/mxcli
Run set-based INSERT, UPDATE and DELETE against Mendix entities through OQL statements, which the runtime supports and Studio Pro cannot author.
mendixlabs/mxcli
Define event-driven APIs over Kafka with Mendix business event services — publish and subscribe contracts, CREATE/DROP/DESCRIBE.
mendixlabs/mxcli
Search the Mendix Catalog platform service registry (catalog.mendix.com) from the CLI to find services published across an organisation.
Categories
Inspect and change navigation profiles in MDL — home pages, menus, login and not-found pages, and role-based routing. Manage Navigation is an agent skill from mendixlabs/mxcli. Inspect and change navigation profiles in MDL — home pages, menus, login and not-found pages, and role-based routing.
Manage Navigation fits situations like: asked to change where the app opens; restructure the menu; route roles to different home pages.
Run `npx skills add mendixlabs/mxcli --skill manage-navigation -a claude-code`. Or copy the skill folder (.claude/skills/mendix/manage-navigation in mendixlabs/mxcli) into .claude/skills/manage-navigation in your project. Claude Code loads it when a task matches its description.
Run `npx skills add mendixlabs/mxcli --skill manage-navigation -a codex`. Or copy the skill folder (.claude/skills/mendix/manage-navigation in mendixlabs/mxcli) into .agents/skills/manage-navigation in your project. Codex loads it when a task matches its description.
Cursor, Gemini CLI, GitHub Copilot and OpenCode also load SKILL.md folders. With the skills CLI, run `npx skills add mendixlabs/mxcli --skill manage-navigation -a cursor` (or -a gemini-cli, github-copilot or opencode for the others). To copy it by hand, put the folder in .cursor/skills/manage-navigation, .gemini/skills/manage-navigation, .github/skills/manage-navigation and .opencode/skills/manage-navigation in your project.
SKILL.md names no scripts, command-line tools or credentials: Manage Navigation is instructions for the agent only.
SKILL.md names 1 domain. In commands or code: docs.mendix.com; the agent is likely to contact it when it follows the instructions. This is read from the text; nothing was executed.
Our automated static check of SKILL.md found no risky patterns, such as piping downloads into a shell, reading credential files or hidden Unicode. It is not a guarantee. Review the folder before installing.
Manage Navigation is published under the Apache-2.0 licence (the repository's licence). It allows redistribution, so the full SKILL.md is shown on this page.
About 6.5k tokens (SKILL.md is roughly 26k characters). Agents keep only the skill's name and description in context until a task matches; then they load SKILL.md in full.
Skills that share tags, products or a category with Manage Navigation: Configuring Horizon (coollabsio/coolify, 63k stars), K8s Security Policies (Cybereason-Public/owLSM, 280 stars), Payload (payloadcms/payload, 45k stars) and Convex Setup Auth (spokvulcan/poker-planning, 114 stars). The comparison table on this page puts their stars, adoption, token cost, safety result and licence side by side.
mendixlabs (a GitHub organization) maintains it in mendixlabs/mxcli, which has 128 GitHub stars. The repository holds 72 skills in this directory. The repository was last updated on October 7, 2026.
Source: mendixlabs/mxcli on GitHub. Facts on this page come from the repository at the commit we read; the author's words are quoted as theirs.