From f412d3cc8311a4e94bf648b6b2f0d2f48678e143 Mon Sep 17 00:00:00 2001 From: Andrew Mason Date: Mon, 2 Sep 2019 21:28:34 -0400 Subject: [PATCH] initial commit --- .gitignore | 2 + Dockerfile | 11 ++++ LICENSE | 21 ++++++++ README.md | 3 ++ lib/action.json | 8 +++ lib/entrypoint.sh | 7 +++ lib/index.rb | 134 ++++++++++++++++++++++++++++++++++++++++++++++ screenshots/.keep | 0 8 files changed, 186 insertions(+) create mode 100644 .gitignore create mode 100644 Dockerfile create mode 100644 LICENSE create mode 100644 README.md create mode 100644 lib/action.json create mode 100755 lib/entrypoint.sh create mode 100644 lib/index.rb create mode 100644 screenshots/.keep diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..b87f77d --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +/tmp/ +/.vscode/ diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..865de90 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,11 @@ +FROM ruby:2.6 + +LABEL com.github.actions.name="Rubocop Linter" +LABEL com.github.actions.description="Lint your Ruby code" +LABEL com.github.actions.icon="code" +LABEL com.github.actions.color="red" + +LABEL maintainer="Andrew Mason " + +COPY lib /action/lib +ENTRYPOINT ["/action/lib/entrypoint.sh"] diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..4467078 --- /dev/null +++ b/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2019 Andrew Mason + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/README.md b/README.md new file mode 100644 index 0000000..e661f18 --- /dev/null +++ b/README.md @@ -0,0 +1,3 @@ +# Rubocop GitHub Action + +TODO diff --git a/lib/action.json b/lib/action.json new file mode 100644 index 0000000..ed92626 --- /dev/null +++ b/lib/action.json @@ -0,0 +1,8 @@ +{ + "repository": { + "owner": { + "login": "andrewmcodes" + } + ,"name": "rubocop-linter" + } +} diff --git a/lib/entrypoint.sh b/lib/entrypoint.sh new file mode 100755 index 0000000..e272643 --- /dev/null +++ b/lib/entrypoint.sh @@ -0,0 +1,7 @@ +#!/bin/sh + +set -e + +gem install rubocop rubocop-performance rubocop-rails + +ruby /action/lib/index.rb diff --git a/lib/index.rb b/lib/index.rb new file mode 100644 index 0000000..a9e1c91 --- /dev/null +++ b/lib/index.rb @@ -0,0 +1,134 @@ +require 'net/http' +require 'json' +require 'time' + +@GITHUB_SHA = ENV["GITHUB_SHA"] +@GITHUB_EVENT_PATH = ENV["GITHUB_EVENT_PATH"] +@GITHUB_TOKEN = ENV["GITHUB_TOKEN"] +@GITHUB_WORKSPACE = ENV["GITHUB_WORKSPACE"] + +@event = JSON.parse(File.read(ENV["GITHUB_EVENT_PATH"])) +@repository = @event["repository"] +@owner = @repository["owner"]["login"] +@repo = @repository["name"] + +@check_name = "Rubocop" + +@headers = { + "Content-Type": 'application/json', + "Accept": 'application/vnd.github.antiope-preview+json', + "Authorization": "Bearer #{@GITHUB_TOKEN}", + "User-Agent": 'rubocop-action' +} + +def create_check + body = { + "name" => @check_name, + "head_sha" => @GITHUB_SHA, + "status" => "in_progress", + "started_at" => Time.now.iso8601 + } + + http = Net::HTTP.new('api.github.com', 443) + http.use_ssl = true + path = "/repos/#{@owner}/#{@repo}/check-runs" + + resp = http.post(path, body.to_json, @headers) + + if resp.code.to_i >= 300 + raise resp.message + end + + data = JSON.parse(resp.body) + return data["id"] +end + +def update_check(id, conclusion, output) + body = { + "name" => @check_name, + "head_sha" => @GITHUB_SHA, + "status" => 'completed', + "completed_at" => Time.now.iso8601, + "conclusion" => conclusion, + "output" => output + } + + http = Net::HTTP.new('api.github.com', 443) + http.use_ssl = true + path = "/repos/#{@owner}/#{@repo}/check-runs/#{id}" + + resp = http.patch(path, body.to_json, @headers) + + if resp.code.to_i >= 300 + raise resp.message + end +end + +@annotation_levels = { + "refactor" => 'failure', + "convention" => 'failure', + "warning" => 'warning', + "error" => 'failure', + "fatal" => 'failure' +} + +def run_rubocop + annotations = [] + errors = nil + Dir.chdir(@GITHUB_WORKSPACE) { + errors = JSON.parse(`rubocop --format json`) + } + conclusion = "success" + count = 0 + + errors["files"].each do |file| + path = file["path"] + offenses = file["offenses"] + + offenses.each do |offense| + severity = offense["severity"] + message = offense["message"] + location = offense["location"] + annotation_level = @annotation_levels[severity] + count = count + 1 + + if annotation_level == "failure" + conclusion = "failure" + end + + annotations.push({ + "path" => path, + "start_line" => location["start_line"], + "end_line" => location["start_line"], + "annotation_level": annotation_level, + "message" => message + }) + end + end + + output = { + "title": @check_name, + "summary": "#{count} offense(s) found", + "annotations" => annotations + } + + return { "output" => output, "conclusion" => conclusion } +end + +def run + id = create_check() + begin + results = run_rubocop() + conclusion = results["conclusion"] + output = results["output"] + + update_check(id, conclusion, output) + + fail if conclusion == "failure" + rescue + update_check(id, "failure", nil) + fail + end +end + +run() diff --git a/screenshots/.keep b/screenshots/.keep new file mode 100644 index 0000000..e69de29