Skip to content

Commit 4bbc2b2

Browse files
committed
improvement(variables): changed object validation to support JavaScript object notation in addition to strict JSON
1 parent 0621caf commit 4bbc2b2

File tree

2 files changed

+37
-18
lines changed

2 files changed

+37
-18
lines changed

apps/sim/app/w/[id]/components/panel/components/variables/variables.tsx

Lines changed: 18 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -179,22 +179,26 @@ export function Variables({ panelWidth }: VariablesProps) {
179179
case 'object':
180180
try {
181181
// Handle both JavaScript and JSON syntax
182-
let valueToValidate = String(variable.value).trim()
183-
184-
// If it's clearly JS syntax, convert it to valid JSON
185-
if (valueToValidate.includes("'") || /\b\w+\s*:/.test(valueToValidate)) {
186-
// Replace JS single quotes with double quotes, but handle escaped quotes correctly
187-
valueToValidate = valueToValidate
188-
.replace(/(\w+)\s*:/g, '"$1":') // Convert unquoted property names to quoted
189-
.replace(/'/g, '"') // Replace single quotes with double quotes
182+
let valueToEvaluate = String(variable.value).trim()
183+
184+
// Basic security check to prevent arbitrary code execution
185+
if (!valueToEvaluate.startsWith('{') || !valueToEvaluate.endsWith('}')) {
186+
return 'Not a valid object format'
187+
}
188+
189+
// Use Function constructor to safely evaluate the object expression
190+
// This is safer than eval() and handles all JS object literal syntax
191+
const parsed = new Function(`return ${valueToEvaluate}`)()
192+
193+
// Verify it's actually an object (not array or null)
194+
if (parsed === null || typeof parsed !== 'object' || Array.isArray(parsed)) {
195+
return 'Not a valid object'
190196
}
191197

192-
const parsed = JSON.parse(valueToValidate)
193-
return !parsed || typeof parsed !== 'object' || Array.isArray(parsed)
194-
? 'Not a valid JSON object'
195-
: undefined
196-
} catch {
197-
return 'Invalid JSON object syntax'
198+
return undefined // Valid object
199+
} catch (e) {
200+
console.log('Object parsing error:', e)
201+
return 'Invalid object syntax'
198202
}
199203
case 'array':
200204
try {

apps/sim/stores/panel/variables/store.ts

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -53,12 +53,27 @@ function validateVariable(variable: Variable): string | undefined {
5353
case 'object':
5454
// Check if it's a valid JSON object
5555
try {
56-
const parsed = JSON.parse(String(variable.value))
56+
// Handle both JavaScript and JSON syntax
57+
let valueToEvaluate = String(variable.value).trim()
58+
59+
// Basic security check to prevent arbitrary code execution
60+
if (!valueToEvaluate.startsWith('{') || !valueToEvaluate.endsWith('}')) {
61+
return 'Not a valid object format'
62+
}
63+
64+
// Use Function constructor to safely evaluate the object expression
65+
// This handles both JSON and JS object literal syntax
66+
const parsed = new Function(`return ${valueToEvaluate}`)()
67+
68+
// Verify it's actually an object (not array or null)
5769
if (parsed === null || typeof parsed !== 'object' || Array.isArray(parsed)) {
58-
return 'Not a valid JSON object'
70+
return 'Not a valid object'
5971
}
60-
} catch {
61-
return 'Invalid JSON object syntax'
72+
73+
return undefined // Valid object
74+
} catch (e) {
75+
console.log('Object parsing error:', e)
76+
return 'Invalid object syntax'
6277
}
6378
break
6479
case 'array':

0 commit comments

Comments
 (0)