Releases
Released
Features:
- Add physical MFA like yubikey via webauthn, or passkey
- Chat history for the AI chat
- Passkey support
- Adding AGENTS.md file
Passkeys, persistent AI chat history, and stricter quality checks.
Passkeys
Users can now register passkeys (Face ID, Touch ID, hardware security keys) from their security settings. Up to 5 per user. Two modes ship:
- Primary auth - sign in with a passkey, no password needed. A “Sign in with passkey” button appears on the login page.
- Second factor - passkey as 2FA on top of password, mirrors the existing TOTP flow.
Passkeys are phishing-resistant by design. The credential is cryptographically bound to your domain. Fully optional - existing auth methods (password, magic link, OAuth, TOTP) are untouched.
Persistent admin chat history
Admin AI chat conversations are now stored in the database and survive page reloads and server restarts. The sidebar lists recent conversations so you can pick up where you left off. History is scoped per admin user.
Stricter quality checks
mix quality now runs credo --strict and dialyzer alongside the existing checks. Fresh clones pass both out of the box.
Fixed
- Sidebar user profile dropdown no longer gets clipped when the sidebar is collapsed
- Changelog admin: publish modal no longer crashes with an atom upcase error, and read stats load correctly
- Changelog admin: form handlers now use the correct params key — validate/save events were raising a FunctionClauseError
Features:
Petal Pro v4.0.0 — a major architecture overhaul with new features, AI-first dev tooling, and a long list of hardening improvements.
Highlights: GDPR data export + deletion, per-type notification preferences, an admin MCP server (POST /api/mcp) that exposes admin tools to Claude Code and Claude Desktop, an in-app AI admin chat backed by the same registry, AI cost tracking, an in-app feedback system, page view analytics, Hammer-based rate limiting, native Sentry, Resend email, a sidebar-only layout, and 22 Claude Code recipe slash commands plus a full sub-agent + skill suite.
Under the hood: UUID v7 primary keys across the schema, Req replacing HTTPoison and Tesla, Styler 1.11, a modularized seed and route system, slow query telemetry, and a Production Dockerfile.
Removed: ChromicPDF + dynamic OG image generation, Wallaby E2E testing, Tidewave dev dependency, LangChain (replaced by Jido AI).
Added
-
GDPR compliance — “Your Data” settings page (
/app/users/your-data) lets users download all personal data as JSON and submit account deletion requests with soft-delete, anonymization cascade, and Oban background processing - Per-type notification preferences — users can toggle in-app and email channels independently per notification type; security-critical notifications (e.g. password changes) are forced-on and cannot be disabled
-
Notifications.notify/3entry point — single dispatch function that checks per-user, per-type preferences before sending in-app or email notifications - Welcome notification on registration and password change alert on password update
-
Admin MCP server — exposes admin tools to external AI clients (Claude Code, Claude Desktop) via JSON-RPC 2.0 at
POST /api/mcpwith bearer token auth; setMCP_ADMIN_TOKENenv var -
AI admin chat (Jido + ReqLLM) — admin-only natural-language interface at
/admin/chat. Tools are nativeJido.Actionmodules underPetalPro.AI.AdminChat.Actions.*, registered inActionRegistryand shared with the MCP server. Default modelgoogle:gemini-2.5-flash-lite, overridable via:ai_admin_chat_model. -
AI cost tracking — Req plugin that automatically logs every AI API call with token counts, costs, and timing to the
ai_call_logstable; daily budget enforcement via:ai_daily_budget_cents - In-app feedback system — users can submit feedback from any page; admin dashboard for reviewing and managing submissions
-
Sentry error monitoring — auto-activates when
SENTRY_DSNenv var is set; no code changes required - Hammer-based rate limiting — applied to auth endpoints via plugs
-
Resend email adapter — set
RESEND_API_KEYto use Resend for transactional email via Swoosh - Production Dockerfile — ready-to-use containerized deployment
- Generic JS hooks collection — infinite scroll, scroll to bottom, scroll to hash, select all, share
- Email component enhancements — configurable gap, gray button variant, and callout boxes
-
Dev scripts —
server.sh,reset_db.sh,kill_db.shfor common development tasks - Lightweight page view analytics — bot filtering and daily aggregation
- Daily Slack digest worker — activity summaries via Oban cron
- Slow query telemetry logging — configurable threshold for dev environment
- Interactive DB schema visualizer — dev page with Mermaid ER diagrams (pan/zoom), domain-grouped tables, column details with PK/FK indicators
- Hierarchical route tree — collapsible tree view mirroring URL path structure with verb badges and click-to-copy helpers
-
22 AI-powered recipe commands (
.claude/commands/recipes/) — Claude Code slash commands for common customizations: auth, billing, feature removal, integrations, structural changes -
Claude Code sub-agents —
schema-architect,test-runner,elixir-reviewer,heex-reviewer,ui-ux-reviewer - Claude Code skills and commands — CI, commit, review, changelog, scaffolding workflows
- COMPONENTS.md — reference document cataloging all available components and JS hooks
- CLAUDE.md project instructions — scoped per directory for in-repo AI context
Updated
- UUID v7 primary keys across the schema (migrated from bigint)
- Req for all HTTP calls — replaced HTTPoison and Tesla throughout
- Sidebar-only layout — converted to sidebar-only; no desktop header; integrated user profile and notification badge
-
Styler upgraded from 0.11 to 1.11 — run
mix formatafter upgrading -
Changelog context — restructured
ChangelogUpdates→Changelogwith proper schema naming (Update,Like,Read), Flop DataTable with pagination/sorting/filtering on admin index, sharedChangelogHelpersmodule, comprehensive test coverage, and SEO meta descriptions on public pages - Modularized seed system — split into production and development modules
- Fly.io deploy — now triggers on push to main
-
NPM packages updated — including ESbuild, with updated
esbuild.js - Sidebar collapse button — redesigned as flush edge tab with directional chevrons; deferred transitions prevent flash on load
-
Updated deps —
phoenix_live_view 1.1.27,petal_components 3.0.2,jido 2.1,sentry 12.0.3,swoosh 1.23.1
Removed
- ChromicPDF + dynamic OG image generation
-
Wallaby E2E testing dependency (and
AllowEctoSandboxHook, feature tests) - Tidewave dev dependency
- LangChain (replaced by Jido AI)
Fixed
- Hardened auth security — timing-safe PIN comparison, rate limiting, cookie flags
- Hardened REST API with JSON 401s, rate limiting, and MCP safety
- Hardened admin panel with audit logging, bulk caps, and safer membership deletion
- Prevent Stripe webhook crash loop when customer not found locally
- Daily budget enforcement on AI calls
- Bot-detection + error handling on page analytics
- Email infrastructure hardened for production reliability
- Wallaby test race condition in signup flow
See the full v4 changelog and the upgrade guide for migration steps.
- Upgrades Petal Pro to Tailwind 4!
- New Pro components - Aurora and BorderBeam
- Adds support for Stripe metered usage (thanks @mikehostetler)
- Replaces Admin Jobs with Oban Web
-
Adds
TailwindFormatter(thanks @fredwu) - Port is configurable for the test environment (thanks @fredwu)
-
Updated: Adds
mix assets.build -
Updated: Combobox will warn if
:tom_select_options_global_variableincludes load handler and:remote_options_event_nameis set - Fixed: SubscribeController redirects and shows Stripe error
- Fixed: Authenticated views no longer auto-subscribe to user notifications
- Fixed: Adds missed exception for blog route (thanks @bkono)
- Fixed: Seeder clears posts/files properly
- Fixed: Post/File is based on PetalPro.Schema
- Fixed: Combobox does not disappear when navigating to another page
Upgrade Notes
Petal Pro has been upgraded to Tailwind 4. Some utilities have been removed or renamed. See the Tailwind upgrade guide for more information.
To upgrade to Tailwind 4 in your project, make sure you update mix.exs:
- {:tailwind, "~> 0.2", runtime: Mix.env() == :dev}
+ {:tailwind, "~> 0.3", runtime: Mix.env() == :dev}
And config.exs (note that the paths have changed and that you need 4.0.9 or above):
config :tailwind,
- version: "3.3.3",
+ version: "4.1.11",
default: [
args: ~w(
- --config=tailwind.config.js
- --input=css/app.css
- --output=../priv/static/assets/app.css
+ --input=assets/css/app.css
+ --output=priv/static/assets/app.css
),
- cd: Path.expand("../assets", __DIR__)
+ cd: Path.expand("..", __DIR__)
]
Don’t forget to run:
mix tailwind.install
Updated app.css
app.css has been updated to support CSS first configuration:
@import "tailwindcss";
@source "../../deps/petal_components/**/*.*ex";
@import "../../deps/petal_components/assets/default.css";
@import "./colors.css";
@import "./combo-box.css";
@import "./editorjs.css";
@import "./animations.css";
@import "../node_modules/tippy.js/dist/tippy.css" layer(components);
@plugin "@tailwindcss/typography";
@plugin "@tailwindcss/forms";
@plugin "@tailwindcss/aspect-ratio";
@plugin "./tailwind_heroicons.js";
...
To see the latest changes for 3.0.0, go to:
https://github.com/petalframework/petal_pro/tree/v3.0.0/assets/css
The following files have changed:
-
app.css -
combo-box.css -
editorjs.css
The following files have been added:
-
colors.css -
animations.css -
tailwind_heroicons.js
Finally, tailwind.config.js has been removed.
Now you should be able to follow the Tailwind upgrade guide to update the rest of your project. Running mix format should automatically arrange tailwind classes in your project.
Features:
- Support for LiveView 1.0
- Rich content editor and blog/CMS feature
- Admin/User AI chat - use LangChain to interrogate Petal Pro
- Updated: Using latest Heroicons from Petal Components 2.0.6
-
Updated:
petal.gen.liveuses Table instead of Data Table (and is based on streams). Use the--data-tableoption to generate templates using a Data Table -
Updated: Compatability increased for code generated by
phx.gen.liveandphx.gen.html - Updated: Upgrades to gettext 0.26
- Fixed: Sticky class for stacked layout
- Fixed: Stacked layout renders sub-menu in mobile
-
Fixed: User notifications marked as read based on
socketurl (previously only worked withconnrequest path) - Fixed: Combobox has rounded corners after selection
Upgrade Notes
In Petal Components, the heroicons dependency has been replaced with an alternate CSS-based approach. This is based on what has been implemented in the Phoenix repo - the reasoning is explained in this issue. To upgrade an existing Petal Pro project, add the dependency in mix.exs:
# mix.exs
def deps do
[
+ {:heroicons,
+ github: "tailwindlabs/heroicons",
+ tag: "v2.1.5",
+ app: false,
+ compile: false,
+ sparse: "optimized"},
]
end
This will download a copy of the source SVG files directly from GitHub (into deps/heroicons/optimized). Then the following code will process these files to create custom CSS classes:
# assets/tailwind.config.js
const colors = require("tailwindcss/colors");
const plugin = require("tailwindcss/plugin");
+ const fs = require("fs");
+ const path = require("path");
module.exports = {
plugins: [
+ // Embeds Heroicons (https://heroicons.com) into your app.css bundle
+ // See your `CoreComponents.icon/1` for more information.
+ //
+ plugin(function({matchComponents, theme}) {
+ let iconsDir = path.join(__dirname, "../deps/heroicons/optimized")
+ let values = {}
+ let icons = [
+ ["", "/24/outline"],
+ ["-solid", "/24/solid"],
+ ["-mini", "/20/solid"],
+ ["-micro", "/16/solid"]
+ ]
+ icons.forEach(([suffix, dir]) => {
+ fs.readdirSync(path.join(iconsDir, dir)).forEach(file => {
+ let name = path.basename(file, ".svg") + suffix
+ values[name] = {name, fullPath: path.join(iconsDir, dir, file)}
+ })
+ })
+ matchComponents({
+ "hero": ({name, fullPath}) => {
+ let content = fs.readFileSync(fullPath).toString().replace(/\r?\n|\r/g, "")
+ let size = theme("spacing.6")
+ if (name.endsWith("-mini")) {
+ size = theme("spacing.5")
+ } else if (name.endsWith("-micro")) {
+ size = theme("spacing.4")
+ }
+ return {
+ [`--hero-${name}`]: `url('data:image/svg+xml;utf8,${content}')`,
+ "-webkit-mask": `var(--hero-${name})`,
+ "mask": `var(--hero-${name})`,
+ "mask-repeat": "no-repeat",
+ "background-color": "currentColor",
+ "vertical-align": "middle",
+ "display": "inline-block",
+ "width": size,
+ "height": size
+ }
+ }
+ }, {values})
+ })
],
};
Features:
- Admin dashboard with graphs/stats
- Make all components accessible (a11y - WCAG-compliant)
- Admin can see current users (using Phoenix Presence)
- Official Figma design kit
- Persistent Notifications Management
- Petal Framework is merged into Petal Pro
- Npm packages recipe is merged in as default
- Graphs/stats dashboard in the Admin console
- See who’s currently active (via Presence) in the Admin console
- If user belongs to only one org, current org is automatically set
-
User.is_adminis replaced withUser.role. User role is an enum -
Integrate
:typed_ecto_schemawithEcto.Schemafallback for users who have not installed it. - Orgs are added to log view
- Ecto insights tab is enabled in LiveDashboard
- Fixed: Edge case for Combo Box - Tom Select is re-generated when there is a change in option count
- Fixed: App does not crash when impersonating a user and the session has expired
- Fixed: Subscription logs weren’t working!
- Fixed: Race condition with subscription create/update when responding to Stripe web hooks
- Fixed: In docker compose, postgres container will not auto-restart if stopped
Upgrade Notes
Starting with this release, the Petal Framework is no longer referenced as an external package. If you have generated a Dockerfile for deployment, then you can remove the following section:
# Remove the Petal repo:
RUN --mount=type=secret,id=PETAL_LICENSE_KEY \
mix hex.repo add petal https://petal.build/repo \
--fetch-public-key "SHA256:6Ff7LeQCh4464psGV3w4a8WxReEwRl+xWmgtuHdHsjs" \
--auth-key $(cat /run/secrets/PETAL_LICENSE_KEY)
You may also need to add nodejs and npm:
# install build dependencies
RUN apt-get update -y && apt-get install -y build-essential git nodejs npm \
&& apt-get clean && rm -f /var/lib/apt/lists/*_*
Finally, lib/petal_pro_web/petal_framework_translations.ex is no longer required. Components like the
DataTable can use Gettext directly.
Features:
- JSON API: You can use the Petal Pro API for user management (register, sign in and update). It comes with OpenAPI support out of the box. Includes Swagger UI
- Update: Can sync all Stripe subscriptions including cancelled ones
- Added expanded user and org admin pages
- Fixed: PetalProWeb.Controllers.UserAuth.disconnect_user_liveviews doesn’t disconnect the user’s live views #216
- Fixed: Passwordless sign in issue from latest Phoenix Live View fixed #222
- Update: Sidebar layout now collapsible
Features:
- Stripe integration - can buy subscriptions and manage them - support for both individuals and orgs
- Use styler for code formatting
- Updated landing page components to a more modern look
- Use bandit instead of cowboy (4x faster)
- Lots of small changes
- Fix bug where users registering via passwordless / 3rd parties would not get invites to orgs
- Important passwordless security fix - anyone using passwordless should update
- Update deps
Features:
New
- <.image_upload> component for uploading single images like avatars. Used in user settings
- Local, Cloudinary and S3 support for <.image_upload>
- User impersonation - admins can login as any user without knowing their password - available via the Admin console (under the User menu).
Updated
- All forms now use the new FormField structure
- <.public_layout> has been moved into public.html.heex (it’s likely you’ll want to modify this to your brand and hence a component doesn’t make sense)
Fixed
- Reset password page now accessible when logged in (previously would redirect)
Removed
- Page builder (it was getting too complex to manage - let us know if you used this a lot and we’ll consider bringing it back)
Features:
New
-
Uses the
petal_frameworkprivate package (deletes all the_petal_frameworkfolders). This will allow for an easier upgrade process in the future, especially for components like the data table. -
Data Table supports
base_url_params. Keep custom query params when changing sort order. - Data Table is now self contained in the live view - code isn’t scattered across the model and context.
-
Added
mix recodefor code linting and refactoring -
Use
<.flash_group>to show flash messages (Petal Framework 0.3.0)
Changes
-
Enabled Wallaby tests by default (
mix test) - Updated Tailwind to 3.3
- Updated Erlang to 25.3
-
Added
rename_projectlib to replace custom mix task
Breaking
- Data table API has changed slightly. See our docs https://petal.build/components/data-table on how to use
Fixed
- Data table going blank when changing page size
-
Navigation problems for the Data Table when setting the
default_limitvia a schema file - Fix Finch issue with email sending
New
- Develop Petal Pro in GitHub CodeSpaces!
- Data Table column - can now filter by a select list
- Data Table column - can now filter by a float
Changed
- topbar.js version updated to 2.0
- mix setup no longer fetches tailwind/esbuild if they already exist
- Upgrade Petal Components to 1.0
- Data Table is now a function component
Fixed
- Github auth working again
Features:
Changed
- Upgraded Phoenix to 1.7
- Routes use the new verified routes
- Authentication pages converted to live views
- Upgraded fully from Hericons v1 to v2
-
petal.gen.livenow uses the Data Table component - Tesla now uses the more secure Finch over Hackney (https://github.com/petalframework/petal_pro/issues/66)
- Confirmation page will redirect to org invitations if invitation exists (https://github.com/petalframework/petal_pro/issues/68)
- Removed Petal Enhance (it was more complex than we thought)
Fixes
-
Redirect to
/app/orgsif an invalid org slug is used (https://github.com/petalframework/petal_pro/issues/70) -
When editing user via
/admin/users-patch_back_to_indexno longer crashes (https://github.com/petalframework/petal_pro/issues/61) - Always show Data Table filters (https://github.com/petalframework/petal_pro/issues/60)
Features:
Added
- Updated to LiveView 0.18 + Petal Components 0.18
- All components updated with declarative assigns (attr / slot)
- Data table component
- Local time component
- Sobelow for security checking
- Coveralls for code test coverage
- test.yml Github action for code quality
- Easily modifiable content security policy to help prevent XSS
- Added a docker-compose.yaml that adds Postgres so you don’t need to install it
Changed
- Router significantly more streamlined
- Some routes have been moved into their own files: AdminRoutes, AuthRoutes, DevRoutes, MailblusterRoutes
- Users are forced to be confirmed to access /app routes (easily configurable)
- Use Ecto enums for org roles
Fixes
- Fix reset password failing when signed in
- Clean up dashboard_live.ex - some old code unused was left in there
- Improved SEO meta tags in _head.html.eex
- Show a warning in the logs when no title/meta_desciprion is set on a public page
-
Added
open-graph.png(to be replaced by dev) - Fix require_confirmed_user plug
- Fix landing page GSAP not working
Features:
Added
- Two-factor authentication using time-based one time passwords (paired with something like Google Authenticator)
Changed
- Decoupled DashboardLive from Orgs so you can get started quicker if you don’t want orgs
- Can pass a custom header class to the public layout
- Sidebar and stacked layouts now support grouped menu items (see dev_layout_component.ex for an example)
- Update Tailwind to 3.1
- Split CSS into different files thanks to Tailwind 3.1
Fixed
- Onboarding now remembers user_return_to
- Fixed nav dropdown bug after modal toggle
- Fixed gettext in live views
Features:
- Oauth2 SSO social logins like Google / Facebook / Apple
- Passwordless auth
- Add petal.gen.html generator
- Multi-org schema: Org <- OrgsUsers -> Users
Added
- Login with Google & Github - easy to add more auth providers
- Passwordless auth - register/sign in via a code sent to your email
- Orgs - create an org, invite & manage members, and more
- User lifecycle actions - run code after actions like register, sign_in, sign_out, password_reset, etc
- New generator: mix petal.gen.html (same args as phx.gen.html)
- New component: <.markdown content=””> & <.pretty_markdown content=””> (uses Tailwind Typography plugin)
- Added License and Privacy pages (with some content from a template to get you started)
- New layout: <.layout type=”public”>, for public marketing related pages like landing, about us, privacy, etc
- Hooks can now be run in dead views if compatible (see color-scheme-hook.js as an example)
Changed
-
Simpler config access (
PetalPro.config(:app_name)instead ofApplication.get_env(:petal_pro, :app_name)) - Refactor <.layout> to take less props
- Refactor dark/light mode system. Much simpler now and no longer needs cookies
- Put Petal Pro Components in their own folder for easier future upgrades (can duplicate if you want to modify them)
- Sidebar and stacked layout have a new slot for the top right corner (if you want to add something like a notifications bell)
Fixed
- Log metadata wasn’t being cast
- More user actions are logged
- Fixed petal.live generator tests
- Added tests for user settings live views
- Bump Oban version to stop random error showing
- Bump Petal Components
- Use new <.table> component in petal.gen.live generator & logs
- Dark mode persists on all pages with cookies
- Fix logo showing twice in emails
- Improved the Fly.io deploy flow
- Fix admin user search
- Remove guide (this is now online)