## Summary
- Add CLI project import support from synced `.webstudio/data.json` into
another project via a destination share link.
- Move project bundle import/export contract into
`@webstudio-is/protocol`, including bundle versioning, staged upload
constants, schema validation, and fixture coverage.
- Upload project bundle data through staged TUS upload before calling
the import RPC to avoid request body limits.
- Upload referenced assets as binary files through the existing asset
upload route before importing asset rows.
- Add `--skip-assets` and `--ignore-version-check` import options.
- Add retry handling for transient missing imported asset files by
re-uploading only the reported missing assets.
- Share missing-asset import error formatting/parsing through protocol
to avoid duplicated string contracts.
- Preserve browser asset upload behavior while adding API upload
support.
- Normalize schema naming across the branch to lower-case names without
`Schema` suffix.
Closes https://github.com/webstudio-is/webstudio/issues/4586
Closes https://github.com/webstudio-is/webstudio/issues/4619
## Summary
Fixes shared Slot editing so linked Slot occurrences stay consistent
across structural edits and labels.
## Changes
- Fixed moving a direct Slot child out of a Slot so the child is removed
from all linked Slot occurrences.
- Fixed unwrapping a direct Slot child so the child is removed from all
linked Slot occurrences.
- Added linked Slot label sync when renaming from Navigator or Settings
panel.
- Added/updated tests for canonical Slots, legacy Slots, nested Slot
children, keyboard moves, unwrap, reparent, and label sync.
- Simplified stale Slot detach logic that was incorrectly cloning only
the selected Slot occurrence.
## Testing
- `pnpm --filter @webstudio-is/builder test --
app/shared/instance-utils/...`
- `pnpm --filter @webstudio-is/builder test --
app/builder/shared/commands.test.ts`
- `pnpm --filter @webstudio-is/builder typecheck`
- `pnpm lint`
- `git diff --check`
Limits projects to 8 editable breakpoints, with a toast warning when
users try to add more. Pasted/imported styles that exceed the limit are
merged into the closest existing breakpoint instead of creating new
ones.
Also updates the breakpoint editor UI with required names, hover-only
trash actions, scrolling, and tighter layout polish.
Closes https://github.com/webstudio-is/webstudio/issues/4209
- Add Token class and token() helper in template package for JSX token
support
- Refactor insertFragmentWithConflictResolution to
detectFragmentTokenConflicts
- Refactor insertPageWithConflictResolution to detectPageTokenConflicts
- Move dialog display to callers for better testability
- Add conflictResolution parameter to page-utils
- Add comprehensive tests for token functionality and conflict detection
- Fix bug: remove .values() call on arrays in breakpoint handling
Fixes https://github.com/webstudio-is/webstudio/issues/5491
## Description
- When pasting an instance with tokens, we can compare the name and the
contents. If they are identical, we can choose the existing one and
avoid having any conflicts.
- When pasting a token and the name is already used, add a numeric
suffix to it.
- find duplicate tokens command that will go based on content even if
name is different
## Steps for reproduction
1. click button
2. expect xyz
## Code Review
- [ ] hi @kof, I need you to do
- conceptual review (architecture, feature-correctness)
- detailed review (read every line)
- test it on preview
## Before requesting a review
- [ ] made a self-review
- [ ] added inline comments where things may be not obvious (the "why",
not "what")
## Before merging
- [ ] tested locally and on preview environment (preview dev login:
0000)
- [ ] updated [test
cases](https://github.com/webstudio-is/webstudio/blob/main/apps/builder/docs/test-cases.md)
document
- [ ] added tests
- [ ] if any new env variables are added, added them to `.env` file
Users started to build own marketplaces. And we found paste something
copied from other browser like firefox -> chromium based app doesn't
work. This is because OSs guarantee only text/plain to be stored in
system clipboard.
Here I changed copy paste logic to copy as text/plain and paste as both
application/json and text/plain if possible.
Ref https://github.com/webstudio-is/webstudio/issues/4093
Here a few delete instance improvements
- fixed deleting resources bound to props (action in webhook form)
- rewrote all tests with jsx template
- switched from instance selector to instance path
- added slot test
Every time somebody is facing invalid constraint issue whole tree is
blocked from deleting instances except the problematic one with actual
issue.
Here rewrote detachability check to validate only ancestors and avoid
traversing potentially problematic siblings.
Here replaced a bunch boilerplaty code with more general
findClosestInsertable. This also reduced amount of explicit instance
selector calls. Prevented inserting list item into body. Refactored
tests with jsx.
Ref https://github.com/webstudio-is/webstudio/issues/4364
We need to implement universal linking of current user view. For this I
added "awareness" state which reflects terminology from collaboration
libraries.
First migrated selected page id and fixed usages.
## Description
- webflow css preset
## Steps for reproduction
1. click button
2. expect xyz
## Code Review
- [ ] hi @kof, I need you to do
- conceptual review (architecture, feature-correctness)
- detailed review (read every line)
- test it on preview
## Before requesting a review
- [ ] made a self-review
- [ ] added inline comments where things may be not obvious (the "why",
not "what")
## Before merging
- [ ] tested locally and on preview environment (preview dev login:
5de6)
- [ ] updated [test
cases](https://github.com/webstudio-is/webstudio/blob/main/apps/builder/docs/test-cases.md)
document
- [ ] added tests
- [ ] if any new env variables are added, added them to `.env` file
Here improved page duplicate logic to support replacing old variables in
page meta and path params variable with new references.
Also improved path duplicating to preserve path params by prefixing with
`/copy-n` subpath.
Ref https://github.com/webstudio-is/webstudio/issues/2532
Here refactored insertInstancesSliceCopy to accept webstudio data
instead of creating transaction.
This let us avoid hacky callbacks in duplicate instance and duplicate
page functionalities.
Note: review with hidden whitespaces
Here refactored delete instance to accept and mutate webstudio data
instead of accessing data stores.
Now we can avoid double transaction when delete pages.
Note: review with hidden whitespaces
Here added two new types
WebstudioFragment - reusable fragment of webstudio data which can be
generated (markdown, embed template), transferred (copied or stored in
marketplace) and inserted.
WebstudioData - all available normalized data to allow composing
multiple operations within single transaction like delete instance and
then insert into other part of the page.
Ref https://github.com/webstudio-is/webstudio/issues/2532
Important constrain on the way to custom components to not use data
sources defined in other components when copy paste.
## Steps for reproduction
1. Test covers it
Use same well tested utility to slice and insert its copy for copy
paste. Moved most utilities inside of instance plugin and added more
tests for it.
## Steps for reproduction
1. play with copy paste
Ref https://github.com/webstudio-is/webstudio/issues/2532
Here added a "core" collection component to support iterating over json
arrays.
There is a lot of room for unification of all this logic though would
require building reactive tree abstraction.
Canvas automatically renders stub component for collection to make it
droppable. We can do the same for slot component.
Slot and Fragment eventually will go to "core" components too.
Added json/parameter prop types to embed template to support collection.
Fixed loosing focus while typing in json prop.
## Steps for reproduction
1. Drop collection component
2. play with it
Ref https://github.com/webstudio-is/webstudio/issues/2532
On the last discussion about bindings we agreed expression are always
bound to single prop and cannot be reused.
Here added new prop.type = 'expression' as a replacement to
dataSource.type = 'expression'.
This will let us unify expression/variable reference and avoid deep
dependencies. Expressions and actions become similar.
For now both expression prop and legacy expression data source are
supported until we migrate completely in db.
Ref https://github.com/webstudio-is/webstudio/issues/2532
Here improved copy/paste behavior.
Before variables outside of copied tree were inlined. For example
ErrorMessage were loosing its expression when duplicated within same
form.
Now expressions and variables are preserved
and variables are inlined into expressions when paste target do not have
such variable. For example ErrorMessage get `"initial" == "error"`. With
upcoming UI it will be more obvious. The main idea here to not loose all
expressions but only references to unavailable variables.
Split instances slicer into separate utility from copy paste plugin.
Will be used to duplicate pages. Along with splitting added more tests
to better cover behavior.
New version of immerhin moved global queue into store instance so we can
stop filtering and just call store.popAll().
Also replaced default store with webstudio own serverSyncStore instance.
Now auto import works much better.
We are planning to move all types necessary to represent generated site
into separate package. This way we will be able to make CLI as small as
possible.
Here moved only assets schema. Now we get rid of aws, sharp and one
prisma usage (project-build still use it)
```diff
- 99MB
+ 75MB
```
Here added action copy paste support.
When all action dependencies are scoped to copied instance new variable
nams are ussed.
When some any dependency is not scoped execution is removed from copied
prop.
Here added meta.detachable flag which allows when set to true disable
copying, dragging and deleting instances of this component without ts
parent instance.
This is necessary to constrain components based on external code and
prevent deleting hidden components user cannot add again.
Fixes https://github.com/webstudio-is/webstudio-builder/issues/1994
Here changed behavior when copy and paste without changing instance
selection. Now it works as duplicating and copy is inserted after
selection.
Added cmd+d and ctrl+d shortcut to do this with single press without
polluting clipboard.
Here fixed the case when copy pasted form looses state and give errors
on submit.
Immerhin now converted to esm to work in tests.
Added tests for instances copy paste plugin.
The new logic is copy data sources as is if they are bound to copied
instances.
The new computeExpressionsDependencies used to detect if expression
depends on data sources outside of copied instances scope.
Fixes https://github.com/webstudio-is/webstudio-builder/issues/1950
Here added new utility to compute constraints for tree when insert embed
template, paste something or reparent. I previous implementation all
constraints were merged which gave us false positives like when paste
List>ListItem we got "requiredAncestors: [List]". Here tree layout is
considered to exclude such false positives.
For testing try to copy paste List>ListItem
Here refactored copy paste plugin system to try each plugin until it
succeeds. This way we can have multiple solutions to copy paste from
plain text. For example embed template is hand written text and should
succeed before markdown starts parsing it.
```json
{
"@webstudio/template": [
{
"type": "instance",
"component": "Box",
"children": [
{ "type": "text", "value": "Hello, I'm Box!" }
]
}
]
}
```
Fixed the issue with pasting checkbox into button
which is wrapped into label
Prevented inserting label, checkbox, radio button and input into
buttons.
Here added support for callbacks or event handlers on components which
basically can do only assignment to variables for now with extended
(with assignment operator) syntax of expressions.
Ref https://github.com/webstudio-is/webstudio-builder/issues/1529
Here introduced two types of data sources into "variable" and
"expression". First stores the value, the second only executable code.
Execute expressions now output results of all expressions so we could
access values globally with "computed" store
Embed template references now allow to define both variable reference
and expression.