22138 Commits

Author SHA1 Message Date
Yamila Moreno
eb22c59e5a 🐳 Add penpot-mcp service to official docker-compose.yml 2026-05-12 18:31:13 +02:00
Andrey Antukh
947f6d392d
🎉 Add chunked upload support for font variants (#9551)
*  Add additional logging and validation for image upload

* 🎉 Add chunked upload support for font variants

Extend the font variant upload flow across frontend, backend, and common
to support the standardized chunked upload protocol.

**Backend:**
- Add \`:font-max-file-size\` config default (30 MiB) and schema entry
- Add \`validate-font-size!\` in \`media.clj\` (mirrors
  \`validate-media-size!\`, raises \`:font-max-file-size-reached\`)
- Extend \`schema:create-font-variant\` to accept either \`:data\`
  (legacy bytes or chunk-vector) or \`:uploads\` (new chunked session
  map), with a validator requiring exactly one
- Add \`prepare-font-data-from-uploads\`: assembles each chunked
  session via \`cmedia/assemble-chunks\`, validates type+size
- Add \`prepare-font-data-from-legacy\`: normalises legacy byte/chunk
  entries, writing to a tempfile (joining via SequenceInputStream),
  validates type+size
- Add structured logging ("init"/"end") with \`:size\`, \`:mtypes\`,
  and \`:elapsed\` in \`create-font-variant\`

**Frontend:**
- \`upload-blob-chunked\` accepts a per-caller \`:chunk-size\` option
- Add \`font-upload-chunk-size\` (10 MiB) and \`upload-font-variant\`
  fn that uploads each mtype as a separate chunked session
- \`on-upload*\` in dashboard fonts now calls \`upload-font-variant\`
  instead of issuing \`create-font-variant\` RPC directly
- \`process-upload\` stores raw ArrayBuffer instead of chunking
  client-side

**Common:**
- Replace \`"font/opentype"\` with \`"font/woff2"\` in \`font-types\`

**Tests:**
- 25 tests / 224 assertions covering all three upload paths (direct
  bytes, legacy chunk-vector, new chunked sessions), size validation,
  and media type validation

Signed-off-by: Andrey Antukh <niwi@niwi.nz>

* 📎 Add a script for check the commit format locally

---------

Signed-off-by: Andrey Antukh <niwi@niwi.nz>
2026-05-12 18:30:19 +02:00
Alejandro Alonso
63ff5c87c2
Merge pull request #9523 from penpot/superalex-test-firefox
🐛 Fix WASM viewport interaction lifecycle for pan/zoom
2026-05-12 15:34:25 +02:00
Andrey Antukh
1e746add31
Merge pull request #9299 from oraios/mcp-self-improvement
 Add agentic DevEnv (with extended MCP server for self-improvement)
2026-05-12 15:05:42 +02:00
Alejandro Alonso
9ebf7875ea 🐛 Fix WASM viewport interaction lifecycle for pan/zoom 2026-05-12 14:13:18 +02:00
Andrey Antukh
ade0d2d0a8 📎 Update changelog with PR info 2026-05-12 13:01:42 +02:00
Michael Panchenko
7a2ca6c08f 🎉 Add two new MCP tools for Clojure development
* CljsCompilerOutputTool: Checks compiler output and reports errors
* CljCheckParentheses: Precisely locates incorrect/unbalanced parentheses

GitHub #9214
2026-05-12 12:49:58 +02:00
Dominik Jain
b952783621 📚 Add documentation page on the agentic DevEnv #9216 2026-05-12 12:49:58 +02:00
Michael Panchenko
c2a1d5c6f7 Add run-devenv-agentic command, starting the Serena MCP server in the container
Serena provides useful tools for the agentic workflow for penpot.
The following additional extensions are added:

1. uv and Serena installation, including a suitable serena_config.yml, are added to the devenv docker image
2. Serena configuration options are set via env vars and flags in manage.sh
3. run-devenv can now take -e flags which it forwards to docker exec

GitHub #9315
2026-05-12 12:49:47 +02:00
Dominik Jain
85cf3fcc3c 📚 Improve/restructure critical-info memory, adding navigation memory 2026-05-12 12:36:55 +02:00
Dominik Jain
65fce36898 🎉 Add ImportPenpotFileTool for importing .penpot files via URL
Adds a new MCP tool (devenv-only) that imports .penpot files into the
running Penpot instance. The tool downloads the file from a given URL,
stages it in the frontend's static directory, and triggers the import
via the ClojureScript REPL using the frontend's web worker infrastructure.
The temporary file is cleaned up after the import completes or fails.

Registered alongside CljsReplTool, sharing the same NreplClient instance.

Github #9217

Co-authored-by: Claude <noreply@anthropic.com>
2026-05-12 12:36:55 +02:00
Dominik Jain
1630561382 📚 Add memory on handling Penpot frontend crashes #9300
Documents how to detect, diagnose, and recover from frontend crashes
(the Internal Error page) when working through the Penpot Plugin API:

- Detect via (some? (:exception @app.main.store/state)) in the cljs REPL
- Read cause from the same map (:type, :code, :hint, :details, :uri, ...)
- Reload by listing/selecting the workspace tab in playwright and
  re-navigating to its URL, then re-checking the exception is gone

Co-authored-by: Claude <noreply@anthropic.com>
2026-05-12 12:36:55 +02:00
Dominik Jain
fe23c731d4 📚 Add memory on PR creation 2026-05-12 12:36:55 +02:00
Dominik Jain
a25f43ff42 📚 Reorganise memories, introducing an entrypoint memory
Add `critical-info` memory as an entrypoint (bootstrap memory) for the LLM, which
points to critical tools and memories, allowing the LLM to dynamically build up
relevant context
2026-05-12 12:36:55 +02:00
Dominik Jain
af1c72df01 📚 Add memory on commit creation 2026-05-12 12:36:55 +02:00
Dominik Jain
eee8ee3103 📎 Exclude versioned .md files from .gitignore pattern
Exclude files like CONTRIBUTING.md or README.md from being ignored by /*.md pattern,
as this can influence agent behaviour (configurations that disallow ignored files
from being edited)
2026-05-12 12:36:55 +02:00
Dominik Jain
f1affdbadc Revamp cljs expression evaluation to full-blown REPL 2026-05-12 12:36:55 +02:00
Dominik Jain
66d518f15d 🎉 Add MCP tool for ClojureScript expression evaluation
New tool to evaluate ClojureScript expressions by connecting to the
nREPL service already provided in devenv.

Add dependency 'nrepl-client' and a corresponding client class
as well as types to support this.

Add a new environment variable for 'devenv mode', which enables
the new tool (PENPOT_MCP_DEVENV).
2026-05-12 12:36:44 +02:00
Dominik Jain
e1493de777 📎 Ignore .idea 2026-05-12 12:35:38 +02:00
Dominik Jain
6de41f072c Add initial Serena project 2026-05-12 12:35:38 +02:00
Dominik Jain
b7b31f6ee3 Start MCP server in devenv if PENPOT_FLAGS contains 'enable-mcp' 2026-05-12 12:35:38 +02:00
Alejandro Alonso
97c8fcd4ad
Merge pull request #9509 from penpot/elenatorro-14038-fix-component-thumbnail-update
🐛 Fix component thumbnail sync
2026-05-12 12:29:28 +02:00
Elena Torro
76e3df5836 🐛 Use extrect to capture component's thumbnail 2026-05-12 12:21:06 +02:00
Elena Torro
847d55bfb4 🐛 Update component thumbnails to match current shape 2026-05-12 12:21:06 +02:00
Alejandro Alonso
086ed83847
Merge pull request #9389 from penpot/azazeln28-refactor-state
♻️ Refactor State into DesignState
2026-05-12 12:15:05 +02:00
Aitor Moreno
a126379cc7 ♻️ Refactor State into DesignState 2026-05-12 12:14:38 +02:00
Pablo Alba
269edcd0ee
🐛 Fix restore saved version keeps view-only (#9514)
* 🐛 Fix restore saved verrsion keeps view-only

* 📎 Remove outdated note from CHANGES.md

Remove note about restoring saved version from Preview mode.

Signed-off-by: Andrey Antukh <niwi@niwi.nz>

---------

Signed-off-by: Andrey Antukh <niwi@niwi.nz>
Co-authored-by: Andrey Antukh <niwi@niwi.nz>
2026-05-12 10:32:12 +02:00
Luis de Dios
f62a89dcc2
🐛 Fix font selection position is hiding fonts (#9499) 2026-05-12 10:25:16 +02:00
Alejandro Alonso
f044104db1
Merge pull request #9524 from penpot/elenatorro-fix-blur-on-page-transition
🐛 Fix blur on page transition
2026-05-12 10:10:49 +02:00
Yamila Moreno
328efd4e16
📚 Add notice regarding architectural constraints with MCP Server (#9423) 2026-05-12 10:06:13 +02:00
Andrey Antukh
11a72abdcd 📎 Update version on mcp server 2026-05-12 10:04:12 +02:00
Elena Torro
463017b5c9 🐛 Fix blur on page transition 2026-05-12 09:47:00 +02:00
Andrey Antukh
bd3ca6f8e5 📚 Update changelog 2.15.0 2026-05-12 09:33:33 +02:00
Jack Storment
c394a281c8
🐛 Revert blend-mode hover preview when dismissing dropdown (#9237)
* 🐛 Revert blend-mode hover preview when dismissing dropdown

When the blend-mode dropdown was dismissed by clicking outside instead
of selecting an option, the canvas kept rendering the last hovered
blend mode even though the inspector and data state had reverted. The
visible state of the shape no longer matched its stored state. Reset
the canvas render back to the shape's saved blend mode on dropdown
close so the preview never outlives the dropdown.

Signed-off-by: jack-stormentswe <crazycoder131@gmail.com>

* Fix blend-mode dropdown and various bugs

Fix blend-mode dropdown behavior and revert WASM render on pointer leave. Also, address multiple bugs related to user interactions and data handling.

Signed-off-by: Alejandro Alonso <alejandro.alonso@kaleidos.net>

---------

Signed-off-by: jack-stormentswe <crazycoder131@gmail.com>
Signed-off-by: Jack Storment <88656337+jack-stormentswe@users.noreply.github.com>
Co-authored-by: Alejandro Alonso <alejandro.alonso@kaleidos.net>
2026-05-12 08:17:07 +02:00
Alejandro Alonso
7650fa1716
Merge pull request #9500 from penpot/alotor-fix-text-edition
🐛 Fix problem when editing text not being redrawn
2026-05-12 06:50:02 +02:00
alonso.torres
effb8bcf10 🐛 Fix problem when editing text not being redrawn 2026-05-12 06:45:28 +02:00
Andrey Antukh
962bb1fa9b Merge remote-tracking branch 'origin/staging' into develop 2026-05-11 17:53:03 +02:00
Andrey Antukh
fd82744c62 Merge branch 'main' into staging 2026-05-11 17:52:52 +02:00
Andrey Antukh
843a4a5b58 🐛 Fix mattermost and database logger related to the audit event change 2.15.0-RC10 2026-05-11 17:08:38 +02:00
Andrey Antukh
d670ba4bff 🐛 Fix mattermost and database logger related to the audit event change 2026-05-11 17:07:59 +02:00
Andrey Antukh
27e6c1e420 Merge remote-tracking branch 'origin/staging' into develop 2026-05-11 16:24:55 +02:00
Andrey Antukh
c76e536cd8 Merge remote-tracking branch 'origin/main' into staging 2026-05-11 16:24:27 +02:00
Andrey Antukh
102c97040a 🐛 Fix unexpected exception on handling webhook events 2.15.0-RC9 2026-05-11 16:23:14 +02:00
Andrey Antukh
1de2718d43 Merge remote-tracking branch 'origin/main' into staging 2026-05-11 15:24:15 +02:00
Andrey Antukh
8f4f948104 🐛 Skip the ssrf check on internal audit-log archive task 2.15.0-RC8 2026-05-11 15:22:59 +02:00
Michael Panchenko
7fb19fc1a2
🐛 Fix float comparison #14070 (#9434)
* 📎 Add test that surfaces the bug described in #14070

The bug: alt-drag-duplicating a variant master into the variant container
auto-creates a new variant component cloned from the source
via duplicate-component, which preserves :touched on every cloned shape.
The resulting copy's children inherit those :geometry-group touched flags
through add-touched-from-ref-chain on switch.

variants-switch -> component-swap (keep-touched? true) -> generate-keep-touched
then runs update-attrs-on-switch for each touched child. The new shape's
:y is correctly skipped by the per-attr "different masters" guard, but
:selrect/:points fall through to a width/height-based safety check that
uses exact equality. In practice, the alt-drag modifier path leaves a
sub-pixel drift in :width on the copy, so equal-geometry? returns false,
the safety check is bypassed, and the :else branch copies the source
variant's :selrect verbatim onto the freshly instantiated target shape.
The shape ends up with :y from the target master but :selrect.y from the
source — the renderer reads :selrect, so the child appears at the source
position inside a parent that has resized to the target's dimensions:
the visible "button cut off" symptom.

The new test sets up a variant container whose children are themselves
component copies (matching production: variant masters' children carry
:touched), introduces the same kind of width drift on the copy that the
alt-drag path produces, and runs the swap directly via the existing
test harness. It asserts (a) :y matches the target, (b) :selrect.y
matches the target, and (c) :y and :selrect.y agree. With the current
code (a) passes and (b)/(c) fail — capturing both the wrong value and
the internal inconsistency that causes the visible regression.

* 🐛 Fix #14070 by no longer comparing floats for exact equality in equal-geometry?
2026-05-11 15:17:48 +02:00
Leona Lee
02bbbae0b0
🐛 Fix typography removal from plugin API (#9279)
* 🐛 Fix typography removal from plugin API

* 🔥 Remove unrelated delete-typography test

---------

Signed-off-by: Leona Lee <63717587+leonaIee@users.noreply.github.com>
Co-authored-by: Andrey Antukh <niwi@niwi.nz>
2026-05-11 14:58:42 +02:00
dhgoal
3094d512f4
🐛 Expose Source Sans Pro 600 weight in builtin fonts list (#9247)
The font-family list at frontend/src/app/main/fonts.cljs registers
Source Sans Pro variants for weights 200, 300, 400, 700 and 900, but
omits the semibold (600) entries even though the font assets are
already bundled (frontend/resources/fonts/sourcesanspro-semibold.*)
and the CSS @font-face declarations that load them are present
(frontend/resources/styles/common/dependencies/fonts.scss:55-56).

Result: weight 600 cannot be selected from the font picker even
though the bytes are downloadable; users see a 400 -> 700 jump.

Add the two missing variant entries (600 and 600 italic) using the
same :suffix style as the other numeric-id entries (200, 300), since
the file-name component "semibold" doesn't match the weight number.

Issue mentions weights 500 and 800 as also missing, but no
sourcesanspro-medium or sourcesanspro-extrabold assets exist in the
repo, so this PR scopes to weight 600 only — the recoverable subset.

Closes #7378.

Signed-off-by: Andrey Antukh <niwi@niwi.nz>
Co-authored-by: Andrey Antukh <niwi@niwi.nz>
2026-05-11 14:55:25 +02:00
FairyPiggyDev
09bd7f96f6
Add author, relative timestamp and short identifier to history entries (#9132)
The workspace Actions history panel previously showed the operation
icon and a one-line message for each undo entry with no indication
of when the action happened, any stable way to refer to it, or who
made the change. The reporter of issue #7660 (and @Takhoffman's
follow-up comment) asked for a git-like display: `<hash> · <time> by
<name>`.

This change stamps each undo entry with its creation timestamp and
author at the moment it lands on the undo stack and surfaces three
extra pieces of information in the history sidebar:

- A short 7-character identifier derived from the entry's existing
  `:undo-group` UUID. Hovering shows the full UUID.
- A relative timestamp (e.g. `just now`, `5 minutes ago`, `2 hours
  ago`, `3 days ago`) rendered via `app.common.time/timeago` so it
  matches the formatting already used for comments and the dashboard.
- The display name of the profile that created the entry, rendered
  as `by <Name>` in the same metadata row.

The undo stack is client-side per profile, so every entry is always
the current user; the author is stored on the entry anyway so the UI
does not need to reach into profile state while rendering and so the
data stays correct if the stack shape ever changes.

Changes at a glance:

- `data/workspace/undo.cljs`: extend `schema:undo-entry` with an
  optional `:timestamp` and `:by`; new `profile-display-name` helper
  that falls back from full name to email to nil; `stamp-entry` now
  takes state and fills in both fields on entries that do not
  already carry them. Pre-stamped entries (e.g. coming out of an
  accumulated transaction) keep their original values.
- `ui/workspace/sidebar/history.cljs`: propagate `:timestamp`,
  `:undo-group`, and `:by` through `parse-entries`; add `short-id`
  helper; render the metadata row in `history-entry` using
  `app.common.time/timeago` against `:timestamp`; skip the author
  span entirely when `:by` is nil.
- `ui/workspace/sidebar/history.scss`: styling for the new metadata
  row (monospace hash, muted separator, truncated time/author).
- `translations/en.po`: 1 new string for `by %s`.

Existing undo entries created before this change have neither
timestamp nor author; the UI is defensive about both, so old entries
simply render with whatever data they have (and often the plain
title on its own).

Github #7660

Signed-off-by: FairyPigDev <luislee3108@gmail.com>
Signed-off-by: FairyPiggyDev <luislee3108@gmail.com>
Co-authored-by: Andrey Antukh <niwi@niwi.nz>
2026-05-11 14:48:32 +02:00
jony376
f7fbd3007e
🐛 Prevent viewers from overwriting file thumbnails (#9285)
* 🐛 Prevent viewers from overwriting file thumbnails

* 🐛 Fix message

---------

Co-authored-by: jony376 <jony376@gmail.com>
Co-authored-by: Andrey Antukh <niwi@niwi.nz>
2026-05-11 14:38:40 +02:00