aboutsummaryrefslogtreecommitdiff
path: root/src/libexpr/value-to-json.cc
diff options
context:
space:
mode:
authorEelco Dolstra <eelco.dolstra@logicblox.com>2016-08-26 18:55:55 +0200
committerEelco Dolstra <eelco.dolstra@logicblox.com>2016-08-29 17:29:24 +0200
commitc0a7b84748d5e27e6804117b8a57ce71269c3c66 (patch)
tree40f22e1dd5636673f764bc1f289ab254971ca95d /src/libexpr/value-to-json.cc
parent9fa21765e7f267efcc65e1aa6ab21402ea6125ad (diff)
nix path-info: Add --json flag
Also, factor out JSON generation from value-to-json.{cc,hh}, and support producing indented JSON.
Diffstat (limited to 'src/libexpr/value-to-json.cc')
-rw-r--r--src/libexpr/value-to-json.cc55
1 files changed, 23 insertions, 32 deletions
diff --git a/src/libexpr/value-to-json.cc b/src/libexpr/value-to-json.cc
index 47ee324a6..72e413e44 100644
--- a/src/libexpr/value-to-json.cc
+++ b/src/libexpr/value-to-json.cc
@@ -1,4 +1,5 @@
#include "value-to-json.hh"
+#include "json.hh"
#include "eval-inline.hh"
#include "util.hh"
@@ -8,24 +9,8 @@
namespace nix {
-
-void escapeJSON(std::ostream & str, const string & s)
-{
- str << "\"";
- for (auto & i : s)
- if (i == '\"' || i == '\\') str << "\\" << i;
- else if (i == '\n') str << "\\n";
- else if (i == '\r') str << "\\r";
- else if (i == '\t') str << "\\t";
- else if (i >= 0 && i < 32)
- str << "\\u" << std::setfill('0') << std::setw(4) << std::hex << (uint16_t) i << std::dec;
- else str << i;
- str << "\"";
-}
-
-
void printValueAsJSON(EvalState & state, bool strict,
- Value & v, std::ostream & str, PathSet & context)
+ Value & v, JSONPlaceholder & out, PathSet & context)
{
checkInterrupt();
@@ -34,58 +19,58 @@ void printValueAsJSON(EvalState & state, bool strict,
switch (v.type) {
case tInt:
- str << v.integer;
+ out.write(v.integer);
break;
case tBool:
- str << (v.boolean ? "true" : "false");
+ out.write(v.boolean);
break;
case tString:
copyContext(v, context);
- escapeJSON(str, v.string.s);
+ out.write(v.string.s);
break;
case tPath:
- escapeJSON(str, state.copyPathToStore(context, v.path));
+ out.write(state.copyPathToStore(context, v.path));
break;
case tNull:
- str << "null";
+ out.write(nullptr);
break;
case tAttrs: {
Bindings::iterator i = v.attrs->find(state.sOutPath);
if (i == v.attrs->end()) {
- JSONObject json(str);
+ auto obj(out.object());
StringSet names;
for (auto & j : *v.attrs)
names.insert(j.name);
for (auto & j : names) {
Attr & a(*v.attrs->find(state.symbols.create(j)));
- json.attr(j);
- printValueAsJSON(state, strict, *a.value, str, context);
+ auto placeholder(obj.placeholder(j));
+ printValueAsJSON(state, strict, *a.value, placeholder, context);
}
} else
- printValueAsJSON(state, strict, *i->value, str, context);
+ printValueAsJSON(state, strict, *i->value, out, context);
break;
}
case tList1: case tList2: case tListN: {
- JSONList json(str);
+ auto list(out.list());
for (unsigned int n = 0; n < v.listSize(); ++n) {
- json.elem();
- printValueAsJSON(state, strict, *v.listElems()[n], str, context);
+ auto placeholder(list.placeholder());
+ printValueAsJSON(state, strict, *v.listElems()[n], placeholder, context);
}
break;
}
case tExternal:
- v.external->printValueAsJSON(state, strict, str, context);
+ v.external->printValueAsJSON(state, strict, out, context);
break;
case tFloat:
- str << v.fpoint;
+ out.write(v.fpoint);
break;
default:
@@ -93,9 +78,15 @@ void printValueAsJSON(EvalState & state, bool strict,
}
}
+void printValueAsJSON(EvalState & state, bool strict,
+ Value & v, std::ostream & str, PathSet & context)
+{
+ JSONPlaceholder out(str);
+ printValueAsJSON(state, strict, v, out, context);
+}
void ExternalValueBase::printValueAsJSON(EvalState & state, bool strict,
- std::ostream & str, PathSet & context) const
+ JSONPlaceholder & out, PathSet & context) const
{
throw TypeError(format("cannot convert %1% to JSON") % showType());
}