@@ -120,34 +120,155 @@ export const dispatchHttp468Request = async (props: HttpRequestProps): Promise<H
120120 2. Replace newline strings
121121 */
122122 const replaceJsonBodyString = ( text : string ) => {
123- const valToStr = ( val : any ) => {
123+ // Check if the variable is in quotes
124+ const isVariableInQuotes = ( text : string , variable : string ) => {
125+ const index = text . indexOf ( variable ) ;
126+ if ( index === - 1 ) return false ;
127+
128+ // 计算变量前面的引号数量
129+ const textBeforeVar = text . substring ( 0 , index ) ;
130+ const matches = textBeforeVar . match ( / " / g) || [ ] ;
131+
132+ // 如果引号数量为奇数,则变量在引号内
133+ return matches . length % 2 === 1 ;
134+ } ;
135+ const valToStr = ( val : any , isQuoted = false ) => {
124136 if ( val === undefined ) return 'null' ;
125137 if ( val === null ) return 'null' ;
126138
127139 if ( typeof val === 'object' ) return JSON . stringify ( val ) ;
128140
129141 if ( typeof val === 'string' ) {
142+ if ( isQuoted ) {
143+ return val . replace ( / (?< ! \\ ) " / g, '\\"' ) ;
144+ }
130145 try {
131- const parsed = JSON . parse ( val ) ;
132- if ( typeof parsed === 'object' ) {
133- return JSON . stringify ( parsed ) ;
134- }
146+ JSON . parse ( val ) ;
135147 return val ;
136148 } catch ( error ) {
137149 const str = JSON . stringify ( val ) ;
150+
138151 return str . startsWith ( '"' ) && str . endsWith ( '"' ) ? str . slice ( 1 , - 1 ) : str ;
139152 }
140153 }
141154
142155 return String ( val ) ;
143156 } ;
157+ // Test cases for variable replacement in JSON body
158+ // const bodyTest = () => {
159+ // const testData = [
160+ // // 基本字符串替换
161+ // {
162+ // body: `{"name":"{{name}}","age":"18" }`,
163+ // variables: [{ key: '{{name}}', value: '测试' }],
164+ // result: `{"name":"测试","age":"18"}`
165+ // },
166+ // // 特殊字符处理
167+ // {
168+ // body: `{"text":"{{text}}" }`,
169+ // variables: [{ key: '{{text}}', value: '包含"引号"和\\反斜杠' }],
170+ // result: `{"text":"包含\\"引号\\"和\\反斜杠"}`
171+ // },
172+ // // 数字类型处理
173+ // {
174+ // body: `{"count":{{count}},"price":{{price}} }`,
175+ // variables: [
176+ // { key: '{{count}}', value: '42' },
177+ // { key: '{{price}}', value: '99.99' }
178+ // ],
179+ // result: `{"count":42,"price":99.99}`
180+ // },
181+ // // 布尔值处理
182+ // {
183+ // body: `{"isActive":{{isActive}},"hasData":{{hasData}} }`,
184+ // variables: [
185+ // { key: '{{isActive}}', value: 'true' },
186+ // { key: '{{hasData}}', value: 'false' }
187+ // ],
188+ // result: `{"isActive":true,"hasData":false}`
189+ // },
190+ // // 对象类型处理
191+ // {
192+ // body: `{"user":{{user}},"user2":"{{user2}}" }`,
193+ // variables: [
194+ // { key: '{{user}}', value: `{"id":1,"name":"张三"}` },
195+ // { key: '{{user2}}', value: `{"id":1,"name":"张三"}` }
196+ // ],
197+ // result: `{"user":{"id":1,"name":"张三"},"user2":"{\\"id\\":1,\\"name\\":\\"张三\\"}"}`
198+ // },
199+ // // 数组类型处理
200+ // {
201+ // body: `{"items":{{items}}}`,
202+ // variables: [{ key: '{{items}}', value: '[1, 2, 3]' }],
203+ // result: `{"items":[1,2,3]}`
204+ // },
205+ // // null 和 undefined 处理
206+ // {
207+ // body: `{"nullValue":{{nullValue}},"undefinedValue":{{undefinedValue}} }`,
208+ // variables: [
209+ // { key: '{{nullValue}}', value: 'null' },
210+ // { key: '{{undefinedValue}}', value: 'undefined' }
211+ // ],
212+ // result: `{"nullValue":null,"undefinedValue":null}`
213+ // },
214+ // // 嵌套JSON结构
215+ // {
216+ // body: `{"data":{"nested":{"value":"{{nestedValue}}" }}}`,
217+ // variables: [{ key: '{{nestedValue}}', value: '嵌套值' }],
218+ // result: `{"data":{"nested":{"value":"嵌套值"}}}`
219+ // },
220+ // // 多变量替换
221+ // {
222+ // body: `{"first":"{{first}}","second":"{{second}}","third":{{third}} }`,
223+ // variables: [
224+ // { key: '{{first}}', value: '第一' },
225+ // { key: '{{second}}', value: '第二' },
226+ // { key: '{{third}}', value: '3' }
227+ // ],
228+ // result: `{"first":"第一","second":"第二","third":3}`
229+ // },
230+ // // JSON字符串作为变量值
231+ // {
232+ // body: `{"config":{{config}}}`,
233+ // variables: [{ key: '{{config}}', value: '{"setting":"enabled","mode":"advanced"}' }],
234+ // result: `{"config":{"setting":"enabled","mode":"advanced"}}`
235+ // }
236+ // ];
237+
238+ // for (let i = 0; i < testData.length; i++) {
239+ // const item = testData[i];
240+ // let bodyStr = item.body;
241+ // for (const variable of item.variables) {
242+ // const isQuote = isVariableInQuotes(bodyStr, variable.key);
243+ // bodyStr = bodyStr.replace(variable.key, valToStr(variable.value, isQuote));
244+ // }
245+ // bodyStr = bodyStr.replace(/(".*?")\s*:\s*undefined\b/g, '$1:null');
246+
247+ // console.log(bodyStr === item.result, i);
248+ // if (bodyStr !== item.result) {
249+ // console.log(bodyStr);
250+ // console.log(item.result);
251+ // } else {
252+ // try {
253+ // JSON.parse(item.result);
254+ // } catch (error) {
255+ // console.log('反序列化异常', i, item.result);
256+ // }
257+ // }
258+ // }
259+ // };
260+ // bodyTest();
144261
145262 // 1. Replace {{key.key}} variables
146263 const regex1 = / \{ \{ \$ ( [ ^ . ] + ) \. ( [ ^ $ ] + ) \$ \} \} / g;
147264 const matches1 = [ ...text . matchAll ( regex1 ) ] ;
148265 matches1 . forEach ( ( match ) => {
149266 const nodeId = match [ 1 ] ;
150267 const id = match [ 2 ] ;
268+ const fullMatch = match [ 0 ] ;
269+
270+ // 检查变量是否在引号内
271+ const isInQuotes = isVariableInQuotes ( text , fullMatch ) ;
151272
152273 const variableVal = ( ( ) => {
153274 if ( nodeId === VARIABLE_NODE_ID ) {
@@ -165,9 +286,9 @@ export const dispatchHttp468Request = async (props: HttpRequestProps): Promise<H
165286 return getReferenceVariableValue ( { value : input . value , nodes : runtimeNodes , variables } ) ;
166287 } ) ( ) ;
167288
168- const formatVal = valToStr ( variableVal ) ;
289+ const formatVal = valToStr ( variableVal , isInQuotes ) ;
169290
170- const regex = new RegExp ( `\\{\\{\\$(${ nodeId } \\.${ id } )\\$\\}\\}` , 'g ' ) ;
291+ const regex = new RegExp ( `\\{\\{\\$(${ nodeId } \\.${ id } )\\$\\}\\}` , '' ) ;
171292 text = text . replace ( regex , ( ) => formatVal ) ;
172293 } ) ;
173294
@@ -176,10 +297,16 @@ export const dispatchHttp468Request = async (props: HttpRequestProps): Promise<H
176297 const matches2 = text . match ( regex2 ) || [ ] ;
177298 const uniqueKeys2 = [ ...new Set ( matches2 . map ( ( match ) => match . slice ( 2 , - 2 ) ) ) ] ;
178299 for ( const key of uniqueKeys2 ) {
179- text = text . replace ( new RegExp ( `{{(${ key } )}}` , 'g' ) , ( ) => valToStr ( allVariables [ key ] ) ) ;
300+ const fullMatch = `{{${ key } }}` ;
301+ // 检查变量是否在引号内
302+ const isInQuotes = isVariableInQuotes ( text , fullMatch ) ;
303+
304+ text = text . replace ( new RegExp ( `{{(${ key } )}}` , '' ) , ( ) =>
305+ valToStr ( allVariables [ key ] , isInQuotes )
306+ ) ;
180307 }
181308
182- return text . replace ( / ( " .* ?" ) \s * : \s * u n d e f i n e d \b / g, '$1: null' ) ;
309+ return text . replace ( / ( " .* ?" ) \s * : \s * u n d e f i n e d \b / g, '$1:null' ) ;
183310 } ;
184311
185312 httpReqUrl = replaceStringVariables ( httpReqUrl ) ;
0 commit comments