jsonpretty 1.0.0 → 1.2.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 89641014acab0632260843ff87e190604e7342d386109dfa77245ec343ff1ee4
4
+ data.tar.gz: 7fe4a6155fed431b9c64735fa3a8c133354c293a60d9a03c5786a15f3e31348d
5
+ SHA512:
6
+ metadata.gz: 17e783dbab3458c8c46ef6b9cb3f6065f6552eccbe65b6ba408003709bed7cbc92e98ab4f3d09750363fd2fbd7426df7accb2ea4716ec24f53b5c92e24789d14
7
+ data.tar.gz: d3b01927f851234aba103921e43b8db1cc2d07383ea73c825b78027cd6bfacf8b763be0112aff91ba8e08dd53a1b27d61129aa1dd10861a4267e438d3d7dd6e2
data/.gitignore ADDED
@@ -0,0 +1,5 @@
1
+ *.gem
2
+ pkg
3
+ /Gemfile.lock
4
+
5
+ dist/
data/.goreleaser.yaml ADDED
@@ -0,0 +1,30 @@
1
+ # This is an example .goreleaser.yml file with some sensible defaults.
2
+ # Make sure to check the documentation at https://goreleaser.com
3
+ before:
4
+ hooks:
5
+ # You may remove this if you don't use go modules.
6
+ - go mod tidy
7
+ builds:
8
+ - env:
9
+ - CGO_ENABLED=0
10
+ goos:
11
+ - linux
12
+ - windows
13
+ - darwin
14
+ archives:
15
+ - replacements:
16
+ darwin: Darwin
17
+ linux: Linux
18
+ windows: Windows
19
+ 386: i386
20
+ amd64: x86_64
21
+ checksum:
22
+ name_template: 'checksums.txt'
23
+ snapshot:
24
+ name_template: "{{ incpatch .Version }}-next"
25
+ changelog:
26
+ sort: asc
27
+ filters:
28
+ exclude:
29
+ - '^docs:'
30
+ - '^test:'
@@ -0,0 +1,74 @@
1
+ # Contributor Covenant Code of Conduct
2
+
3
+ ## Our Pledge
4
+
5
+ In the interest of fostering an open and welcoming environment, we as
6
+ contributors and maintainers pledge to making participation in our project and
7
+ our community a harassment-free experience for everyone, regardless of age, body
8
+ size, disability, ethnicity, gender identity and expression, level of experience,
9
+ nationality, personal appearance, race, religion, or sexual identity and
10
+ orientation.
11
+
12
+ ## Our Standards
13
+
14
+ Examples of behavior that contributes to creating a positive environment
15
+ include:
16
+
17
+ * Using welcoming and inclusive language
18
+ * Being respectful of differing viewpoints and experiences
19
+ * Gracefully accepting constructive criticism
20
+ * Focusing on what is best for the community
21
+ * Showing empathy towards other community members
22
+
23
+ Examples of unacceptable behavior by participants include:
24
+
25
+ * The use of sexualized language or imagery and unwelcome sexual attention or
26
+ advances
27
+ * Trolling, insulting/derogatory comments, and personal or political attacks
28
+ * Public or private harassment
29
+ * Publishing others' private information, such as a physical or electronic
30
+ address, without explicit permission
31
+ * Other conduct which could reasonably be considered inappropriate in a
32
+ professional setting
33
+
34
+ ## Our Responsibilities
35
+
36
+ Project maintainers are responsible for clarifying the standards of acceptable
37
+ behavior and are expected to take appropriate and fair corrective action in
38
+ response to any instances of unacceptable behavior.
39
+
40
+ Project maintainers have the right and responsibility to remove, edit, or
41
+ reject comments, commits, code, wiki edits, issues, and other contributions
42
+ that are not aligned to this Code of Conduct, or to ban temporarily or
43
+ permanently any contributor for other behaviors that they deem inappropriate,
44
+ threatening, offensive, or harmful.
45
+
46
+ ## Scope
47
+
48
+ This Code of Conduct applies both within project spaces and in public spaces
49
+ when an individual is representing the project or its community. Examples of
50
+ representing a project or community include using an official project e-mail
51
+ address, posting via an official social media account, or acting as an appointed
52
+ representative at an online or offline event. Representation of a project may be
53
+ further defined and clarified by project maintainers.
54
+
55
+ ## Enforcement
56
+
57
+ Instances of abusive, harassing, or otherwise unacceptable behavior may be
58
+ reported by contacting the project team at nick@nicksieger.com. All
59
+ complaints will be reviewed and investigated and will result in a response that
60
+ is deemed necessary and appropriate to the circumstances. The project team is
61
+ obligated to maintain confidentiality with regard to the reporter of an incident.
62
+ Further details of specific enforcement policies may be posted separately.
63
+
64
+ Project maintainers who do not follow or enforce the Code of Conduct in good
65
+ faith may face temporary or permanent repercussions as determined by other
66
+ members of the project's leadership.
67
+
68
+ ## Attribution
69
+
70
+ This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4,
71
+ available at [http://contributor-covenant.org/version/1/4][version]
72
+
73
+ [homepage]: http://contributor-covenant.org
74
+ [version]: http://contributor-covenant.org/version/1/4/
data/Gemfile ADDED
@@ -0,0 +1,6 @@
1
+ source "https://rubygems.org"
2
+
3
+ git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }
4
+
5
+ # Specify your gem's dependencies in jsonpretty.gemspec
6
+ gemspec
data/History.txt CHANGED
@@ -1,3 +1,19 @@
1
+ === 1.2.0 / 2021-12-30
2
+
3
+ * New version to correspond with go port
4
+
5
+ === 1.1.2 / 2021-12-27
6
+
7
+ * Fix regex typo, thanks Sami Samhuri
8
+
9
+ === 1.1.1 / 2021-12-17
10
+
11
+ * Handles any HTTP version
12
+
13
+ === 1.1.0 / 2010-01-20
14
+
15
+ * Parses and displays jsonp–flavored json
16
+
1
17
  === 1.0.0 / 2009-02-20
2
18
 
3
19
  * 1 major enhancement
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2007-2021 Nick Sieger <nick@nicksieger.com>
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,45 @@
1
+ # jsonpretty
2
+
3
+ - http://github.com/nicksieger/jsonpretty
4
+
5
+ ## DESCRIPTION
6
+
7
+ Command-line JSON pretty-printer, using the json gem.
8
+
9
+ ## FEATURES/PROBLEMS
10
+
11
+ - Parse and pretty-print JSON/JSONP either from stdin or from command-line
12
+ arguments.
13
+ - All arguments are concatenated together in a single string for
14
+ pretty-printing.
15
+ - Use '@filename' as an argument to include the contents of the file.
16
+ - Use '-' or '@-' as an argument (or use no arguments) to read stdin.
17
+ - Detects HTTP response/headers, prints them untouched, and skips to
18
+ the body (for use with `curl -i').
19
+
20
+ ## SYNOPSIS
21
+
22
+ ```
23
+ curl -i http://api.com/json | jsonpretty
24
+ ```
25
+
26
+ ## REQUIREMENTS
27
+
28
+ json or json_pure
29
+
30
+ ## INSTALL
31
+
32
+ ```
33
+ gem install jsonpretty
34
+ ```
35
+
36
+ or install globally with brew-gem:
37
+
38
+ ```
39
+ brew install brew-gem
40
+ brew gem install jsonpretty
41
+ ```
42
+
43
+ ## LICENSE
44
+
45
+ See [LICENSE](LICENSE.txt).
data/Rakefile CHANGED
@@ -1,28 +1,4 @@
1
1
  # -*- ruby -*-
2
2
 
3
- require 'rubygems'
4
- require 'hoe'
5
- require './lib/jsonpretty.rb'
3
+ require "bundler/gem_tasks"
6
4
 
7
- h = Hoe.new('jsonpretty', Jsonpretty::VERSION) do |p|
8
- p.rubyforge_name = 'caldersphere'
9
- p.developer('Nick Sieger', 'nick@nicksieger.com')
10
- p.url = 'http://github.com/nicksieger/jsonpretty'
11
- p.extra_deps << ['json', '> 0'] if ENV["VERSION"]
12
- end
13
- spec = h.spec
14
- spec.dependencies.delete_if { |dep| dep.name == "hoe" }
15
- def spec.to_ruby
16
- additional_src = %{
17
- if defined?(JRUBY_VERSION)
18
- s.add_dependency('json_pure', '> 0')
19
- else
20
- s.add_dependency('json', '> 0')
21
- end
22
- }
23
- super.sub(/end\n\Z/m, "#{additional_src}\nend\n")
24
- end
25
-
26
- task :gemspec do
27
- File.open("jsonpretty.gemspec", "w") {|f| f << spec.to_ruby }
28
- end
File without changes
data/go.mod ADDED
@@ -0,0 +1,3 @@
1
+ module github.com/nicksieger/jsonpretty
2
+
3
+ go 1.17
@@ -0,0 +1,28 @@
1
+
2
+ lib = File.expand_path("../lib", __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require "jsonpretty/version"
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "jsonpretty"
8
+ spec.version = Jsonpretty::VERSION
9
+ spec.authors = ["Nick Sieger"]
10
+ spec.email = ["nick@nicksieger.com"]
11
+
12
+ spec.summary = %q{Command-line JSON pretty-printer, using the json gem.}
13
+ spec.description = %q{Command-line JSON pretty-printer, using the json gem.}
14
+ spec.homepage = %q{http://github.com/nicksieger/jsonpretty}
15
+ spec.license = "MIT"
16
+
17
+ # Specify which files should be added to the gem when it is released.
18
+ # The `git ls-files -z` loads the files in the RubyGem that have been added into git.
19
+ spec.files = Dir.chdir(File.expand_path('..', __FILE__)) do
20
+ `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
21
+ end
22
+ spec.bindir = "exe"
23
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
24
+ spec.require_paths = ["lib"]
25
+
26
+ spec.add_development_dependency "bundler", "~> 1.17"
27
+ spec.add_development_dependency "rake", "~> 10.0"
28
+ end
@@ -0,0 +1,3 @@
1
+ class Jsonpretty
2
+ VERSION = "1.2.0"
3
+ end
data/lib/jsonpretty.rb CHANGED
@@ -1,8 +1,6 @@
1
1
  require 'json'
2
2
 
3
3
  class Jsonpretty
4
- VERSION = '1.0.0'
5
-
6
4
  def file_value(filename)
7
5
  file = if filename == '-'
8
6
  $stdin
@@ -10,7 +8,7 @@ class Jsonpretty
10
8
  File.open(filename)
11
9
  end
12
10
  lines = file.readlines
13
- if lines.first =~ /^HTTP\/1\./ # looks like an HTTP response; we just want the body
11
+ if lines.first =~ /^HTTP\/\d/ # looks like an HTTP response; we just want the body
14
12
  index = lines.index("\r\n") || lines.index("\n")
15
13
  puts lines[0..index]
16
14
  lines[(index+1)..-1].join('')
@@ -25,6 +23,16 @@ class Jsonpretty
25
23
  file_value('-')
26
24
  end
27
25
 
26
+ def clean_jsonp(input_string)
27
+ match = input_string.match(/^(.+)\((.+)\)$/)
28
+ if match
29
+ puts "jsonp method name: #{match[1]}\n\n"
30
+ match[2]
31
+ else
32
+ input_string
33
+ end
34
+ end
35
+
28
36
  def main
29
37
  if ARGV.length == 0
30
38
  ARGV.unshift stdin_value
@@ -48,7 +56,9 @@ class Jsonpretty
48
56
  end
49
57
  end
50
58
 
51
- puts JSON.pretty_generate(JSON.parse(ARGV.join(' ')))
59
+ input = clean_jsonp(ARGV.join(' '))
60
+ json = JSON.parse(input)
61
+ puts JSON.pretty_generate(json)
52
62
  rescue => e
53
63
  $stderr.puts "jsonpretty failed: #{e.message}"
54
64
  exit 1
data/main.go ADDED
@@ -0,0 +1,199 @@
1
+ package main
2
+
3
+ import (
4
+ "bytes"
5
+ "encoding/json"
6
+ "fmt"
7
+ "io"
8
+ "os"
9
+ "regexp"
10
+ "strings"
11
+ )
12
+
13
+ var (
14
+ version = "dev"
15
+ commit = ""
16
+ date = ""
17
+ builtBy = ""
18
+ )
19
+
20
+ type JsonArg struct {
21
+ file *os.File
22
+ content []byte
23
+ }
24
+
25
+ func (j JsonArg) Close() error {
26
+ if j.file != nil {
27
+ return j.file.Close()
28
+ }
29
+ return nil
30
+ }
31
+
32
+ func usage(code int) {
33
+ fmt.Printf("usage: %s [args|@filename|@- (stdin)]\n", os.Args[0])
34
+ fmt.Printf("Parse and pretty-print JSON, either from stdin or from arguments concatenated together\n")
35
+ os.Exit(code)
36
+ }
37
+
38
+ func versionInfo() string {
39
+ if commit != "" && date != "" {
40
+ return fmt.Sprintf("%s (%s on %s)", version, commit[0:7], date[0:10])
41
+ }
42
+ return version
43
+ }
44
+
45
+ func checkFlags(arg string) {
46
+ if arg[0] == '-' && len(arg) > 1 {
47
+ code := 1
48
+ if arg == "-v" || strings.HasPrefix(arg, "--v") {
49
+ fmt.Printf("jsonpretty version %s\n", versionInfo())
50
+ os.Exit(0)
51
+ } else if arg == "-h" || strings.HasPrefix(arg, "--h") {
52
+ code = 0
53
+ }
54
+ if code == 1 {
55
+ fmt.Printf("unrecognized flag %s\n", arg)
56
+ }
57
+ usage(code)
58
+ }
59
+ }
60
+
61
+ func buildJsonSource(args []JsonArg) *bytes.Buffer {
62
+ buffer := bytes.NewBuffer(nil)
63
+ for _, arg := range args {
64
+ if arg.file != nil {
65
+ _, err := buffer.ReadFrom(arg.file)
66
+ if err != nil {
67
+ fmt.Fprintf(os.Stderr, "error reading file: %v\n", err)
68
+ }
69
+ } else {
70
+ _, err := buffer.Write(arg.content)
71
+ if err != nil {
72
+ fmt.Fprintf(os.Stderr, "error appending content: %v\n", err)
73
+ }
74
+ }
75
+ }
76
+ return buffer
77
+ }
78
+
79
+ func readArguments(args []string) *bytes.Buffer {
80
+ jsonArgs := []JsonArg{}
81
+ defer func() {
82
+ for _, j := range jsonArgs {
83
+ _ = j.Close()
84
+ }
85
+ }()
86
+ for _, arg := range args {
87
+ checkFlags(arg)
88
+
89
+ if arg == "-" || arg == "@-" {
90
+ jsonArgs = append(jsonArgs, JsonArg{file: os.Stdin})
91
+ } else if strings.HasPrefix(arg, "@") {
92
+ file, err := os.Open(arg[1:])
93
+ if err != nil {
94
+ fmt.Fprintf(os.Stderr, "skipping '%s' due to error: %v\n", arg, err)
95
+ continue
96
+ }
97
+ jsonArgs = append(jsonArgs, JsonArg{file: file})
98
+ } else {
99
+ jsonArgs = append(jsonArgs, JsonArg{content: []byte(arg)})
100
+ }
101
+ }
102
+
103
+ if len(jsonArgs) == 0 {
104
+ jsonArgs = append(jsonArgs, JsonArg{file: os.Stdin})
105
+ }
106
+ return buildJsonSource(jsonArgs)
107
+ }
108
+
109
+ var httpRegex *regexp.Regexp = regexp.MustCompile("^HTTP/\\d")
110
+
111
+ func parseHeaders(src *bytes.Buffer) ([]byte, []byte, error) {
112
+ headerBuffer := bytes.NewBuffer(nil)
113
+ line, err := src.ReadBytes('\n')
114
+ if err != nil && err != io.EOF {
115
+ return nil, nil, err
116
+ }
117
+
118
+ if httpRegex.Match(line) {
119
+ for {
120
+ _, err = headerBuffer.Write(line)
121
+ if err != nil {
122
+ return nil, nil, err
123
+ }
124
+ if (len(line) == 1 && line[0] == '\n') ||
125
+ (len(line) == 2 && line[0] == '\r' && line[1] == '\n') {
126
+ break
127
+ }
128
+
129
+ line, err = src.ReadBytes('\n')
130
+
131
+ if err == io.EOF {
132
+ _, err = headerBuffer.Write(line)
133
+ if err != nil {
134
+ return nil, nil, err
135
+ }
136
+ break
137
+ }
138
+
139
+ if err != nil && err != io.EOF {
140
+ return nil, nil, err
141
+ }
142
+ }
143
+ } else {
144
+ newsrc := bytes.NewBuffer(line)
145
+ _, err = newsrc.Write(src.Bytes())
146
+ if err != nil {
147
+ return nil, nil, err
148
+ }
149
+ src = newsrc
150
+ }
151
+ return headerBuffer.Bytes(), src.Bytes(), nil
152
+ }
153
+
154
+ var jsonpRegexp *regexp.Regexp = regexp.MustCompile("^([a-zA-Z$_][^ \t\r\n(]+)\\(")
155
+ var endingParen *regexp.Regexp = regexp.MustCompile("\\)[ \t\r\n]*$")
156
+
157
+ func cleanJsonp(jsonSrc []byte) ([]byte, string) {
158
+ match := jsonpRegexp.FindSubmatch(jsonSrc)
159
+ ending := endingParen.FindSubmatch(jsonSrc)
160
+ if match != nil && ending != nil {
161
+ return jsonSrc[len(match[0]) : len(jsonSrc)-len(ending[0])], string(match[1])
162
+ }
163
+ return jsonSrc, ""
164
+ }
165
+
166
+ func handleParseError(err error, jsonSrc []byte) {
167
+ if err != nil {
168
+ fmt.Fprintf(os.Stderr, "error parsing json: %v\ninput:\n%s\n", err, string(jsonSrc))
169
+ os.Exit(1)
170
+ }
171
+ }
172
+
173
+ func main() {
174
+ buffer := readArguments(os.Args[1:])
175
+ headers, jsonSrc, err := parseHeaders(buffer)
176
+ handleParseError(err, jsonSrc)
177
+
178
+ jsonSrc, jsonpName := cleanJsonp(jsonSrc)
179
+
180
+ if len(headers) > 0 {
181
+ fmt.Print(string(headers))
182
+ }
183
+
184
+ if jsonpName != "" {
185
+ fmt.Printf("jsonp method name: %s\n\n", jsonpName)
186
+ }
187
+
188
+ var jsonObj interface{}
189
+ err = json.Unmarshal(jsonSrc, &jsonObj)
190
+ handleParseError(err, jsonSrc)
191
+
192
+ enc := json.NewEncoder(os.Stdout)
193
+ enc.SetIndent("", " ")
194
+ err = enc.Encode(&jsonObj)
195
+ if err != nil {
196
+ fmt.Fprintf(os.Stderr, "error encoding json: %v\n", err)
197
+ os.Exit(1)
198
+ }
199
+ }
data/main_test.go ADDED
@@ -0,0 +1,180 @@
1
+ package main
2
+
3
+ import (
4
+ "bytes"
5
+ "fmt"
6
+ "os"
7
+ "testing"
8
+ )
9
+
10
+ type Testfile struct {
11
+ name string
12
+ content string
13
+ file *os.File
14
+ }
15
+
16
+ var stdinSaved *os.File = os.Stdin
17
+
18
+ func Setup(contents []string, t *testing.T) []Testfile {
19
+ var err error
20
+ os.Stdin, err = os.CreateTemp("", "stdin")
21
+ if err != nil {
22
+ t.FailNow()
23
+ }
24
+
25
+ testfiles := make([]Testfile, len(contents))
26
+ for i, c := range contents {
27
+ testfiles[i] = Testfile{content: c}
28
+ file, err := os.CreateTemp("", fmt.Sprintf("tf%d", i))
29
+ if err != nil {
30
+ t.Logf("unable to create tempfile for '%s'", c)
31
+ t.FailNow()
32
+ }
33
+ _, err = file.Write([]byte(c))
34
+ if err != nil {
35
+ t.Logf("unable to write tempfile with '%s'", c)
36
+ t.FailNow()
37
+ }
38
+ err = file.Close()
39
+ if err != nil {
40
+ t.Logf("unable to close tempfile for '%s'", c)
41
+ t.FailNow()
42
+ }
43
+ testfiles[i].file = file
44
+ testfiles[i].name = file.Name()
45
+ }
46
+ return testfiles
47
+ }
48
+
49
+ func TearDown(testfiles []Testfile) {
50
+ for _, tf := range testfiles {
51
+ _ = os.Remove(tf.name)
52
+ }
53
+ _ = os.Stdin.Close()
54
+ os.Stdin = stdinSaved
55
+ }
56
+
57
+ func assertEqual(expect []byte, actual []byte, t *testing.T) {
58
+ if bytes.Compare(expect, actual) != 0 {
59
+ t.Errorf("bytes did not match:\n. expected:\n %s\n actual:\n %s\n",
60
+ string(expect), string(actual))
61
+ }
62
+ }
63
+
64
+ func TestReadArguments(t *testing.T) {
65
+ files := Setup([]string{"1", "2", "{\"foo\": true, \"bar\": false}"}, t)
66
+ defer TearDown(files)
67
+
68
+ tests := [][]Testfile{
69
+ {}, // nothing
70
+ {Testfile{content: "{\"hello\":\"world\"}"}},
71
+ {Testfile{content: "["}, files[0], Testfile{content: ","}, files[1], Testfile{content: "]"}},
72
+ {files[2]},
73
+ }
74
+
75
+ for i, test := range tests {
76
+ t.Run(fmt.Sprintf("test%d", i), func(t *testing.T) {
77
+ expected := bytes.NewBuffer(nil)
78
+ args := make([]string, len(test))
79
+ for j, testfile := range test {
80
+ if testfile.name != "" {
81
+ args[j] = fmt.Sprintf("@%s", testfile.name)
82
+ } else {
83
+ args[j] = testfile.content
84
+ }
85
+ expected.WriteString(testfile.content)
86
+ }
87
+ expect := expected.Bytes()
88
+ actual := readArguments(args)
89
+ assertEqual(expect, actual.Bytes(), t)
90
+ })
91
+ }
92
+ }
93
+
94
+ func TestReadArgumentsStdin(t *testing.T) {
95
+ f := Setup([]string{}, t)
96
+ defer TearDown(f)
97
+
98
+ expect := []byte("{\"foo\": true, \"bar\": false}")
99
+ _, err := os.Stdin.Write(expect)
100
+ if err != nil {
101
+ t.Logf("unable to write to stdin\n")
102
+ t.FailNow()
103
+ }
104
+ _ = os.Stdin.Close()
105
+
106
+ reopen := func(t *testing.T) {
107
+ f, err := os.Open(os.Stdin.Name())
108
+ if err != nil {
109
+ t.Logf("unable to reopen stdin")
110
+ t.FailNow()
111
+ }
112
+ os.Stdin = f
113
+ }
114
+
115
+ t.Run("no args", func(t *testing.T) {
116
+ reopen(t)
117
+ actual := readArguments([]string{})
118
+ assertEqual(expect, actual.Bytes(), t)
119
+ })
120
+
121
+ t.Run("-", func(t *testing.T) {
122
+ reopen(t)
123
+ actual := readArguments([]string{"-"})
124
+ assertEqual(expect, actual.Bytes(), t)
125
+ })
126
+
127
+ t.Run("@-", func(t *testing.T) {
128
+ reopen(t)
129
+ actual := readArguments([]string{"@-"})
130
+ assertEqual(expect, actual.Bytes(), t)
131
+ })
132
+ }
133
+
134
+ func TestParseHeaders(t *testing.T) {
135
+ tests := [][]string{
136
+ {"", "", ""},
137
+ {"{}", "", "{}"},
138
+ {"not http\n\nhello\nworld", "", "not http\n\nhello\nworld"},
139
+ {"HTTP/1.1 200 OK\nContent-Type: application/json\nContent-Length: 19\n\n{\"hello\":\"world\"}\n",
140
+ "HTTP/1.1 200 OK\nContent-Type: application/json\nContent-Length: 19\n\n",
141
+ "{\"hello\":\"world\"}\n"},
142
+ {"HTTP/1.1 200 OK\nContent-Type: application/json\nContent-Length: 0\n\n",
143
+ "HTTP/1.1 200 OK\nContent-Type: application/json\nContent-Length: 0\n\n",
144
+ ""},
145
+ {"myfunc(1,2,3)", "", "myfunc(1,2,3)"},
146
+ }
147
+
148
+ for i, test := range tests {
149
+ t.Run(fmt.Sprintf("test%d", i), func(t *testing.T) {
150
+ buffer := bytes.NewBuffer(nil)
151
+ buffer.WriteString(test[0])
152
+ headers, jsonsrc, err := parseHeaders(buffer)
153
+ if err != nil {
154
+ t.Logf("error parseHeaders: %v", err)
155
+ t.FailNow()
156
+ }
157
+ assertEqual([]byte(test[1]), headers, t)
158
+ assertEqual([]byte(test[2]), jsonsrc, t)
159
+ })
160
+ }
161
+ }
162
+
163
+ func TestCleanJsonp(t *testing.T) {
164
+ tests := [][]string{
165
+ {"jsonp(true)", "true", "jsonp"},
166
+ {"true", "true", ""},
167
+ {"myJSFunc({\"hello\":\"world\"})", "{\"hello\":\"world\"}", "myJSFunc"},
168
+ {"[1,2,3]", "[1,2,3]", ""},
169
+ {"myfunc(1,2,3)", "1,2,3", "myfunc"},
170
+ {"myfunc(1,2,3)\n", "1,2,3", "myfunc"},
171
+ }
172
+
173
+ for i, test := range tests {
174
+ t.Run(fmt.Sprintf("test%d", i), func(t *testing.T) {
175
+ jsonSrc, jsonpName := cleanJsonp([]byte(test[0]))
176
+ assertEqual([]byte(test[1]), jsonSrc, t)
177
+ assertEqual([]byte(test[2]), []byte(jsonpName), t)
178
+ })
179
+ }
180
+ }
metadata CHANGED
@@ -1,71 +1,88 @@
1
- --- !ruby/object:Gem::Specification
1
+ --- !ruby/object:Gem::Specification
2
2
  name: jsonpretty
3
- version: !ruby/object:Gem::Version
4
- version: 1.0.0
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.2.0
5
5
  platform: ruby
6
- authors:
6
+ authors:
7
7
  - Nick Sieger
8
8
  autorequire:
9
- bindir: bin
9
+ bindir: exe
10
10
  cert_chain: []
11
-
12
- date: 2009-02-20 00:00:00 -06:00
13
- default_executable:
14
- dependencies:
15
- - !ruby/object:Gem::Dependency
16
- name: json
17
- type: :runtime
18
- version_requirement:
19
- version_requirements: !ruby/object:Gem::Requirement
20
- requirements:
21
- - - ">"
22
- - !ruby/object:Gem::Version
23
- version: "0"
24
- version:
11
+ date: 2021-12-30 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: bundler
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '1.17'
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '1.17'
27
+ - !ruby/object:Gem::Dependency
28
+ name: rake
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '10.0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '10.0'
25
41
  description: Command-line JSON pretty-printer, using the json gem.
26
- email:
42
+ email:
27
43
  - nick@nicksieger.com
28
- executables:
44
+ executables:
29
45
  - jsonpretty
30
46
  extensions: []
31
-
32
- extra_rdoc_files:
47
+ extra_rdoc_files: []
48
+ files:
49
+ - ".gitignore"
50
+ - ".goreleaser.yaml"
51
+ - CODE_OF_CONDUCT.md
52
+ - Gemfile
33
53
  - History.txt
54
+ - LICENSE.txt
34
55
  - Manifest.txt
35
- - README.txt
36
- files:
37
- - History.txt
38
- - Manifest.txt
39
- - README.txt
56
+ - README.md
40
57
  - Rakefile
41
- - bin/jsonpretty
58
+ - exe/jsonpretty
59
+ - go.mod
60
+ - jsonpretty.gemspec
42
61
  - lib/jsonpretty.rb
43
- has_rdoc: true
62
+ - lib/jsonpretty/version.rb
63
+ - main.go
64
+ - main_test.go
44
65
  homepage: http://github.com/nicksieger/jsonpretty
66
+ licenses:
67
+ - MIT
68
+ metadata: {}
45
69
  post_install_message:
46
- rdoc_options:
47
- - --main
48
- - README.txt
49
- require_paths:
70
+ rdoc_options: []
71
+ require_paths:
50
72
  - lib
51
- required_ruby_version: !ruby/object:Gem::Requirement
52
- requirements:
73
+ required_ruby_version: !ruby/object:Gem::Requirement
74
+ requirements:
53
75
  - - ">="
54
- - !ruby/object:Gem::Version
55
- version: "0"
56
- version:
57
- required_rubygems_version: !ruby/object:Gem::Requirement
58
- requirements:
76
+ - !ruby/object:Gem::Version
77
+ version: '0'
78
+ required_rubygems_version: !ruby/object:Gem::Requirement
79
+ requirements:
59
80
  - - ">="
60
- - !ruby/object:Gem::Version
61
- version: "0"
62
- version:
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
63
83
  requirements: []
64
-
65
- rubyforge_project: caldersphere
66
- rubygems_version: 1.3.1
84
+ rubygems_version: 3.0.3.1
67
85
  signing_key:
68
- specification_version: 2
86
+ specification_version: 4
69
87
  summary: Command-line JSON pretty-printer, using the json gem.
70
88
  test_files: []
71
-
data/README.txt DELETED
@@ -1,54 +0,0 @@
1
- = jsonpretty
2
-
3
- * http://github.com/nicksieger/jsonpretty
4
-
5
- == DESCRIPTION:
6
-
7
- Command-line JSON pretty-printer, using the json gem.
8
-
9
- == FEATURES/PROBLEMS:
10
-
11
- - Parse and pretty-print JSON either from stdin or from command-line
12
- arguments.
13
- - All arguments are concatenated together in a single string for
14
- pretty-printing.
15
- - Use '@filename' as an argument to include the contents of the file.
16
- - Use '-' or '@-' as an argument (or use no arguments) to read stdin.
17
- - Detects HTTP response/headers, prints them untouched, and skips to
18
- the body (for use with `curl -i').
19
-
20
- == SYNOPSIS:
21
-
22
-
23
- == REQUIREMENTS:
24
-
25
- json or json_pure
26
-
27
- == INSTALL:
28
-
29
- gem install jsonpretty
30
-
31
- == LICENSE:
32
-
33
- (The MIT License)
34
-
35
- Copyright (c) 2007-2009 Nick Sieger <nick@nicksieger.com>
36
-
37
- Permission is hereby granted, free of charge, to any person obtaining
38
- a copy of this software and associated documentation files (the
39
- 'Software'), to deal in the Software without restriction, including
40
- without limitation the rights to use, copy, modify, merge, publish,
41
- distribute, sublicense, and/or sell copies of the Software, and to
42
- permit persons to whom the Software is furnished to do so, subject to
43
- the following conditions:
44
-
45
- The above copyright notice and this permission notice shall be
46
- included in all copies or substantial portions of the Software.
47
-
48
- THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND,
49
- EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
50
- MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
51
- IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
52
- CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
53
- TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
54
- SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.