Skip to content

Instantly share code, notes, and snippets.

@bluerabbit
Last active October 26, 2022 01:05
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save bluerabbit/085feb474622575abf1c5dd8aae2d54e to your computer and use it in GitHub Desktop.
Save bluerabbit/085feb474622575abf1c5dd8aae2d54e to your computer and use it in GitHub Desktop.
CircleCIにてrspecでテストが落ちてたらGitHubのPull RequestのDescriptionに落ちたテストファイルを列挙する
require "octokit"
require "json"
class GithubPullRequest
def initialize(access_token: ENV["GITHUB_TOKEN"], repository:)
@client = Octokit::Client.new(access_token: access_token)
@repository = repository
end
def update_description!(rspec_examples:, pull_request_number:, ci_build_url:)
errors = rspec_examples.select { |e| e["status"] == "failed" }.map { |e| "#{e["file_path"]}:#{e["line_number"]}" }
time = Time.now.strftime("%Y/%m/%d %H:%M")
header = "[:cry: #{time}](#{ci_build_url}) #{rspec_examples.size} tests with #{errors.size} failures"
fail_message = errors.map { |v| "- [ ] `#{v}`" }.join("\n")
if errors.size > 5
fail_message = "<details><summary>#{errors.size} failures</summary>\n\n#{fail_message}\n\n</details>"
end
body = "#{fetch_body(pull_request_number)}\n## #{header}\n\n#{fail_message}\n"
@client.update_pull_request(@repository, pull_request_number, {body: body})
end
private
def fetch_body(pull_request_number)
@client.pull_request(@repository, pull_request_number)[:body]
end
end
unless ENV["CI_PULL_REQUEST"].nil?
rspec_result_json_file_path = ENV["RSPEC_JSON_PATH"]
if File.exist?(rspec_result_json_file_path)
github_pr = GithubPullRequest.new(repository: "#{ENV["CIRCLE_PROJECT_USERNAME"]}/#{ENV["CIRCLE_PROJECT_REPONAME"]}")
github_pr.update_description!(rspec_examples: JSON.parse(File.read(rspec_result_json_file_path))["examples"],
pull_request_number: ENV["CI_PULL_REQUEST"].split("/").last.to_i,
ci_build_url: ENV["CIRCLE_BUILD_URL"])
end
end
@bluerabbit
Copy link
Author

bluerabbit commented Mar 1, 2019

.circleci/config.yml

- run: bundle exec rspec --format json --out /tmp/rspec.json
- run:
    name: Update GitHub Pull Request Description
    when: on_fail
    environment:
      RSPEC_JSON_PATH: /tmp/rspec.json
      TZ: Asia/Tokyo
    command: |
      gem install octokit
      curl https://gist.githubusercontent.com/bluerabbit/085feb474622575abf1c5dd8aae2d54e/raw/9d6cff7c6c59573e3c6ccb721029343adcb84619/github_pull_request.rb -o github_pull_request.rb
      ruby github_pull_request.rb
- run:
    name: Create CircleCI Test Summary
    when: always
    command: |
      gem install circleci-test_report
      circleci-test_report -f /tmp/rspec.json -o /tmp/test-results/rspec.xml
- store_test_results:
    path: /tmp/test-results
  • CircleCIの環境変数設定でGITHUB_ACCESS_TOKENが必要
  • rspecのjsonフォーマットのファイルを使って処理をするため rspec --format json --out /tmp/rspec.json が必要
  • jsonではCircleCIのテストレポートが出せないためjsonファイルをcircleci-test_reportでjunit formatに変換する

テストが落ちたらPull Requestに箇条書きで落ちたファイルが並ぶ

ss 2019-03-01 22 58 36

@bluerabbit
Copy link
Author

personal-access-tokenで必要な権限

image

Octokitで確認

oct = Octokit::Client.new(access_token: 'your_pat_here')
repo = "user/repo"
pr_number = 1
oct.update_pull_request(repo, pr_number, {body: "test"})
oct.pull_request(repo, pr_number)[:body] # test

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment