@@ -40,7 +40,7 @@ import { safeSelf } from './safe-self.js';
4040function editOutboundObjectFn (
4141 trusted = false ,
4242 propChain = '' ,
43- jsonq = '' ,
43+ jsonq = ''
4444) {
4545 if ( propChain === '' ) { return ; }
4646 const safe = safeSelf ( ) ;
@@ -127,6 +127,42 @@ registerScriptlet(trustedEditOutboundObject, {
127127} ) ;
128128
129129/******************************************************************************/
130+
131+ function jsonEditFn ( trusted = false , jsonq = '' , ...varargs ) {
132+ const safe = safeSelf ( ) ;
133+ const logPrefix = safe . makeLogPrefix (
134+ `${ trusted ? 'trusted-' : '' } json-edit` ,
135+ jsonq ,
136+ ...varargs
137+ ) ;
138+ const jsonp = JSONPath . create ( jsonq ) ;
139+ if ( jsonp . valid === false || jsonp . value !== undefined && trusted !== true ) {
140+ return safe . uboLog ( logPrefix , 'Bad JSONPath query' ) ;
141+ }
142+ const extraArgs = safe . parseVarargs ( varargs ) ;
143+ const pattern = extraArgs . matches && safe . initPattern ( extraArgs . matches ) ;
144+ proxyApplyFn ( 'JSON.parse' , function ( context ) {
145+ const json = context . callArgs [ 0 ] ;
146+ const obj = context . reflect ( ) ;
147+ if ( pattern && safe . testPattern ( pattern , json ) === false ) { return obj ; }
148+ const objAfter = jsonp . apply ( obj ) ;
149+ if ( objAfter === undefined ) { return obj ; }
150+ safe . uboLog ( logPrefix , 'Edited' ) ;
151+ if ( safe . logLevel > 1 ) {
152+ safe . uboLog ( logPrefix , `After edit:\n${ safe . JSON_stringify ( objAfter , null , 2 ) } ` ) ;
153+ }
154+ return objAfter ;
155+ } ) ;
156+ }
157+ registerScriptlet ( jsonEditFn , {
158+ name : 'json-edit.fn' ,
159+ dependencies : [
160+ JSONPath ,
161+ proxyApplyFn ,
162+ safeSelf ,
163+ ] ,
164+ } ) ;
165+
130166/******************************************************************************/
131167/**
132168 * @scriptlet json-edit.js
@@ -138,15 +174,20 @@ registerScriptlet(trustedEditOutboundObject, {
138174 * @param jsonq
139175 * A uBO-flavored JSONPath query.
140176 *
177+ * @param 'matches', pattern
178+ * Vararg, optional: The JSONPath will be applied if and only if the pattern
179+ * matches the inbound JSON string. The pattern can be a plain string or a
180+ * regex.
181+ *
141182 * */
142183
143- function jsonEdit ( jsonq = '' ) {
144- editOutboundObjectFn ( false , 'JSON.parse' , jsonq ) ;
184+ function jsonEdit ( jsonq = '' , ... varargs ) {
185+ jsonEditFn ( false , jsonq , ... varargs ) ;
145186}
146187registerScriptlet ( jsonEdit , {
147188 name : 'json-edit.js' ,
148189 dependencies : [
149- editOutboundObjectFn ,
190+ jsonEditFn ,
150191 ] ,
151192} ) ;
152193
@@ -161,16 +202,21 @@ registerScriptlet(jsonEdit, {
161202 * @param jsonq
162203 * A uBO-flavored JSONPath query.
163204 *
205+ * @param 'matches', pattern
206+ * Vararg, optional: The JSONPath will be applied if and only if the pattern
207+ * matches the inbound JSON string. The pattern can be a plain string or a
208+ * regex.
209+ *
164210 * */
165211
166- function trustedJsonEdit ( jsonq = '' ) {
167- editOutboundObjectFn ( true , 'JSON.parse' , jsonq ) ;
212+ function trustedJsonEdit ( jsonq = '' , ... varargs ) {
213+ jsonEditFn ( true , jsonq , ... varargs ) ;
168214}
169215registerScriptlet ( trustedJsonEdit , {
170216 name : 'trusted-json-edit.js' ,
171217 requiresTrust : true ,
172218 dependencies : [
173- editOutboundObjectFn ,
219+ jsonEditFn ,
174220 ] ,
175221} ) ;
176222
0 commit comments