1
// Copyright 2014 BitPay Inc.
2
// Distributed under the MIT software license, see the accompanying
3
// file COPYING or https://opensource.org/licenses/mit-license.php.
4

            
5
#include <iomanip>
6
#include <stdio.h>
7
#include "univalue.h"
8
#include "univalue_escapes.h"
9

            
10
static std::string json_escape(const std::string& inS)
11
{
12
    std::string outS;
13
    outS.reserve(inS.size() * 2);
14

            
15
    for (unsigned int i = 0; i < inS.size(); i++) {
16
        unsigned char ch = static_cast<unsigned char>(inS[i]);
17
        const char *escStr = escapes[ch];
18

            
19
        if (escStr)
20
            outS += escStr;
21
        else
22
            outS += static_cast<char>(ch);
23
    }
24

            
25
    return outS;
26
}
27

            
28
std::string UniValue::write(unsigned int prettyIndent,
29
                            unsigned int indentLevel) const
30
{
31
    std::string s;
32
    s.reserve(1024);
33

            
34
    unsigned int modIndent = indentLevel;
35
    if (modIndent == 0)
36
        modIndent = 1;
37

            
38
    switch (typ) {
39
    case VNULL:
40
        s += "null";
41
        break;
42
    case VOBJ:
43
        writeObject(prettyIndent, modIndent, s);
44
        break;
45
    case VARR:
46
        writeArray(prettyIndent, modIndent, s);
47
        break;
48
    case VSTR:
49
        s += "\"" + json_escape(val) + "\"";
50
        break;
51
    case VNUM:
52
        s += val;
53
        break;
54
    case VBOOL:
55
        s += (val == "1" ? "true" : "false");
56
        break;
57
    }
58

            
59
    return s;
60
}
61

            
62
static void indentStr(unsigned int prettyIndent, unsigned int indentLevel, std::string& s)
63
{
64
    s.append(prettyIndent * indentLevel, ' ');
65
}
66

            
67
void UniValue::writeArray(unsigned int prettyIndent, unsigned int indentLevel, std::string& s) const
68
{
69
    s += "[";
70
    if (prettyIndent)
71
        s += "\n";
72

            
73
    for (unsigned int i = 0; i < values.size(); i++) {
74
        if (prettyIndent)
75
            indentStr(prettyIndent, indentLevel, s);
76
        s += values[i].write(prettyIndent, indentLevel + 1);
77
        if (i != (values.size() - 1)) {
78
            s += ",";
79
        }
80
        if (prettyIndent)
81
            s += "\n";
82
    }
83

            
84
    if (prettyIndent)
85
        indentStr(prettyIndent, indentLevel - 1, s);
86
    s += "]";
87
}
88

            
89
void UniValue::writeObject(unsigned int prettyIndent, unsigned int indentLevel, std::string& s) const
90
{
91
    s += "{";
92
    if (prettyIndent)
93
        s += "\n";
94

            
95
    for (unsigned int i = 0; i < keys.size(); i++) {
96
        if (prettyIndent)
97
            indentStr(prettyIndent, indentLevel, s);
98
        s += "\"" + json_escape(keys[i]) + "\":";
99
        if (prettyIndent)
100
            s += " ";
101
        s += values.at(i).write(prettyIndent, indentLevel + 1);
102
        if (i != (values.size() - 1))
103
            s += ",";
104
        if (prettyIndent)
105
            s += "\n";
106
    }
107

            
108
    if (prettyIndent)
109
        indentStr(prettyIndent, indentLevel - 1, s);
110
    s += "}";
111
}
112