xref: /freebsd/contrib/libxo/doc/xo.rst (revision 7899f917b1c0ea178f1d2be0cfb452086d079d23)
1.. index:: --libxo, xo
2.. _xo:
3
4The "xo" Utility
5================
6
7The `xo` utility allows command line access to the functionality of
8the libxo library.  Using `xo`, shell scripts can emit XML, JSON, and
9HTML using the same commands that emit text output.
10
11The style of output can be selected using a specific option: "-X" for
12XML, "-J" for JSON, "-H" for HTML, or "-T" for TEXT, which is the
13default.  The "--style <style>" option can also be used.  The standard
14set of "--libxo" options are available (see :ref:`options`), as well
15as the :ref:`LIBXO_OPTIONS <libxo-options>` environment variable.
16
17The `xo` utility accepts a format string suitable for `xo_emit` and
18a set of zero or more arguments used to supply data for that string::
19
20    xo "The {k:name} weighs {:weight/%d} pounds.\n" fish 6
21
22  TEXT:
23    The fish weighs 6 pounds.
24
25  XML:
26    <name>fish</name>
27    <weight>6</weight>
28
29  JSON:
30    "name": "fish",
31    "weight": 6
32
33  HTML:
34    <div class="line">
35      <div class="text">The </div>
36      <div class="data" data-tag="name">fish</div>
37      <div class="text"> weighs </div>
38      <div class="data" data-tag="weight">6</div>
39      <div class="text"> pounds.</div>
40    </div>
41
42The `--wrap $path` option can be used to wrap emitted content in a
43specific hierarchy.  The path is a set of hierarchical names separated
44by the '/' character::
45
46    xo --wrap top/a/b/c '{:tag}' value
47
48  XML:
49    <top>
50      <a>
51        <b>
52          <c>
53            <tag>value</tag>
54          </c>
55        </b>
56      </a>
57    </top>
58
59  JSON:
60    "top": {
61      "a": {
62        "b": {
63          "c": {
64            "tag": "value"
65          }
66        }
67      }
68    }
69
70The `--open $path` and `--close $path` can be used to emit
71hierarchical information without the matching close and open
72tag.  This allows a shell script to emit open tags, data, and
73then close tags.  The `--depth` option may be used to set the
74depth for indentation.  The `--leading-xpath` may be used to
75prepend data to the XPath values used for HTML output style::
76
77  EXAMPLE:
78    #!/bin/sh
79    xo --open top/data
80    xo --depth 2 '{:tag}' value
81    xo --close top/data
82
83  XML:
84    <top>
85      <data>
86        <tag>value</tag>
87      </data>
88    </top>
89
90  JSON:
91    "top": {
92      "data": {
93        "tag": "value"
94      }
95    }
96
97When making partial lines of output (where the format string does not
98include a newline), use the `--continuation` option to let secondary
99invocations know they are adding data to an existing line.
100
101When emitting a series of objects, use the `--not-first` option to
102ensure that any details from the previous object (e.g. commas in JSON)
103are handled correctly.
104
105Use the `--top-wrap` option to ensure any top-level object details are
106handled correctly, e.g. wrap the entire output in a top-level set of
107braces for JSON output.
108
109::
110
111  EXAMPLE:
112    #!/bin/sh
113    xo --top-wrap --open top/data
114    xo --depth 2 'First {:tag} ' value1
115    xo --depth 2 --continuation 'and then {:tag}\n' value2
116    xo --top-wrap --close top/data
117
118  TEXT:
119    First value1 and then value2
120
121  HTML:
122    <div class="line">
123      <div class="text">First </div>
124      <div class="data" data-tag="tag">value1</div>
125      <div class="text"> </div>
126      <div class="text">and then </div>
127      <div class="data" data-tag="tag">value2</div>
128    </div>
129
130  XML:
131    <top>
132      <data>
133        <tag>value1</tag>
134        <tag>value2</tag>
135      </data>
136    </top>
137
138  JSON:
139    {
140      "top": {
141        "data": {
142        "tag": "value1",
143        "tag": "value2"
144        }
145      }
146    }
147
148Lists and Instances
149-------------------
150
151A "*list*" is set of one or more instances that appear under the same
152parent.  The instances contain details about a specific object.  One
153can think of instances as objects or records.  A call is needed to
154open and close the list, while a distinct call is needed to open and
155close each instance of the list.
156
157Use the `--open-list` and `--open-instances` to open lists and
158instances.  Use the `--close-list` and `--close-instances` to close
159them.  Each of these options take a `name` parameter, providing the
160name of the list and instance.
161
162In the following example, a list named "machine" is created with three
163instances::
164
165    opts="--json"
166    xo $opts --open-list machine
167    NF=
168    for name in red green blue; do
169        xo $opts --depth 1 $NF --open-instance machine
170        xo $opts --depth 2 "Machine {k:name} has {:memory}\n" $name 55
171        xo $opts --depth 1 --close-instance machine
172        NF=--not-first
173    done
174    xo $opts $NF --close-list machine
175
176The normal `libxo` functions use a state machine to help these
177transitions, but since each `xo` command is invoked independent of the
178previous calls, the state must be passed in explicitly via these
179command line options.
180
181The `--instance` option can be used to treat a single `xo` invocation
182as an instance with the given set of fields::
183
184  % xo --libxo:XP --instance foo 'The {:product} is {:status}\n' stereo "in route"
185  <foo>
186    <product>stereo</product>
187    <status>in route</status>
188  </foo>
189
190Command Line Options
191--------------------
192
193::
194
195  Usage: xo [options] format [fields]
196    --close <path>        Close tags for the given path
197    --close-instance <name> Close an open instance name
198    --close-list <name>   Close an open list name
199    --continuation OR -C  Output belongs on same line as previous output
200    --depth <num>         Set the depth for pretty printing
201    --help                Display this help text
202    --html OR -H          Generate HTML output
203    --instance OR -I <name> Wrap in an instance of the given name
204    --json OR -J          Generate JSON output
205    --leading-xpath <path> Add a prefix to generated XPaths (HTML)
206    --not-first           Indicate this object is not the first (JSON)
207    --open <path>         Open tags for the given path
208    --open-instance <name> Open an instance given by name
209    --open-list <name>   Open a list given by name
210    --option <opts> -or -O <opts>  Give formatting options
211    --pretty OR -p        Make 'pretty' output (add indent, newlines)
212    --style <style>       Generate given style (xml, json, text, html)
213    --text OR -T          Generate text output (the default style)
214    --top-wrap            Generate a top-level object wrapper (JSON)
215    --version             Display version information
216    --warn OR -W          Display warnings in text on stderr
217    --warn-xml            Display warnings in xml on stdout
218    --wrap <path>         Wrap output in a set of containers
219    --xml OR -X           Generate XML output
220    --xpath               Add XPath data to HTML output)
221
222Example
223-------
224
225::
226
227  % xo 'The {:product} is {:status}\n' stereo "in route"
228  The stereo is in route
229  % xo -p -X 'The {:product} is {:status}\n' stereo "in route"
230  <product>stereo</product>
231  <status>in route</status>
232  % xo --libxo xml,pretty 'The {:product} is {:status}\n' stereo "in route"
233  <product>stereo</product>
234  <status>in route</status>
235