parser

package
v1.0.2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Mar 3, 2023 License: MIT Imports: 12 Imported by: 0

Documentation

Index

Examples

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type CheckStyleError

type CheckStyleError struct {
	Column   int    `xml:"column,attr,omitempty"`
	Line     int    `xml:"line,attr"`
	Message  string `xml:"message,attr"`
	Severity string `xml:"severity,attr,omitempty"`
	Source   string `xml:"source,attr,omitempty"`
}

CheckStyleError represents <error line="1" column="10" severity="error" message="msg" source="src" />

type CheckStyleFile

type CheckStyleFile struct {
	Name   string             `xml:"name,attr"`
	Errors []*CheckStyleError `xml:"error"`
}

CheckStyleFile represents <file name="fname"><error ... />...</file>

type CheckStyleParser

type CheckStyleParser struct{}

CheckStyleParser is checkstyle parser.

Example
const sample = `<?xml version="1.0" encoding="utf-8"?><checkstyle version="4.3"><file name="/path/to/file"><error line="1" column="10" severity="error" message="&apos;addOne&apos; is defined but never used. (no-unused-vars)" source="eslint.rules.no-unused-vars" /><error line="2" column="9" severity="error" message="Use the isNaN function to compare with NaN. (use-isnan)" source="eslint.rules.use-isnan" /><error line="3" column="16" severity="error" message="Unexpected space before unary operator &apos;++&apos;. (space-unary-ops)" source="eslint.rules.space-unary-ops" /><error line="3" column="20" severity="warning" message="Missing semicolon. (semi)" source="eslint.rules.semi" /><error line="4" column="12" severity="warning" message="Unnecessary &apos;else&apos; after &apos;return&apos;. (no-else-return)" source="eslint.rules.no-else-return" /><error line="5" column="7" severity="warning" message="Expected indentation of 8 spaces but found 6. (indent)" source="eslint.rules.indent" /><error line="5" column="7" severity="error" message="Expected a return value. (consistent-return)" source="eslint.rules.consistent-return" /><error line="5" column="13" severity="warning" message="Missing semicolon. (semi)" source="eslint.rules.semi" /><error line="7" column="2" severity="error" message="Unnecessary semicolon. (no-extra-semi)" source="eslint.rules.no-extra-semi" /></file></checkstyle>`

p := NewCheckStyleParser()
diagnostics, err := p.Parse(strings.NewReader(sample))
if err != nil {
	panic(err)
}
for _, d := range diagnostics {
	rdjson, _ := protojson.MarshalOptions{Indent: "  "}.Marshal(d)
	var out bytes.Buffer
	json.Indent(&out, rdjson, "", "  ")
	fmt.Println(out.String())
}
Output:

{
  "message": "'addOne' is defined but never used. (no-unused-vars)",
  "location": {
    "path": "/path/to/file",
    "range": {
      "start": {
        "line": 1,
        "column": 10
      }
    }
  },
  "severity": "ERROR",
  "code": {
    "value": "eslint.rules.no-unused-vars"
  },
  "originalOutput": "/path/to/file:1:10: error: 'addOne' is defined but never used. (no-unused-vars) (eslint.rules.no-unused-vars)"
}
{
  "message": "Use the isNaN function to compare with NaN. (use-isnan)",
  "location": {
    "path": "/path/to/file",
    "range": {
      "start": {
        "line": 2,
        "column": 9
      }
    }
  },
  "severity": "ERROR",
  "code": {
    "value": "eslint.rules.use-isnan"
  },
  "originalOutput": "/path/to/file:2:9: error: Use the isNaN function to compare with NaN. (use-isnan) (eslint.rules.use-isnan)"
}
{
  "message": "Unexpected space before unary operator '++'. (space-unary-ops)",
  "location": {
    "path": "/path/to/file",
    "range": {
      "start": {
        "line": 3,
        "column": 16
      }
    }
  },
  "severity": "ERROR",
  "code": {
    "value": "eslint.rules.space-unary-ops"
  },
  "originalOutput": "/path/to/file:3:16: error: Unexpected space before unary operator '++'. (space-unary-ops) (eslint.rules.space-unary-ops)"
}
{
  "message": "Missing semicolon. (semi)",
  "location": {
    "path": "/path/to/file",
    "range": {
      "start": {
        "line": 3,
        "column": 20
      }
    }
  },
  "severity": "WARNING",
  "code": {
    "value": "eslint.rules.semi"
  },
  "originalOutput": "/path/to/file:3:20: warning: Missing semicolon. (semi) (eslint.rules.semi)"
}
{
  "message": "Unnecessary 'else' after 'return'. (no-else-return)",
  "location": {
    "path": "/path/to/file",
    "range": {
      "start": {
        "line": 4,
        "column": 12
      }
    }
  },
  "severity": "WARNING",
  "code": {
    "value": "eslint.rules.no-else-return"
  },
  "originalOutput": "/path/to/file:4:12: warning: Unnecessary 'else' after 'return'. (no-else-return) (eslint.rules.no-else-return)"
}
{
  "message": "Expected indentation of 8 spaces but found 6. (indent)",
  "location": {
    "path": "/path/to/file",
    "range": {
      "start": {
        "line": 5,
        "column": 7
      }
    }
  },
  "severity": "WARNING",
  "code": {
    "value": "eslint.rules.indent"
  },
  "originalOutput": "/path/to/file:5:7: warning: Expected indentation of 8 spaces but found 6. (indent) (eslint.rules.indent)"
}
{
  "message": "Expected a return value. (consistent-return)",
  "location": {
    "path": "/path/to/file",
    "range": {
      "start": {
        "line": 5,
        "column": 7
      }
    }
  },
  "severity": "ERROR",
  "code": {
    "value": "eslint.rules.consistent-return"
  },
  "originalOutput": "/path/to/file:5:7: error: Expected a return value. (consistent-return) (eslint.rules.consistent-return)"
}
{
  "message": "Missing semicolon. (semi)",
  "location": {
    "path": "/path/to/file",
    "range": {
      "start": {
        "line": 5,
        "column": 13
      }
    }
  },
  "severity": "WARNING",
  "code": {
    "value": "eslint.rules.semi"
  },
  "originalOutput": "/path/to/file:5:13: warning: Missing semicolon. (semi) (eslint.rules.semi)"
}
{
  "message": "Unnecessary semicolon. (no-extra-semi)",
  "location": {
    "path": "/path/to/file",
    "range": {
      "start": {
        "line": 7,
        "column": 2
      }
    }
  },
  "severity": "ERROR",
  "code": {
    "value": "eslint.rules.no-extra-semi"
  },
  "originalOutput": "/path/to/file:7:2: error: Unnecessary semicolon. (no-extra-semi) (eslint.rules.no-extra-semi)"
}

func (*CheckStyleParser) Parse

func (p *CheckStyleParser) Parse(r io.Reader) ([]*rdf.Diagnostic, error)

type CheckStyleResult

type CheckStyleResult struct {
	XMLName xml.Name          `xml:"checkstyle"`
	Version string            `xml:"version,attr"`
	Files   []*CheckStyleFile `xml:"file,omitempty"`
}

CheckStyleResult represents checkstyle XML result. <?xml version="1.0" encoding="utf-8"?><checkstyle version="4.3"><file ...></file>...</checkstyle>

References:

type DiffParser

type DiffParser struct {
	// contains filtered or unexported fields
}

DiffParser is a unified diff parser.

Example
const sample = `diff --git a/gofmt.go b/gofmt.go
--- a/gofmt.go	2020-07-26 08:01:09.260800318 +0000
+++ b/gofmt.go	2020-07-26 08:01:09.260800318 +0000
@@ -1,6 +1,6 @@
 package testdata
 
-func    fmt     () {
+func fmt() {
 	// test
 	// test line
 	// test line
@@ -10,11 +10,11 @@
 	// test line
 	// test line
 
-println(
-		"hello, gofmt test"    )
-//comment
+	println(
+		"hello, gofmt test")
+	//comment
 }
 
+type s struct{ A int }
 
-type s struct { A int }
 func (s s) String() { return "s" }
`
const strip = 1
p := NewDiffParser(strip)
diagnostics, err := p.Parse(strings.NewReader(sample))
if err != nil {
	panic(err)
}
for _, d := range diagnostics {
	rdjson, _ := protojson.MarshalOptions{Indent: "  "}.Marshal(d)
	var out bytes.Buffer
	json.Indent(&out, rdjson, "", "  ")
	fmt.Println(out.String())
}
Output:

{
  "location": {
    "path": "gofmt.go",
    "range": {
      "start": {
        "line": 3
      },
      "end": {
        "line": 3
      }
    }
  },
  "suggestions": [
    {
      "range": {
        "start": {
          "line": 3
        },
        "end": {
          "line": 3
        }
      },
      "text": "func fmt() {"
    }
  ],
  "originalOutput": "gofmt.go:3:-func    fmt     () {\ngofmt.go:3:+func fmt() {"
}
{
  "location": {
    "path": "gofmt.go",
    "range": {
      "start": {
        "line": 13
      },
      "end": {
        "line": 15
      }
    }
  },
  "suggestions": [
    {
      "range": {
        "start": {
          "line": 13
        },
        "end": {
          "line": 15
        }
      },
      "text": "\tprintln(\n\t\t\"hello, gofmt test\")\n\t//comment"
    }
  ],
  "originalOutput": "gofmt.go:13:-println(\ngofmt.go:14:-\t\t\"hello, gofmt test\"    )\ngofmt.go:15:-//comment\ngofmt.go:13:+\tprintln(\ngofmt.go:14:+\t\t\"hello, gofmt test\")\ngofmt.go:15:+\t//comment"
}
{
  "location": {
    "path": "gofmt.go",
    "range": {
      "start": {
        "line": 18,
        "column": 1
      },
      "end": {
        "line": 18,
        "column": 1
      }
    }
  },
  "suggestions": [
    {
      "range": {
        "start": {
          "line": 18,
          "column": 1
        },
        "end": {
          "line": 18,
          "column": 1
        }
      },
      "text": "type s struct{ A int }\n"
    }
  ],
  "originalOutput": "gofmt.go:18:+type s struct{ A int }"
}
{
  "location": {
    "path": "gofmt.go",
    "range": {
      "start": {
        "line": 19
      },
      "end": {
        "line": 19
      }
    }
  },
  "suggestions": [
    {
      "range": {
        "start": {
          "line": 19
        },
        "end": {
          "line": 19
        }
      }
    }
  ],
  "originalOutput": "gofmt.go:19:-type s struct { A int }"
}

func NewDiffParser

func NewDiffParser(strip int) *DiffParser

NewDiffParser creates a new DiffParser.

func (*DiffParser) Parse

func (p *DiffParser) Parse(r io.Reader) ([]*rdf.Diagnostic, error)

Parse parses input as unified diff format and return it as diagnostics.

type ErrorformatParser

type ErrorformatParser struct {
	// contains filtered or unexported fields
}

ErrorformatParser is errorformat parser.

Example
const sample = `/path/to/file1.txt:1:14: [E][RULE:14] message 1
/path/to/file2.txt:2:14: [N][RULE:7] message 2`

p, err := NewErrorformatParserString([]string{`%f:%l:%c: [%t][RULE:%n] %m`})
if err != nil {
	panic(err)
}
diagnostics, err := p.Parse(strings.NewReader(sample))
if err != nil {
	panic(err)
}
for _, d := range diagnostics {
	rdjson, _ := protojson.MarshalOptions{Indent: "  "}.Marshal(d)
	var out bytes.Buffer
	json.Indent(&out, rdjson, "", "  ")
	fmt.Println(out.String())
}
Output:

{
  "message": "message 1",
  "location": {
    "path": "/path/to/file1.txt",
    "range": {
      "start": {
        "line": 1,
        "column": 14
      }
    }
  },
  "severity": "ERROR",
  "code": {
    "value": "14"
  },
  "originalOutput": "/path/to/file1.txt:1:14: [E][RULE:14] message 1"
}
{
  "message": "message 2",
  "location": {
    "path": "/path/to/file2.txt",
    "range": {
      "start": {
        "line": 2,
        "column": 14
      }
    }
  },
  "severity": "INFO",
  "code": {
    "value": "7"
  },
  "originalOutput": "/path/to/file2.txt:2:14: [N][RULE:7] message 2"
}

func NewErrorformatParser

func NewErrorformatParser(efm *errorformat.Errorformat) *ErrorformatParser

NewErrorformatParser returns a new ErrorformatParser.

func NewErrorformatParserString

func NewErrorformatParserString(efms []string) (*ErrorformatParser, error)

NewErrorformatParserString returns a new ErrorformatParser from errorformat in string representation.

func (*ErrorformatParser) Parse

func (p *ErrorformatParser) Parse(r io.Reader) ([]*rdf.Diagnostic, error)

type Option

type Option struct {
	FormatName  string
	Errorformat []string
	DiffStrip   int
}

Option represents option to create Parser. Either FormatName or Errorformat should be specified.

type Parser

type Parser interface {
	Parse(r io.Reader) ([]*rdf.Diagnostic, error)
}

Parser is an interface which parses compilers, linters, or any tools results.

func New

func New(opt *Option) (Parser, error)

New returns Parser based on Option.

func NewCheckStyleParser

func NewCheckStyleParser() Parser

NewCheckStyleParser returns a new CheckStyleParser.

type RDJSONLParser

type RDJSONLParser struct{}

RDJSONLParser is parser for rdjsonl format.

func NewRDJSONLParser

func NewRDJSONLParser() *RDJSONLParser

NewRDJSONLParser returns a new RDJSONParser.

func (*RDJSONLParser) Parse

func (p *RDJSONLParser) Parse(r io.Reader) ([]*rdf.Diagnostic, error)

Parse parses rdjson (JSONL of Diagnostic).

type RDJSONParser

type RDJSONParser struct{}

RDJSONParser is parser for rdjsonl format.

Example
const sample = `
{
  "source": {
    "name": "linter-name",
    "url": "https://github.com/reviewdog#linter-name"
  },
  "severity": "INFO",
  "diagnostics": [
    {
      "source": {
        "name": "deadcode"
      },
      "message": "'unused' is unused",
      "location": {
        "path": "testdata/main.go",
        "range": {
          "start": {
            "line": 18,
            "column": 6
          }
        }
      }
    },
    {
      "message": "printf: Sprintf format %d reads arg #1, but call has 0 args",
      "location": {
        "path": "testdata/main.go",
        "range": {
          "start": {
            "line": 13,
            "column": 2
          }
        }
      }
    },
    {
      "source": {
        "name": "severity-test"
      },
      "message": "severity test (string)",
      "location": {
        "path": "testdata/main.go",
        "range": {
          "start": {
            "line": 24,
            "column": 6
          }
        }
      },
      "severity": "WARNING"
    },
    {
      "source": {
        "name": "severity-test"
      },
      "message": "severity test (number)",
      "location": {
        "path": "testdata/main.go",
        "range": {
          "start": {
            "line": 24,
            "column": 6
          }
        }
      },
      "severity": 1
    }
  ]
}`
p := NewRDJSONParser()
diagnostics, err := p.Parse(strings.NewReader(sample))
if err != nil {
	panic(err)
}
for _, d := range diagnostics {
	d.OriginalOutput = "" // Skip for testing as it's not deterministic.
	rdjson, _ := protojson.MarshalOptions{Indent: "  "}.Marshal(d)
	var out bytes.Buffer
	json.Indent(&out, rdjson, "", "  ")
	fmt.Println(out.String())
}
Output:

{
  "message": "'unused' is unused",
  "location": {
    "path": "testdata/main.go",
    "range": {
      "start": {
        "line": 18,
        "column": 6
      }
    }
  },
  "severity": "INFO",
  "source": {
    "name": "deadcode"
  }
}
{
  "message": "printf: Sprintf format %d reads arg #1, but call has 0 args",
  "location": {
    "path": "testdata/main.go",
    "range": {
      "start": {
        "line": 13,
        "column": 2
      }
    }
  },
  "severity": "INFO",
  "source": {
    "name": "linter-name",
    "url": "https://github.com/reviewdog#linter-name"
  }
}
{
  "message": "severity test (string)",
  "location": {
    "path": "testdata/main.go",
    "range": {
      "start": {
        "line": 24,
        "column": 6
      }
    }
  },
  "severity": "WARNING",
  "source": {
    "name": "severity-test"
  }
}
{
  "message": "severity test (number)",
  "location": {
    "path": "testdata/main.go",
    "range": {
      "start": {
        "line": 24,
        "column": 6
      }
    }
  },
  "severity": "ERROR",
  "source": {
    "name": "severity-test"
  }
}

func NewRDJSONParser

func NewRDJSONParser() *RDJSONParser

NewRDJSONParser returns a new RDJSONParser.

func (*RDJSONParser) Parse

func (p *RDJSONParser) Parse(r io.Reader) ([]*rdf.Diagnostic, error)

Parse parses rdjson (JSON of DiagnosticResult).

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL