json.go 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752
  1. package executor
  2. import (
  3. "bytes"
  4. "encoding/json"
  5. "fmt"
  6. "strconv"
  7. "strings"
  8. )
  9. // jsonText is a JSON value produced by a JSON1 function. It carries the JSON
  10. // subtype across nested function calls (so json_insert can embed the result of
  11. // json() verbatim) and is normalized to a plain string before it is stored.
  12. type jsonText string
  13. // jsonEncode marshals a decoded JSON tree without HTML escaping.
  14. func jsonEncode(v interface{}) (string, error) {
  15. var buf bytes.Buffer
  16. enc := json.NewEncoder(&buf)
  17. enc.SetEscapeHTML(false)
  18. if err := enc.Encode(v); err != nil {
  19. return "", err
  20. }
  21. return strings.TrimRight(buf.String(), "\n"), nil
  22. }
  23. // jsonDecode parses JSON text, preserving number precision with json.Number.
  24. func jsonDecode(s string) (interface{}, error) {
  25. dec := json.NewDecoder(strings.NewReader(s))
  26. dec.UseNumber()
  27. var v interface{}
  28. if err := dec.Decode(&v); err != nil {
  29. return nil, fmt.Errorf("malformed JSON")
  30. }
  31. // Reject trailing content, matching JSON1's strict parsing.
  32. if dec.More() {
  33. return nil, fmt.Errorf("malformed JSON")
  34. }
  35. return v, nil
  36. }
  37. // jsonInput resolves a JSON1 input argument to a decoded tree.
  38. func jsonInput(v interface{}) (interface{}, error) {
  39. switch t := v.(type) {
  40. case nil:
  41. return nil, nil
  42. case jsonText:
  43. return jsonDecode(string(t))
  44. case string:
  45. return jsonDecode(t)
  46. case []byte:
  47. return jsonDecode(string(t))
  48. default:
  49. return nil, fmt.Errorf("malformed JSON")
  50. }
  51. }
  52. // jsonArgToNode converts a SQL value into a JSON tree node for embedding.
  53. func jsonArgToNode(v interface{}) interface{} {
  54. switch t := v.(type) {
  55. case nil:
  56. return nil
  57. case jsonText:
  58. if node, err := jsonDecode(string(t)); err == nil {
  59. return node
  60. }
  61. return string(t)
  62. case bool:
  63. return t
  64. case int:
  65. return json.Number(strconv.FormatInt(int64(t), 10))
  66. case int64:
  67. return json.Number(strconv.FormatInt(t, 10))
  68. case uint64:
  69. return json.Number(strconv.FormatUint(t, 10))
  70. case float64:
  71. return t
  72. case string:
  73. return t
  74. case []byte:
  75. return string(t)
  76. default:
  77. return fmt.Sprintf("%v", t)
  78. }
  79. }
  80. // jsonNodeToSQL converts a JSON tree node to the SQL value json_extract returns.
  81. func jsonNodeToSQL(v interface{}) interface{} {
  82. switch t := v.(type) {
  83. case nil:
  84. return nil
  85. case json.Number:
  86. if i, err := t.Int64(); err == nil {
  87. return i
  88. }
  89. f, _ := t.Float64()
  90. return f
  91. case bool:
  92. if t {
  93. return int64(1)
  94. }
  95. return int64(0)
  96. case string:
  97. return t
  98. case []interface{}, map[string]interface{}:
  99. s, err := jsonEncode(t)
  100. if err != nil {
  101. return nil
  102. }
  103. return jsonText(s)
  104. default:
  105. return t
  106. }
  107. }
  108. // jsonPathSeg is one component of a parsed JSON path.
  109. type jsonPathSeg struct {
  110. key string
  111. isIndex bool
  112. index int
  113. appendOp bool // [#] — append for insert/set
  114. fromEnd bool // negative index
  115. dynamic bool // PostgreSQL text[] path element resolved by container kind
  116. element string // raw dynamic element text
  117. }
  118. // parseJSONPath parses a JSON1 path expression such as $.a.b[0] or $[#].
  119. func parseJSONPath(path string) ([]jsonPathSeg, error) {
  120. if !strings.HasPrefix(path, "$") {
  121. return nil, fmt.Errorf("JSON path error: %s", path)
  122. }
  123. var segs []jsonPathSeg
  124. i := 1
  125. for i < len(path) {
  126. switch path[i] {
  127. case '.':
  128. i++
  129. if i >= len(path) {
  130. return nil, fmt.Errorf("JSON path error: %s", path)
  131. }
  132. if path[i] == '"' {
  133. end := strings.IndexByte(path[i+1:], '"')
  134. if end < 0 {
  135. return nil, fmt.Errorf("JSON path error: %s", path)
  136. }
  137. segs = append(segs, jsonPathSeg{key: path[i+1 : i+1+end]})
  138. i += end + 2
  139. continue
  140. }
  141. start := i
  142. for i < len(path) && path[i] != '.' && path[i] != '[' {
  143. i++
  144. }
  145. segs = append(segs, jsonPathSeg{key: path[start:i]})
  146. case '[':
  147. end := strings.IndexByte(path[i:], ']')
  148. if end < 0 {
  149. return nil, fmt.Errorf("JSON path error: %s", path)
  150. }
  151. inner := path[i+1 : i+end]
  152. i += end + 1
  153. if inner == "#" {
  154. segs = append(segs, jsonPathSeg{isIndex: true, appendOp: true})
  155. continue
  156. }
  157. if strings.HasPrefix(inner, "\"") && strings.HasSuffix(inner, "\"") && len(inner) >= 2 {
  158. segs = append(segs, jsonPathSeg{key: inner[1 : len(inner)-1]})
  159. continue
  160. }
  161. n, err := strconv.Atoi(inner)
  162. if err != nil {
  163. return nil, fmt.Errorf("JSON path error: %s", path)
  164. }
  165. segs = append(segs, jsonPathSeg{isIndex: true, index: n, fromEnd: n < 0})
  166. default:
  167. return nil, fmt.Errorf("JSON path error: %s", path)
  168. }
  169. }
  170. return segs, nil
  171. }
  172. // jsonLookup walks a decoded tree to the node addressed by segs.
  173. func jsonLookup(root interface{}, segs []jsonPathSeg) (interface{}, bool) {
  174. node, ok, _ := jsonLookupE(root, segs)
  175. return node, ok
  176. }
  177. // jsonLookupE walks a decoded tree to the node addressed by segs. It differs
  178. // from jsonLookup only in reporting a malformed PostgreSQL path element (a
  179. // non-integer step on an array). A step that does not resolve is reported as
  180. // not found, which is the jsonb #> NULL result for a mismatched path.
  181. func jsonLookupE(root interface{}, segs []jsonPathSeg) (interface{}, bool, error) {
  182. cur := root
  183. for _, rawSeg := range segs {
  184. seg, resolved, err := resolveJSONBPathSegment(rawSeg, cur, false)
  185. if err != nil {
  186. return nil, false, err
  187. }
  188. if !resolved {
  189. return nil, false, nil
  190. }
  191. if seg.isIndex {
  192. arr, ok := cur.([]interface{})
  193. if !ok {
  194. return nil, false, nil
  195. }
  196. idx := seg.index
  197. if seg.fromEnd {
  198. idx = len(arr) + idx
  199. }
  200. if idx < 0 || idx >= len(arr) {
  201. return nil, false, nil
  202. }
  203. cur = arr[idx]
  204. continue
  205. }
  206. obj, ok := cur.(map[string]interface{})
  207. if !ok {
  208. return nil, false, nil
  209. }
  210. val, ok := obj[seg.key]
  211. if !ok {
  212. return nil, false, nil
  213. }
  214. cur = val
  215. }
  216. return cur, true, nil
  217. }
  218. // jsonApplyPatch applies json_set/insert/replace mutations to a decoded tree.
  219. // mode is "set", "insert", or "replace".
  220. func jsonApplyPatch(root interface{}, segs []jsonPathSeg, value interface{}, mode string) (interface{}, error) {
  221. if len(segs) == 0 {
  222. return value, nil
  223. }
  224. seg := segs[0]
  225. last := len(segs) == 1
  226. childSegs := segs[1:]
  227. if seg.isIndex {
  228. arr, ok := root.([]interface{})
  229. if !ok {
  230. // A missing container is created only by json_set/json_insert.
  231. if mode == "replace" {
  232. return root, nil
  233. }
  234. arr = []interface{}{}
  235. }
  236. idx := seg.index
  237. if seg.appendOp {
  238. if last {
  239. return append(arr, value), nil
  240. }
  241. child, childOK := interface{}(nil), false
  242. _ = child
  243. _ = childOK
  244. // append a new container for nested paths
  245. container := newJSONContainer(childSegs[0])
  246. newChild, err := jsonApplyPatch(container, childSegs, value, mode)
  247. if err != nil {
  248. return nil, err
  249. }
  250. return append(arr, newChild), nil
  251. }
  252. if seg.fromEnd {
  253. idx = len(arr) + idx
  254. }
  255. if idx < 0 || idx > len(arr) {
  256. return root, nil
  257. }
  258. if last {
  259. if idx == len(arr) {
  260. if mode == "replace" {
  261. return root, nil
  262. }
  263. return append(arr, value), nil
  264. }
  265. replaced := append([]interface{}(nil), arr...)
  266. replaced[idx] = value
  267. return replaced, nil
  268. }
  269. if idx == len(arr) {
  270. if mode == "replace" {
  271. return root, nil
  272. }
  273. container := newJSONContainer(childSegs[0])
  274. newChild, err := jsonApplyPatch(container, childSegs, value, mode)
  275. if err != nil {
  276. return nil, err
  277. }
  278. return append(arr, newChild), nil
  279. }
  280. newChild, err := jsonApplyPatch(arr[idx], childSegs, value, mode)
  281. if err != nil {
  282. return nil, err
  283. }
  284. replaced := append([]interface{}(nil), arr...)
  285. replaced[idx] = newChild
  286. return replaced, nil
  287. }
  288. obj, ok := root.(map[string]interface{})
  289. if !ok {
  290. if mode == "replace" {
  291. return root, nil
  292. }
  293. obj = map[string]interface{}{}
  294. }
  295. if last {
  296. _, exists := obj[seg.key]
  297. if exists && mode == "insert" {
  298. return root, nil
  299. }
  300. if !exists && mode == "replace" {
  301. return root, nil
  302. }
  303. newObj := make(map[string]interface{}, len(obj)+1)
  304. for k, v := range obj {
  305. newObj[k] = v
  306. }
  307. newObj[seg.key] = value
  308. return newObj, nil
  309. }
  310. child, exists := obj[seg.key]
  311. if !exists {
  312. if mode == "replace" {
  313. return root, nil
  314. }
  315. child = newJSONContainer(childSegs[0])
  316. }
  317. newChild, err := jsonApplyPatch(child, childSegs, value, mode)
  318. if err != nil {
  319. return nil, err
  320. }
  321. newObj := make(map[string]interface{}, len(obj)+1)
  322. for k, v := range obj {
  323. newObj[k] = v
  324. }
  325. newObj[seg.key] = newChild
  326. return newObj, nil
  327. }
  328. func newJSONContainer(seg jsonPathSeg) interface{} {
  329. if seg.isIndex {
  330. return []interface{}{}
  331. }
  332. return map[string]interface{}{}
  333. }
  334. // jsonArrowExtract evaluates the SQLite -> and ->> operators. The key operand is
  335. // a field label, an array index, or a $ path. A NULL operand or a path that
  336. // selects nothing yields SQL NULL; malformed JSON in the document is an error,
  337. // as it is for json_extract(). scalar selects ->> (SQL value of the selected
  338. // node) instead of -> (JSON text for the selected node).
  339. func jsonArrowExtract(document, key interface{}, scalar bool) (interface{}, error) {
  340. if document == nil || key == nil {
  341. return nil, nil
  342. }
  343. node, err := jsonInput(document)
  344. if err != nil {
  345. return nil, err
  346. }
  347. segs, err := jsonArrowPath(key)
  348. if err != nil {
  349. return nil, err
  350. }
  351. found, ok := jsonLookup(node, segs)
  352. if !ok {
  353. return nil, nil
  354. }
  355. if scalar {
  356. return jsonNodeToSQL(found), nil
  357. }
  358. s, err := jsonEncode(found)
  359. if err != nil {
  360. return nil, err
  361. }
  362. return jsonText(s), nil
  363. }
  364. // jsonArrowPath turns an arrow-operator operand into a path. Text that starts
  365. // with $ is a JSON path; other text names a single object member, so labels
  366. // containing dots or brackets are not reinterpreted as paths. Integers select
  367. // an array position, with negative values counting from the end.
  368. func jsonArrowPath(key interface{}) ([]jsonPathSeg, error) {
  369. switch t := key.(type) {
  370. case string:
  371. return jsonArrowPathText(t)
  372. case jsonText:
  373. return jsonArrowPathText(string(t))
  374. case int64:
  375. return []jsonPathSeg{{isIndex: true, index: int(t), fromEnd: t < 0}}, nil
  376. case int:
  377. return []jsonPathSeg{{isIndex: true, index: t, fromEnd: t < 0}}, nil
  378. default:
  379. return nil, fmt.Errorf("JSON path error")
  380. }
  381. }
  382. func jsonArrowPathText(path string) ([]jsonPathSeg, error) {
  383. if strings.HasPrefix(path, "$") {
  384. return parseJSONPath(path)
  385. }
  386. return []jsonPathSeg{{key: path}}, nil
  387. }
  388. // jsonTypeName returns the JSON1 type name for a decoded node.
  389. func jsonTypeName(v interface{}) string {
  390. switch v.(type) {
  391. case nil:
  392. return "null"
  393. case bool:
  394. return "false" // caller distinguishes true below
  395. case json.Number:
  396. s := string(v.(json.Number))
  397. if !strings.ContainsAny(s, ".eE") {
  398. return "integer"
  399. }
  400. return "real"
  401. case string:
  402. return "text"
  403. case []interface{}:
  404. return "array"
  405. case map[string]interface{}:
  406. return "object"
  407. default:
  408. return "null"
  409. }
  410. }
  411. // evalJSONFunction evaluates a JSON1 scalar function. It returns handled=false
  412. // for names it does not own.
  413. func evalJSONFunction(name string, args []interface{}) (interface{}, bool, error) {
  414. upper := strings.ToUpper(name)
  415. switch upper {
  416. case "JSON", "JSONB":
  417. if len(args) != 1 {
  418. return nil, true, fmt.Errorf("wrong number of arguments to %s()", name)
  419. }
  420. if args[0] == nil {
  421. return nil, true, nil
  422. }
  423. node, err := jsonInput(args[0])
  424. if err != nil {
  425. return nil, true, err
  426. }
  427. s, err := jsonEncode(node)
  428. if err != nil {
  429. return nil, true, err
  430. }
  431. return jsonText(s), true, nil
  432. case "JSON_VALID", "JSONB_VALID":
  433. if len(args) != 1 {
  434. return nil, true, fmt.Errorf("wrong number of arguments to %s()", name)
  435. }
  436. if _, err := jsonInput(args[0]); err != nil {
  437. return int64(0), true, nil
  438. }
  439. return int64(1), true, nil
  440. case "JSON_TYPE":
  441. if len(args) < 1 || len(args) > 2 {
  442. return nil, true, fmt.Errorf("wrong number of arguments to json_type()")
  443. }
  444. if args[0] == nil {
  445. return nil, true, nil
  446. }
  447. node, err := jsonInput(args[0])
  448. if err != nil {
  449. return nil, true, err
  450. }
  451. if len(args) == 2 {
  452. path, ok := args[1].(string)
  453. if !ok {
  454. if jt, is := args[1].(jsonText); is {
  455. path = string(jt)
  456. } else {
  457. return nil, true, fmt.Errorf("JSON path error")
  458. }
  459. }
  460. segs, perr := parseJSONPath(path)
  461. if perr != nil {
  462. return nil, true, perr
  463. }
  464. found, ok := jsonLookup(node, segs)
  465. if !ok {
  466. return nil, true, nil
  467. }
  468. node = found
  469. }
  470. if b, isBool := node.(bool); isBool {
  471. if b {
  472. return "true", true, nil
  473. }
  474. return "false", true, nil
  475. }
  476. return jsonTypeName(node), true, nil
  477. case "JSON_EXTRACT", "JSONB_EXTRACT":
  478. if len(args) < 2 {
  479. return nil, true, fmt.Errorf("wrong number of arguments to json_extract()")
  480. }
  481. if args[0] == nil {
  482. return nil, true, nil
  483. }
  484. node, err := jsonInput(args[0])
  485. if err != nil {
  486. return nil, true, err
  487. }
  488. for _, p := range args[1:] {
  489. path, ok := jsonPathArg(p)
  490. if !ok {
  491. return nil, true, fmt.Errorf("JSON path error")
  492. }
  493. segs, perr := parseJSONPath(path)
  494. if perr != nil {
  495. return nil, true, perr
  496. }
  497. found, ok := jsonLookup(node, segs)
  498. if !ok {
  499. return nil, true, nil
  500. }
  501. node = found
  502. }
  503. return jsonNodeToSQL(node), true, nil
  504. case "JSON_SET", "JSONB_SET", "JSON_INSERT", "JSONB_INSERT", "JSON_REPLACE", "JSONB_REPLACE":
  505. if len(args) < 3 || len(args)%2 == 0 {
  506. return nil, true, fmt.Errorf("wrong number of arguments to %s()", name)
  507. }
  508. if args[0] == nil {
  509. return nil, true, nil
  510. }
  511. mode := "set"
  512. if strings.Contains(upper, "INSERT") {
  513. mode = "insert"
  514. } else if strings.Contains(upper, "REPLACE") {
  515. mode = "replace"
  516. }
  517. node, err := jsonInput(args[0])
  518. if err != nil {
  519. return nil, true, err
  520. }
  521. for i := 1; i+1 < len(args); i += 2 {
  522. path, ok := jsonPathArg(args[i])
  523. if !ok {
  524. return nil, true, fmt.Errorf("JSON path error")
  525. }
  526. segs, perr := parseJSONPath(path)
  527. if perr != nil {
  528. return nil, true, perr
  529. }
  530. node, err = jsonApplyPatch(node, segs, jsonArgToNode(args[i+1]), mode)
  531. if err != nil {
  532. return nil, true, err
  533. }
  534. }
  535. s, err := jsonEncode(node)
  536. if err != nil {
  537. return nil, true, err
  538. }
  539. return jsonText(s), true, nil
  540. case "JSON_REMOVE", "JSONB_REMOVE":
  541. if len(args) < 2 {
  542. return nil, true, fmt.Errorf("wrong number of arguments to json_remove()")
  543. }
  544. if args[0] == nil {
  545. return nil, true, nil
  546. }
  547. node, err := jsonInput(args[0])
  548. if err != nil {
  549. return nil, true, err
  550. }
  551. for _, p := range args[1:] {
  552. path, ok := jsonPathArg(p)
  553. if !ok {
  554. return nil, true, fmt.Errorf("JSON path error")
  555. }
  556. segs, perr := parseJSONPath(path)
  557. if perr != nil {
  558. return nil, true, perr
  559. }
  560. node, err = jsonRemove(node, segs)
  561. if err != nil {
  562. return nil, true, err
  563. }
  564. }
  565. s, err := jsonEncode(node)
  566. if err != nil {
  567. return nil, true, err
  568. }
  569. return jsonText(s), true, nil
  570. case "JSON_ARRAY_LENGTH":
  571. if len(args) < 1 || len(args) > 2 {
  572. return nil, true, fmt.Errorf("wrong number of arguments to json_array_length()")
  573. }
  574. if args[0] == nil {
  575. return nil, true, nil
  576. }
  577. node, err := jsonInput(args[0])
  578. if err != nil {
  579. return nil, true, err
  580. }
  581. if len(args) == 2 {
  582. path, ok := jsonPathArg(args[1])
  583. if !ok {
  584. return nil, true, fmt.Errorf("JSON path error")
  585. }
  586. segs, err := parseJSONPath(path)
  587. if err != nil {
  588. return nil, true, err
  589. }
  590. found, ok := jsonLookup(node, segs)
  591. if !ok {
  592. return nil, true, nil
  593. }
  594. node = found
  595. }
  596. if array, ok := node.([]interface{}); ok {
  597. return int64(len(array)), true, nil
  598. }
  599. // SQLite's JSON1 reports zero for a valid non-array document.
  600. return int64(0), true, nil
  601. case "JSON_ARRAY", "JSONB_ARRAY":
  602. arr := make([]interface{}, len(args))
  603. for i, a := range args {
  604. arr[i] = jsonArgToNode(a)
  605. }
  606. s, err := jsonEncode(arr)
  607. if err != nil {
  608. return nil, true, err
  609. }
  610. return jsonText(s), true, nil
  611. case "JSON_OBJECT", "JSONB_OBJECT":
  612. if len(args)%2 != 0 {
  613. return nil, true, fmt.Errorf("json_object() requires an even number of arguments")
  614. }
  615. obj := make(map[string]interface{}, len(args)/2)
  616. for i := 0; i+1 < len(args); i += 2 {
  617. key, ok := args[i].(string)
  618. if !ok {
  619. if jt, is := args[i].(jsonText); is {
  620. key = string(jt)
  621. } else {
  622. return nil, true, fmt.Errorf("json_object() labels must be TEXT")
  623. }
  624. }
  625. obj[key] = jsonArgToNode(args[i+1])
  626. }
  627. s, err := jsonEncode(obj)
  628. if err != nil {
  629. return nil, true, err
  630. }
  631. return jsonText(s), true, nil
  632. case "JSON_QUOTE", "JSONB_QUOTE":
  633. if len(args) != 1 {
  634. return nil, true, fmt.Errorf("json_quote() requires exactly one argument")
  635. }
  636. s, err := jsonEncode(jsonArgToNode(args[0]))
  637. if err != nil {
  638. return nil, true, err
  639. }
  640. return jsonText(s), true, nil
  641. }
  642. return nil, false, nil
  643. }
  644. // jsonPathArg extracts a path string from an argument.
  645. func jsonPathArg(v interface{}) (string, bool) {
  646. switch t := v.(type) {
  647. case string:
  648. return t, true
  649. case jsonText:
  650. return string(t), true
  651. default:
  652. return "", false
  653. }
  654. }
  655. // jsonRemove removes the node addressed by segs from a decoded tree.
  656. func jsonRemove(root interface{}, segs []jsonPathSeg) (interface{}, error) {
  657. if len(segs) == 0 {
  658. return root, nil
  659. }
  660. seg, resolved, err := resolveJSONBPathSegment(segs[0], root, true)
  661. if err != nil {
  662. return nil, err
  663. }
  664. if !resolved {
  665. return root, nil
  666. }
  667. last := len(segs) == 1
  668. if seg.isIndex {
  669. arr, ok := root.([]interface{})
  670. if !ok {
  671. return root, nil
  672. }
  673. idx := seg.index
  674. if seg.fromEnd {
  675. idx = len(arr) + idx
  676. }
  677. if idx < 0 || idx >= len(arr) {
  678. return root, nil
  679. }
  680. if last {
  681. out := make([]interface{}, 0, len(arr)-1)
  682. out = append(out, arr[:idx]...)
  683. out = append(out, arr[idx+1:]...)
  684. return out, nil
  685. }
  686. child, err := jsonRemove(arr[idx], segs[1:])
  687. if err != nil {
  688. return nil, err
  689. }
  690. out := append([]interface{}(nil), arr...)
  691. out[idx] = child
  692. return out, nil
  693. }
  694. obj, ok := root.(map[string]interface{})
  695. if !ok {
  696. return root, nil
  697. }
  698. if last {
  699. out := make(map[string]interface{}, len(obj))
  700. for k, v := range obj {
  701. if k != seg.key {
  702. out[k] = v
  703. }
  704. }
  705. return out, nil
  706. }
  707. child, exists := obj[seg.key]
  708. if !exists {
  709. return root, nil
  710. }
  711. newChild, err := jsonRemove(child, segs[1:])
  712. if err != nil {
  713. return nil, err
  714. }
  715. out := make(map[string]interface{}, len(obj))
  716. for k, v := range obj {
  717. out[k] = v
  718. }
  719. out[seg.key] = newChild
  720. return out, nil
  721. }