• Home
  • History
  • Annotate
Name Date Size #Lines LOC

..03-May-2022-

docs/images/H03-May-2022-

script/H05-Jul-2018-12484

testdata/H05-Jul-2018-32,57432,549

vendor/github.com/H03-May-2022-168,259141,606

.gitignoreH A D05-Jul-201848 97

.travis.ymlH A D05-Jul-201850 86

ADVANCED.mkdH A D05-Jul-20185.8 KiB150132

CHANGELOG.mkdH A D05-Jul-20182.6 KiB10977

CONTRIBUTING.mkdH A D05-Jul-2018460 2518

LICENSEH A D05-Jul-20181 KiB2217

README.mkdH A D05-Jul-20186.6 KiB257213

identifier.goH A D05-Jul-20181.9 KiB8967

identifier_test.goH A D05-Jul-20181.6 KiB9274

main.goH A D05-Jul-20189.9 KiB409309

main_test.goH A D05-Jul-20187.2 KiB336278

original-gron.phpH A D05-Jul-20182.2 KiB10061

statements.goH A D05-Jul-201810 KiB429295

statements_test.goH A D05-Jul-20184.1 KiB205176

token.goH A D05-Jul-20184.3 KiB204145

token_test.goH A D05-Jul-20181.2 KiB5345

ungron.goH A D05-Jul-201810.9 KiB516362

ungron_test.goH A D05-Jul-20185.6 KiB293254

url.goH A D05-Jul-2018736 4234

url_test.goH A D05-Jul-2018428 2622

README.mkd

1# gron
2[![Build Status](https://travis-ci.org/tomnomnom/gron.svg?branch=master)](https://travis-ci.org/tomnomnom/gron)
3
4Make JSON greppable!
5
6gron transforms JSON into discrete assignments to make it easier to `grep` for what you want and see the absolute 'path' to it.
7It eases the exploration of APIs that return large blobs of JSON but have terrible documentation.
8
9<pre>
10▶ <b>gron</b> "https://api.github.com/repos/tomnomnom/gron/commits?per_page=1" | fgrep "commit.author"
11json[0].commit.author = {};
12json[0].commit.author.date = "2016-07-02T10:51:21Z";
13json[0].commit.author.email = "mail@tomnomnom.com";
14json[0].commit.author.name = "Tom Hudson";
15</pre>
16
17gron can work backwards too, enabling you to turn your filtered data back into JSON:
18<pre>
19▶ gron "https://api.github.com/repos/tomnomnom/gron/commits?per_page=1" | fgrep "commit.author" | <b>gron --ungron</b>
20[
21  {
22    "commit": {
23      "author": {
24        "date": "2016-07-02T10:51:21Z",
25        "email": "mail@tomnomnom.com",
26        "name": "Tom Hudson"
27      }
28    }
29  }
30]
31</pre>
32
33> Disclaimer: the GitHub API has fantastic documentation, but it makes for a good example.
34
35## Installation
36
37gron has no runtime dependencies. You can just [download a binary for Linux, Mac, Windows or FreeBSD and run it](https://github.com/tomnomnom/gron/releases).
38Put the binary in your `$PATH` (e.g. in `/usr/local/bin`) to make it easy to use:
39```
40▶ tar xzf gron-linux-amd64-0.1.5.tgz
41▶ sudo mv gron /usr/local/bin/
42```
43
44If you're a Mac user you can also [install gron via brew](http://braumeister.org/formula/gron):
45```
46▶ brew install gron
47```
48
49Or if you're a Go user you can use `go get` (if you're using Go 1.7 or newer):
50
51```
52▶ go get -u github.com/tomnomnom/gron
53```
54
55It's recommended that you alias `ungron` or `norg` (or both!) to `gron --ungron`. Put something like this in your shell profile (e.g. in `~/.bashrc`):
56```
57alias norg="gron --ungron"
58alias ungron="gron --ungron"
59```
60Or you could create a shell script in your $PATH named `ungron` or `norg` to affect all users:
61```
62gron --ungron "$@"
63```
64
65## Usage
66
67Get JSON from a file:
68
69```
70▶ gron testdata/two.json
71json = {};
72json.contact = {};
73json.contact.email = "mail@tomnomnom.com";
74json.contact.twitter = "@TomNomNom";
75json.github = "https://github.com/tomnomnom/";
76json.likes = [];
77json.likes[0] = "code";
78json.likes[1] = "cheese";
79json.likes[2] = "meat";
80json.name = "Tom";
81```
82
83From a URL:
84
85```
86▶ gron http://headers.jsontest.com/
87json = {};
88json.Host = "headers.jsontest.com";
89json["User-Agent"] = "gron/0.1";
90json["X-Cloud-Trace-Context"] = "6917a823919477919dbc1523584ba25d/11970839830843610056";
91```
92
93Or from `stdin`:
94
95```
96▶ curl -s http://headers.jsontest.com/ | gron
97json = {};
98json.Accept = "*/*";
99json.Host = "headers.jsontest.com";
100json["User-Agent"] = "curl/7.43.0";
101json["X-Cloud-Trace-Context"] = "c70f7bf26661c67d0b9f2cde6f295319/13941186890243645147";
102```
103
104Grep for something and easily see the path to it:
105
106```
107▶ gron testdata/two.json | grep twitter
108json.contact.twitter = "@TomNomNom";
109```
110
111gron makes diffing JSON easy too:
112
113```
114▶ diff <(gron two.json) <(gron two-b.json)
1153c3
116< json.contact.email = "mail@tomnomnom.com";
117---
118> json.contact.email = "contact@tomnomnom.com";
119```
120
121The output of `gron` is valid JavaScript:
122
123```
124▶ gron testdata/two.json > tmp.js
125▶ echo "console.log(json);" >> tmp.js
126▶ nodejs tmp.js
127{ contact: { email: 'mail@tomnomnom.com', twitter: '@TomNomNom' },
128  github: 'https://github.com/tomnomnom/',
129  likes: [ 'code', 'cheese', 'meat' ],
130  name: 'Tom' }
131```
132
133It's also possible to obtain the `gron` output as JSON stream via
134the `--json` switch:
135
136```
137▶ curl -s http://headers.jsontest.com/ | gron --json
138[[],{}]
139[["Accept"],"*/*"]
140[["Host"],"headers.jsontest.com"]
141[["User-Agent"],"curl/7.43.0"]
142[["X-Cloud-Trace-Context"],"c70f7bf26661c67d0b9f2cde6f295319/13941186890243645147"]
143```
144
145## ungronning
146gron can also turn its output back into JSON:
147```
148▶ gron testdata/two.json | gron -u
149{
150  "contact": {
151    "email": "mail@tomnomnom.com",
152    "twitter": "@TomNomNom"
153  },
154  "github": "https://github.com/tomnomnom/",
155  "likes": [
156    "code",
157    "cheese",
158    "meat"
159  ],
160  "name": "Tom"
161}
162```
163
164This means you use can use gron with `grep` and other tools to modify JSON:
165```
166▶ gron testdata/two.json | grep likes | gron --ungron
167{
168  "likes": [
169    "code",
170    "cheese",
171    "meat"
172  ]
173}
174```
175
176or
177
178
179```
180▶ gron --json testdata/two.json | grep likes | gron  --json --ungron
181{
182  "likes": [
183    "code",
184    "cheese",
185    "meat"
186  ]
187}
188```
189
190To preserve array keys, arrays are padded with `null` when values are missing:
191```
192▶ gron testdata/two.json | grep likes | grep -v cheese
193json.likes = [];
194json.likes[0] = "code";
195json.likes[2] = "meat";
196▶ gron testdata/two.json | grep likes | grep -v cheese | gron --ungron
197{
198  "likes": [
199    "code",
200    null,
201    "meat"
202  ]
203}
204```
205
206If you get creative you can do [some pretty neat tricks with gron](ADVANCED.mkd), and
207then ungron the output back into JSON.
208
209## Get Help
210
211```
212▶ gron --help
213Transform JSON (from a file, URL, or stdin) into discrete assignments to make it greppable
214
215Usage:
216  gron [OPTIONS] [FILE|URL|-]
217
218Options:
219  -u, --ungron     Reverse the operation (turn assignments back into JSON)
220  -c, --colorize   Colorize output (default on tty)
221  -m, --monochrome Monochrome (don't colorize output)
222  -s, --stream     Treat each line of input as a separate JSON object
223  -k, --insecure   Disable certificate validation
224  -j, --json       Represent gron data as JSON stream
225      --no-sort    Don't sort output (faster)
226      --version    Print version information
227
228Exit Codes:
229  0	OK
230  1	Failed to open file
231  2	Failed to read input
232  3	Failed to form statements
233  4	Failed to fetch URL
234  5	Failed to parse statements
235  6	Failed to encode JSON
236
237Examples:
238  gron /tmp/apiresponse.json
239  gron http://jsonplaceholder.typicode.com/users/1
240  curl -s http://jsonplaceholder.typicode.com/users/1 | gron
241  gron http://jsonplaceholder.typicode.com/users/1 | grep company | gron --ungron
242```
243
244## FAQ
245### Wasn't this written in PHP before?
246Yes it was! The original version is [preserved here for posterity](https://github.com/tomnomnom/gron/blob/master/original-gron.php).
247
248### Why the change to Go?
249Mostly to remove PHP as a dependency. There's a lot of people who work with JSON who don't have PHP installed.
250
251### Why shouldn't I just use jq?
252[jq](https://stedolan.github.io/jq/) is *awesome*, and a lot more powerful than gron, but with that power comes
253complexity. gron aims to make it easier to use the tools you already know, like `grep` and `sed`.
254
255gron's primary purpose is to make it easy to find the path to a value in a deeply nested JSON blob
256when you don't already know the structure; much of jq's power is unlocked only once you know that structure.
257