Skip to content

Commit

Permalink
Destructuring array matcher should not match string codepoints
Browse files Browse the repository at this point in the history
  • Loading branch information
nicowilliams committed Jul 26, 2023
1 parent 3f61e23 commit 3590d6c
Show file tree
Hide file tree
Showing 6 changed files with 23 additions and 3 deletions.
7 changes: 7 additions & 0 deletions docs/content/manual/manual.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2983,6 +2983,10 @@ sections:
value at the index for an array pattern element, `null` is
bound to that variable.
Note that array patterns do not match strings. That is, `.
as [$x]` will not match the first codepoint in `.` if `.` is
a string.
Variables are scoped over the rest of the expression that defines
them, so
Expand Down Expand Up @@ -3059,6 +3063,9 @@ sections:
- program: '.[] as [$a] ?// [$b] | if $a != null then error("err: \($a)") else {$a,$b} end'
input: '[[3]]'
output: ['{"a":null,"b":3}']
- program: '. as [$x] ?// $x | $x'
input: '"abc"'
output: ['"abc"']

- title: 'Defining Functions'
body: |
Expand Down
7 changes: 7 additions & 0 deletions jq.1.prebuilt

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion src/compile.c
Original file line number Diff line number Diff line change
Expand Up @@ -995,7 +995,7 @@ block gen_array_matcher(block left, block curr) {

// `left` goes at the end so that the const index is in a predictable place
return BLOCK(gen_op_simple(DUP), gen_subexp(gen_const(jv_number(index))),
gen_op_simple(INDEX), curr, left);
gen_op_simple(INDEX_D), curr, left);
}

block gen_object_matcher(block name, block curr) {
Expand Down
5 changes: 3 additions & 2 deletions src/execute.c
Original file line number Diff line number Diff line change
Expand Up @@ -674,11 +674,12 @@ jv jq_next(jq_state *jq) {
}

case INDEX:
case INDEX_D:
case INDEX_OPT: {
jv t = stack_pop(jq);
jv k = stack_pop(jq);
jv v;
if (jv_get_kind(t) == JV_KIND_STRING && jv_get_kind(k) == JV_KIND_NUMBER) {
if (opcode != INDEX_D && jv_get_kind(t) == JV_KIND_STRING && jv_get_kind(k) == JV_KIND_NUMBER) {
switch (jv_get_string_kind(t)) {
case JV_STRING_KIND_UTF8:
uint32_t c = jv_string_index(t, jv_number_value(k));
Expand Down Expand Up @@ -730,7 +731,7 @@ jv jq_next(jq_state *jq) {
stack_push(jq, v);
} else {
jv_free(k);
if (opcode == INDEX)
if (opcode == INDEX || opcode == INDEX_D)
set_error(jq, v);
else
jv_free(v);
Expand Down
1 change: 1 addition & 0 deletions src/opcode_list.h
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ OP(STOREV, VARIABLE, 1, 0)
OP(STORE_GLOBAL, GLOBAL, 0, 0)
OP(INDEX, NONE, 2, 1)
OP(INDEX_OPT, NONE, 2, 1)
OP(INDEX_D, NONE, 2, 1) /* For gen_array_matcher() -- destructuring */
OP(EACH, NONE, 1, 1)
OP(EACH_OPT, NONE, 1, 1)
OP(FORK, BRANCH, 0, 0)
Expand Down
4 changes: 4 additions & 0 deletions tests/man.test

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

0 comments on commit 3590d6c

Please sign in to comment.