Add --argfile variant of --arg (issue #117)
This is useful when one has a database (in JSON form) to query using jq
input data.
% echo '{"a":1, "c":5}' > db.json
% echo '"c"'|./jq --argfile f /tmp/a '$f[.]'
5
% echo '"a"'|./jq --argfile f /tmp/a '$f[.]'
1
% echo '"b"'|./jq --argfile f /tmp/a '$f[.]'
null
%
This commit is contained in:
1 parent
0535e724a2
commit
03598bb5d6
2 files changed
+46
-4
No files matched your search
@@ -127,6 +127,14 @@ sections:
|
|||||||
variable. If you run jq with `--arg foo bar`, then `$foo` is
|
variable. If you run jq with `--arg foo bar`, then `$foo` is
|
||||||
available in the program and has the value `"bar"`.
|
available in the program and has the value `"bar"`.
|
||||||
|
|
||||||
|
* `--argfile name filename`:
|
||||||
|
|
||||||
|
This option passes the first value from the named file as a
|
||||||
|
value to the jq program as a predefined variable. If you run jq
|
||||||
|
with `--argfile foo bar`, then `$foo` is available in the
|
||||||
|
program and has the value resulting from parsing the content of
|
||||||
|
the file named `bar`.
|
||||||
|
|
||||||
- title: Basic filters
|
- title: Basic filters
|
||||||
entries:
|
entries:
|
||||||
- title: "`.`"
|
- title: "`.`"
|
||||||
|
|||||||
@@ -92,18 +92,32 @@ static void process(jv value, int flags) {
|
|||||||
jq_teardown(&jq);
|
jq_teardown(&jq);
|
||||||
}
|
}
|
||||||
|
|
||||||
static jv slurp_file(const char* filename) {
|
static jv slurp_file(const char* filename, int raw) {
|
||||||
FILE* file = fopen(filename, "r");
|
FILE* file = fopen(filename, "r");
|
||||||
|
struct jv_parser parser;
|
||||||
|
jv data;
|
||||||
if (!file) {
|
if (!file) {
|
||||||
return jv_invalid_with_msg(jv_string_fmt("Could not open %s: %s",
|
return jv_invalid_with_msg(jv_string_fmt("Could not open %s: %s",
|
||||||
filename,
|
filename,
|
||||||
strerror(errno)));
|
strerror(errno)));
|
||||||
}
|
}
|
||||||
jv data = jv_string("");
|
if (raw) {
|
||||||
|
data = jv_string("");
|
||||||
|
} else {
|
||||||
|
data = jv_array();
|
||||||
|
jv_parser_init(&parser);
|
||||||
|
}
|
||||||
while (!feof(file) && !ferror(file)) {
|
while (!feof(file) && !ferror(file)) {
|
||||||
char buf[4096];
|
char buf[4096];
|
||||||
size_t n = fread(buf, 1, sizeof(buf), file);
|
size_t n = fread(buf, 1, sizeof(buf), file);
|
||||||
data = jv_string_concat(data, jv_string_sized(buf, (int)n));
|
if (raw) {
|
||||||
|
data = jv_string_concat(data, jv_string_sized(buf, (int)n));
|
||||||
|
} else {
|
||||||
|
jv_parser_set_buf(&parser, buf, strlen(buf), !feof(file));
|
||||||
|
jv value;
|
||||||
|
while (jv_is_valid((value = jv_parser_next(&parser))))
|
||||||
|
data = jv_array_append(data, value);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
int badread = ferror(file);
|
int badread = ferror(file);
|
||||||
fclose(file);
|
fclose(file);
|
||||||
@@ -197,6 +211,26 @@ int main(int argc, char* argv[]) {
|
|||||||
arg = jv_object_set(arg, jv_string("value"), jv_string(argv[i+2]));
|
arg = jv_object_set(arg, jv_string("value"), jv_string(argv[i+2]));
|
||||||
program_arguments = jv_array_append(program_arguments, arg);
|
program_arguments = jv_array_append(program_arguments, arg);
|
||||||
i += 2; // skip the next two arguments
|
i += 2; // skip the next two arguments
|
||||||
|
} else if (isoption(argv[i], 0, "argfile")) {
|
||||||
|
if (i >= argc - 2) {
|
||||||
|
fprintf(stderr, "%s: --argfile takes two parameters (e.g. -a varname filename)\n", progname);
|
||||||
|
die();
|
||||||
|
}
|
||||||
|
jv arg = jv_object();
|
||||||
|
arg = jv_object_set(arg, jv_string("name"), jv_string(argv[i+1]));
|
||||||
|
jv data = slurp_file(argv[i+2], 0);
|
||||||
|
if (!jv_is_valid(data)) {
|
||||||
|
data = jv_invalid_get_msg(data);
|
||||||
|
fprintf(stderr, "%s: Bad JSON in --argfile %s %s: %s\n", progname,
|
||||||
|
argv[i+1], argv[i+2], jv_string_value(data));
|
||||||
|
jv_free(data);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
if (jv_array_length(data) == 1)
|
||||||
|
data = jv_array_get(data, 0);
|
||||||
|
arg = jv_object_set(arg, jv_string("value"), data);
|
||||||
|
program_arguments = jv_array_append(program_arguments, arg);
|
||||||
|
i += 2; // skip the next two arguments
|
||||||
} else if (isoption(argv[i], 0, "debug-dump-disasm")) {
|
} else if (isoption(argv[i], 0, "debug-dump-disasm")) {
|
||||||
options |= DUMP_DISASM;
|
options |= DUMP_DISASM;
|
||||||
} else if (isoption(argv[i], 0, "debug-trace")) {
|
} else if (isoption(argv[i], 0, "debug-trace")) {
|
||||||
@@ -220,7 +254,7 @@ int main(int argc, char* argv[]) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (options & FROM_FILE) {
|
if (options & FROM_FILE) {
|
||||||
jv data = slurp_file(program);
|
jv data = slurp_file(program, 1);
|
||||||
if (!jv_is_valid(data)) {
|
if (!jv_is_valid(data)) {
|
||||||
data = jv_invalid_get_msg(data);
|
data = jv_invalid_get_msg(data);
|
||||||
fprintf(stderr, "%s: %s\n", progname, jv_string_value(data));
|
fprintf(stderr, "%s: %s\n", progname, jv_string_value(data));
|
||||||
|
|||||||
Reference in new issue
Block a user