mirror of
https://github.com/webstudio-is/webstudio.git
synced 2026-11-09 05:26:24 +09:00
fix: Variable bindings on Class don't show on live site (#4253)
## Description closes #3683 ## Steps for reproduction Tests and fixtures ## 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
This commit is contained in:
1 parent
b921c1d558
commit
02bf5974a9
7 files changed
+181
-19
No files matched your search
@@ -1,10 +1,10 @@
|
||||
{
|
||||
"build": {
|
||||
"id": "40962d82-ea2d-4536-b94f-dece81312190",
|
||||
"id": "6876de3a-942a-466b-9761-ad7cb2fa2c21",
|
||||
"projectId": "cddc1d44-af37-4cb6-a430-d300cf6f932d",
|
||||
"version": 315,
|
||||
"createdAt": "2024-09-30T13:22:48.689+00:00",
|
||||
"updatedAt": "2024-09-30T13:22:48.689+00:00",
|
||||
"version": 321,
|
||||
"createdAt": "2024-10-08T17:47:04.557+00:00",
|
||||
"updatedAt": "2024-10-08T17:47:04.557+00:00",
|
||||
"pages": {
|
||||
"meta": {
|
||||
"siteName": "KittyGuardedZone",
|
||||
@@ -1540,6 +1540,19 @@
|
||||
"value": 300
|
||||
}
|
||||
}
|
||||
],
|
||||
[
|
||||
"g6Z7dAxi6LYB-XtI6SaRR:UoTkWyaFuTYJihS3MFYK5:marginTop:",
|
||||
{
|
||||
"breakpointId": "UoTkWyaFuTYJihS3MFYK5",
|
||||
"styleSourceId": "g6Z7dAxi6LYB-XtI6SaRR",
|
||||
"property": "marginTop",
|
||||
"value": {
|
||||
"type": "unit",
|
||||
"value": 12,
|
||||
"unit": "px"
|
||||
}
|
||||
}
|
||||
]
|
||||
],
|
||||
"styleSources": [
|
||||
@@ -1717,6 +1730,13 @@
|
||||
"type": "local",
|
||||
"id": "o9VRyqmvIarF6HrGMccU8"
|
||||
}
|
||||
],
|
||||
[
|
||||
"g6Z7dAxi6LYB-XtI6SaRR",
|
||||
{
|
||||
"type": "local",
|
||||
"id": "g6Z7dAxi6LYB-XtI6SaRR"
|
||||
}
|
||||
]
|
||||
],
|
||||
"styleSourceSelections": [
|
||||
@@ -1894,6 +1914,13 @@
|
||||
"instanceId": "drCx7m8q_gnNQLrhPDA-g",
|
||||
"values": ["o9VRyqmvIarF6HrGMccU8"]
|
||||
}
|
||||
],
|
||||
[
|
||||
"T-rqx2b12pRrWcafRRoIG",
|
||||
{
|
||||
"instanceId": "T-rqx2b12pRrWcafRRoIG",
|
||||
"values": ["g6Z7dAxi6LYB-XtI6SaRR"]
|
||||
}
|
||||
]
|
||||
],
|
||||
"props": [
|
||||
@@ -2297,6 +2324,16 @@
|
||||
"type": "string",
|
||||
"value": "\"broken'with`symbols"
|
||||
}
|
||||
],
|
||||
[
|
||||
"I4cM2PzBX49KWxsKdGMd1",
|
||||
{
|
||||
"id": "I4cM2PzBX49KWxsKdGMd1",
|
||||
"instanceId": "T-rqx2b12pRrWcafRRoIG",
|
||||
"name": "className",
|
||||
"type": "expression",
|
||||
"value": "`${$ws$dataSource$FG6camSaR89vSBREAV9PT} class_3`"
|
||||
}
|
||||
]
|
||||
],
|
||||
"dataSources": [
|
||||
@@ -2463,6 +2500,19 @@
|
||||
"scopeInstanceId": "mdyCS8QnKx3fL1MLXifmy",
|
||||
"name": "system"
|
||||
}
|
||||
],
|
||||
[
|
||||
"FG6camSaR89vSBREAV9PT",
|
||||
{
|
||||
"type": "variable",
|
||||
"id": "FG6camSaR89vSBREAV9PT",
|
||||
"scopeInstanceId": "mdyCS8QnKx3fL1MLXifmy",
|
||||
"name": "classVar",
|
||||
"value": {
|
||||
"type": "string",
|
||||
"value": "varClass"
|
||||
}
|
||||
}
|
||||
]
|
||||
],
|
||||
"resources": [
|
||||
@@ -3581,6 +3631,10 @@
|
||||
{
|
||||
"type": "id",
|
||||
"value": "drCx7m8q_gnNQLrhPDA-g"
|
||||
},
|
||||
{
|
||||
"type": "id",
|
||||
"value": "T-rqx2b12pRrWcafRRoIG"
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -3593,6 +3647,15 @@
|
||||
"component": "Box",
|
||||
"children": []
|
||||
}
|
||||
],
|
||||
[
|
||||
"T-rqx2b12pRrWcafRRoIG",
|
||||
{
|
||||
"type": "instance",
|
||||
"id": "T-rqx2b12pRrWcafRRoIG",
|
||||
"component": "Box",
|
||||
"children": []
|
||||
}
|
||||
]
|
||||
],
|
||||
"deployment": {
|
||||
|
||||
+6
-6
@@ -1,26 +1,26 @@
|
||||
export const sitemap = [
|
||||
{
|
||||
path: "/",
|
||||
lastModified: "2024-09-30",
|
||||
lastModified: "2024-10-08",
|
||||
},
|
||||
{
|
||||
path: "/_route_with_symbols_",
|
||||
lastModified: "2024-09-30",
|
||||
lastModified: "2024-10-08",
|
||||
},
|
||||
{
|
||||
path: "/form",
|
||||
lastModified: "2024-09-30",
|
||||
lastModified: "2024-10-08",
|
||||
},
|
||||
{
|
||||
path: "/heading-with-id",
|
||||
lastModified: "2024-09-30",
|
||||
lastModified: "2024-10-08",
|
||||
},
|
||||
{
|
||||
path: "/resources",
|
||||
lastModified: "2024-09-30",
|
||||
lastModified: "2024-10-08",
|
||||
},
|
||||
{
|
||||
path: "/nested/nested-page",
|
||||
lastModified: "2024-09-30",
|
||||
lastModified: "2024-10-08",
|
||||
},
|
||||
];
|
||||
+5
-1
@@ -27,12 +27,16 @@ export const pageFontAssets: FontAsset[] = [];
|
||||
export const pageBackgroundImageAssets: ImageAsset[] = [];
|
||||
|
||||
const Page = ({}: { system: any }) => {
|
||||
let [classVar, set$classVar] = useVariableState<any>("varClass");
|
||||
return (
|
||||
<Body className={"w-body"}>
|
||||
<Box
|
||||
id={"\"broken'with`symbols"}
|
||||
className={"w-box cm16yxw custom-class \"broken 'with `symbols"}
|
||||
className={
|
||||
"w-box cm16yxw" + " " + "custom-class \"broken 'with `symbols"
|
||||
}
|
||||
/>
|
||||
<Box className={"w-box ctm310" + " " + `${classVar} class_3`} />
|
||||
</Body>
|
||||
);
|
||||
};
|
||||
|
||||
@@ -385,4 +385,7 @@
|
||||
.cm16yxw {
|
||||
width: 300px;
|
||||
}
|
||||
.ctm310 {
|
||||
margin-top: 12px;
|
||||
}
|
||||
}
|
||||
@@ -6,7 +6,7 @@
|
||||
"typecheck": "tsc",
|
||||
"cli": "NODE_OPTIONS='--conditions=webstudio --import=tsx' webstudio",
|
||||
"fixtures:link": "pnpm cli link --link https://p-cddc1d44-af37-4cb6-a430-d300cf6f932d-dot-${BUILDER_HOST:-main.development.webstudio.is}'?authToken=1cdc6026-dd5b-4624-b89b-9bd45e9bcc3d'",
|
||||
"fixtures:sync": "pnpm cli sync --buildId 40962d82-ea2d-4536-b94f-dece81312190 && pnpm prettier --write ./.webstudio/",
|
||||
"fixtures:sync": "pnpm cli sync --buildId 6876de3a-942a-466b-9761-ad7cb2fa2c21 && pnpm prettier --write ./.webstudio/",
|
||||
"fixtures:build": "pnpm cli build --template vercel --template internal --preview && pnpm prettier --write ./app/ ./package.json ./tsconfig.json"
|
||||
},
|
||||
"private": true,
|
||||
|
||||
@@ -567,6 +567,30 @@ test("generate component with variables and actions", () => {
|
||||
);
|
||||
});
|
||||
|
||||
test("merge classes if no className", () => {
|
||||
expect(
|
||||
generateWebstudioComponent({
|
||||
classesMap: new Map([["body", ["cls1"]]]),
|
||||
scope: createScope(),
|
||||
name: "Page",
|
||||
rootInstanceId: "body",
|
||||
parameters: [],
|
||||
dataSources: new Map(),
|
||||
indexesWithinAncestors: new Map(),
|
||||
...renderJsx(<$.Body ws:id="body"></$.Body>),
|
||||
})
|
||||
).toEqual(
|
||||
validateJSX(
|
||||
clear(`
|
||||
const Page = () => {
|
||||
return <Body
|
||||
className={"cls1"} />
|
||||
}
|
||||
`)
|
||||
)
|
||||
);
|
||||
});
|
||||
|
||||
test("add classes and merge classes", () => {
|
||||
expect(
|
||||
generateWebstudioComponent({
|
||||
@@ -584,7 +608,70 @@ test("add classes and merge classes", () => {
|
||||
clear(`
|
||||
const Page = () => {
|
||||
return <Body
|
||||
className={"cls1 cls2 \\"cls3\\""} />
|
||||
className={"cls1" + " " + "cls2 \\"cls3\\""} />
|
||||
}
|
||||
`)
|
||||
)
|
||||
);
|
||||
});
|
||||
|
||||
test("add classes", () => {
|
||||
expect(
|
||||
generateWebstudioComponent({
|
||||
classesMap: new Map(),
|
||||
scope: createScope(),
|
||||
name: "Page",
|
||||
rootInstanceId: "body",
|
||||
parameters: [],
|
||||
dataSources: new Map(),
|
||||
indexesWithinAncestors: new Map(),
|
||||
...renderJsx(<$.Body ws:id="body" className='cls2 "cls3"'></$.Body>),
|
||||
})
|
||||
).toEqual(
|
||||
validateJSX(
|
||||
clear(`
|
||||
const Page = () => {
|
||||
return <Body
|
||||
className={"cls2 \\"cls3\\""} />
|
||||
}
|
||||
`)
|
||||
)
|
||||
);
|
||||
});
|
||||
|
||||
test("add bind classes and merge classes", () => {
|
||||
expect(
|
||||
generateWebstudioComponent({
|
||||
classesMap: new Map([["body", ["cls1"]]]),
|
||||
scope: createScope(),
|
||||
name: "Page",
|
||||
rootInstanceId: "body",
|
||||
parameters: [],
|
||||
dataSources: toMap([
|
||||
{
|
||||
type: "variable",
|
||||
id: "variableId",
|
||||
name: "variableName",
|
||||
value: { type: "string", value: "cls3" },
|
||||
},
|
||||
]),
|
||||
indexesWithinAncestors: new Map(),
|
||||
...renderJsx(
|
||||
<$.Body
|
||||
ws:id="body"
|
||||
className={
|
||||
new ExpressionValue(`'cls2' + ' ' + $ws$dataSource$variableId`)
|
||||
}
|
||||
></$.Body>
|
||||
),
|
||||
})
|
||||
).toEqual(
|
||||
validateJSX(
|
||||
clear(`
|
||||
const Page = () => {
|
||||
let [variableName, set$variableName] = useVariableState<any>("cls3")
|
||||
return <Body
|
||||
className={"cls1" + " " + 'cls2' + ' ' + variableName} />
|
||||
}
|
||||
`)
|
||||
)
|
||||
|
||||
@@ -170,11 +170,17 @@ export const generateJsxElement = ({
|
||||
let collectionDataValue: undefined | string;
|
||||
let collectionItemValue: undefined | string;
|
||||
|
||||
const classes = Array.from(classesMap?.get(instance.id) ?? []);
|
||||
const classMapArray = classesMap?.get(instance.id);
|
||||
const classes =
|
||||
classMapArray !== undefined
|
||||
? [JSON.stringify(classMapArray.join(" "))]
|
||||
: [];
|
||||
|
||||
for (const prop of props.values()) {
|
||||
if (prop.instanceId !== instance.id) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const propValue = generatePropValue({
|
||||
scope,
|
||||
prop,
|
||||
@@ -210,10 +216,9 @@ export const generateJsxElement = ({
|
||||
continue;
|
||||
}
|
||||
// We need to merge atomic classes with user-defined className prop.
|
||||
if (prop.name === "className") {
|
||||
if (prop.type === "string") {
|
||||
classes.push(prop.value);
|
||||
}
|
||||
if (prop.name === "className" && propValue !== undefined) {
|
||||
classes.push(propValue);
|
||||
|
||||
continue;
|
||||
}
|
||||
if (propValue !== undefined) {
|
||||
@@ -222,7 +227,7 @@ export const generateJsxElement = ({
|
||||
}
|
||||
|
||||
if (classes.length !== 0) {
|
||||
generatedProps += `\nclassName={${JSON.stringify(classes.join(" "))}}`;
|
||||
generatedProps += `\nclassName={${classes.join(` + " " + `)}}`;
|
||||
}
|
||||
|
||||
let generatedElement = "";
|
||||
|
||||
Reference in new issue
Block a user