allure-report-publisher 0.0.4 → 0.0.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: f0a1bb3d8d9d7a22c080bcb2ce71fcf4d082d49b8ffd528fb3ef409d4afbf0ef
4
- data.tar.gz: 992e16c2cb4ee7feabefd9250efb13f824804e2a30bec5c6f031666f41e8f9a9
3
+ metadata.gz: 2d7d2654f1e2f5e4afe6dd64d08bd24a9fc6764d24abfb06f2f52dc66df21d56
4
+ data.tar.gz: cce27a83826622967fc3847c53275c8b087ef2e9c1aa216da3237081e75e3772
5
5
  SHA512:
6
- metadata.gz: 9806755fe1c216f8c590e183e0b667060a92017d42991a65663ed74aa8519d8e390e2eafe6dd35d67dacd0f40df3e1c75feab23498869073fe343d2514c02767
7
- data.tar.gz: 6a04f0503833d6378c3f4923b159a2567e8b3a9fc3ee642825ec45ef921d514616a2b93c39d50204cd29573dc88723b4ef2c47f9d3c05a30942dff63f6d91433
6
+ metadata.gz: 0141ca8082a561395e97f93e9b02bbe17e2aa69bfddc2146452769e6009824e29e2e23203e2e36ad54afaacfbb91701f30527e65c6599d5b8d6707b3e7e3ffb1
7
+ data.tar.gz: 1420f1b3ec4fa386217bd4f0228bf59615772111190adcfb35f4ff68fce1de6eaa8bf39b173ec408ab4ef3c95645c00013c52d4acaca96cc4ab46efbe64bfb7e
data/README.md CHANGED
@@ -28,36 +28,44 @@ docker pull andrcuns/allure-report-publisher:latest
28
28
 
29
29
  allure-report-publisher will automatically detect if used in CI environment and add relevant executor info and history
30
30
 
31
- ### AWS S3
32
-
33
- - `AWS authentication`: requires environment variables `AWS_ACCESS_KEY_ID`, `AWS_SECRET_ACCESS_KEY` or credentials file `~/.aws/credentials`
34
31
  - `Allure report link`: requires `GITHUB_AUTH_TOKEN` or `GITLAB_AUTH_TOKEN` in order to update pull request description with link to latest report
35
32
 
36
33
  ```shell
37
- $ (allure-report-publisher|docker run --rm andrcuns/allure-report-publisher:latest) upload s3 --help
34
+ $ (allure-report-publisher|docker run --rm andrcuns/allure-report-publisher:latest) upload --help
38
35
  Command:
39
- allure-report-publisher upload s3
36
+ allure-report-publisher upload
40
37
 
41
38
  Usage:
42
- allure-report-publisher upload s3
39
+ allure-report-publisher upload TYPE
43
40
 
44
41
  Description:
45
42
  Generate and upload allure report
46
43
 
44
+ Arguments:
45
+ TYPE # REQUIRED Cloud storage type: (s3/gcs)
46
+
47
47
  Options:
48
- --[no-]color # Toggle color output, default: false
49
- --[no-]update-pr # Update pull request description with url to allure report, default: false
50
- --[no-]copy-latest # Keep copy of latest report at base prefix path, default: false
51
48
  --results-glob=VALUE # Allure results files glob. Required: true
52
49
  --bucket=VALUE # Bucket name. Required: true
53
50
  --prefix=VALUE # Optional prefix for report path. Required: false
51
+ --[no-]update-pr # Update pull request description with url to allure report, default: false
52
+ --[no-]copy-latest # Keep copy of latest report at base prefix path, default: false
53
+ --[no-]color # Toggle color output, default: false
54
54
  --help, -h # Print this help
55
55
 
56
56
  Examples:
57
57
  allure-report-publisher upload s3 --results-glob='path/to/allure-result/**/*' --bucket=my-bucket
58
- allure-report-publisher upload s3 --results-glob='path/to/allure-result/**/*' --bucket=my-bucket --project=my-project/prs
58
+ allure-report-publisher upload gcs --results-glob='path/to/allure-result/**/*' --bucket=my-bucket --prefix=my-project/prs
59
59
  ```
60
60
 
61
+ ### AWS S3
62
+
63
+ - `AWS authentication`: requires environment variables `AWS_ACCESS_KEY_ID`, `AWS_SECRET_ACCESS_KEY` or credentials file `~/.aws/credentials`
64
+
65
+ ### Google Cloud Storage
66
+
67
+ - `GCS authentication`: requires environment variable `GOOGLE_CLOUD_CREDENTIALS_JSON` with contents of credentials.json
68
+
61
69
  ## Development
62
70
 
63
71
  After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
@@ -14,11 +14,8 @@ module Publisher
14
14
  extend Dry::CLI::Registry
15
15
 
16
16
  register "version", Version, aliases: ["-v", "--version"]
17
-
18
- register "upload" do |prefix|
19
- prefix.register "s3", UploadS3
20
- end
17
+ register "upload", Upload, aliases: ["u"]
21
18
  end
22
19
  end
23
20
 
24
- Publisher::Commands.before("upload s3") { Publisher::Helpers.validate_allure_cli_present }
21
+ Publisher::Commands.before("upload") { Publisher::Helpers.validate_allure_cli_present }
@@ -0,0 +1,81 @@
1
+ module Publisher
2
+ module Commands
3
+ # Upload allure report
4
+ #
5
+ class Upload < Dry::CLI::Command
6
+ include Helpers
7
+
8
+ desc "Generate and upload allure report"
9
+
10
+ argument :type,
11
+ type: :string,
12
+ required: true,
13
+ values: %w[s3 gcs],
14
+ desc: "Cloud storage type"
15
+
16
+ option :results_glob,
17
+ desc: "Allure results files glob. Required: true"
18
+ option :bucket,
19
+ desc: "Bucket name. Required: true"
20
+ option :prefix,
21
+ desc: "Optional prefix for report path. Required: false"
22
+ option :update_pr,
23
+ type: :boolean,
24
+ default: false,
25
+ desc: "Update pull request description with url to allure report"
26
+ option :copy_latest,
27
+ type: :boolean,
28
+ default: false,
29
+ desc: "Keep copy of latest report at base prefix path"
30
+ option :color,
31
+ type: :boolean,
32
+ default: false,
33
+ desc: "Toggle color output"
34
+
35
+ example [
36
+ "s3 --results-glob='path/to/allure-result/**/*' --bucket=my-bucket",
37
+ "gcs --results-glob='path/to/allure-result/**/*' --bucket=my-bucket --prefix=my-project/prs"
38
+ ]
39
+
40
+ def call(**args)
41
+ validate_args(args)
42
+ validate_result_files(args[:results_glob])
43
+ Helpers.pastel(force_color: args[:color] || nil)
44
+
45
+ uploaders(args[:type])
46
+ .new(**args.slice(:results_glob, :bucket, :prefix, :copy_latest, :update_pr))
47
+ .execute
48
+ end
49
+
50
+ private
51
+
52
+ # Uploader class
53
+ #
54
+ # @param [String] uploader
55
+ # @return [Publisher::Uploaders::Uploader]
56
+ def uploaders(uploader)
57
+ {
58
+ "s3" => Uploaders::S3,
59
+ "gcs" => Uploaders::GCS
60
+ }[uploader]
61
+ end
62
+
63
+ # Validate required args
64
+ #
65
+ # @param [Hash] args
66
+ # @return [void]
67
+ def validate_args(args)
68
+ error("Missing argument --results-glob!") unless args[:results_glob]
69
+ error("Missing argument --bucket!") unless args[:bucket]
70
+ end
71
+
72
+ # Check if allure results present
73
+ #
74
+ # @param [String] results_glob
75
+ # @return [void]
76
+ def validate_result_files(results_glob)
77
+ Dir.glob(results_glob).empty? && error("Glob '#{results_glob}' did not match any files!")
78
+ end
79
+ end
80
+ end
81
+ end
@@ -12,7 +12,7 @@ module Publisher
12
12
 
13
13
  # Base class for CI executor info
14
14
  #
15
- class Base
15
+ class Provider
16
16
  EXECUTOR_JSON = "executor.json".freeze
17
17
  DESCRIPTION_PATTERN = /<!-- allure -->[\s\S]+<!-- allurestop -->/.freeze
18
18
 
@@ -4,7 +4,7 @@ module Publisher
4
4
  module Providers
5
5
  # Github implementation
6
6
  #
7
- class Github < Base
7
+ class Github < Provider
8
8
  # Run id
9
9
  #
10
10
  # @return [String]
@@ -4,7 +4,7 @@ module Publisher
4
4
  module Providers
5
5
  # Gitlab implementation
6
6
  #
7
- class Gitlab < Base
7
+ class Gitlab < Provider
8
8
  # Get ci run ID without creating instance of ci provider
9
9
  #
10
10
  # @return [String]
@@ -15,19 +15,17 @@ module Publisher
15
15
 
16
16
  def initialize(results_glob:, bucket:, update_pr: false, prefix: nil, copy_latest: false)
17
17
  @results_glob = results_glob
18
- @bucket = bucket
18
+ @bucket_name = bucket
19
19
  @prefix = prefix
20
20
  @update_pr = update_pr
21
- @copy_latest = Providers.provider && copy_latest # copy latest for ci only
21
+ @copy_latest = !!(Providers.provider && copy_latest) # copy latest for ci only
22
22
  end
23
23
 
24
- # :nocov:
25
-
26
24
  # Execute allure report generation and upload
27
25
  #
28
26
  # @return [void]
29
27
  def execute
30
- check_client_configured
28
+ client # initialize client and check for errors
31
29
 
32
30
  generate
33
31
  upload
@@ -38,13 +36,14 @@ module Publisher
38
36
 
39
37
  private
40
38
 
41
- attr_reader :results_glob, :bucket, :prefix, :update_pr, :copy_latest
39
+ attr_reader :results_glob, :bucket_name, :prefix, :update_pr, :copy_latest
42
40
 
43
- # Validate if client is properly configured
44
- # and raise error if it is not
41
+ # :nocov:
42
+
43
+ # Cloud provider client
45
44
  #
46
- # @return [void]
47
- def check_client_configured
45
+ # @return [Object]
46
+ def client
48
47
  raise("Not Implemented!")
49
48
  end
50
49
 
@@ -55,6 +54,13 @@ module Publisher
55
54
  raise("Not Implemented!")
56
55
  end
57
56
 
57
+ # Download allure history
58
+ #
59
+ # @return [void]
60
+ def download_history
61
+ raise("Not implemented!")
62
+ end
63
+
58
64
  # Upload history to s3
59
65
  #
60
66
  # @return [void]
@@ -84,7 +90,7 @@ module Publisher
84
90
  log("Adding allure history")
85
91
  Helpers::Spinner.spin("adding history", exit_on_error: false) do
86
92
  create_history_dir
87
- yield
93
+ download_history
88
94
  end
89
95
  end
90
96
 
@@ -124,7 +130,7 @@ module Publisher
124
130
  #
125
131
  # @return [void]
126
132
  def run_uploads
127
- upload_history unless copy_latest # latest report will add a common history folder
133
+ upload_history unless !run_id || copy_latest
128
134
  upload_report
129
135
  upload_latest_copy if copy_latest
130
136
  end
@@ -0,0 +1,104 @@
1
+ require "google/cloud/storage"
2
+
3
+ module Publisher
4
+ module Uploaders
5
+ # Google cloud storage uploader implementation
6
+ #
7
+ class GCS < Uploader
8
+ private
9
+
10
+ # GCS client
11
+ #
12
+ # @return [Google::Cloud::Storage::Project]
13
+ def client
14
+ @client ||= Google::Cloud::Storage.new
15
+ end
16
+
17
+ # GCS bucket
18
+ #
19
+ # @return [Google::Cloud::Storage::Bucket]
20
+ def bucket
21
+ @bucket ||= client.bucket(bucket_name, skip_lookup: true)
22
+ end
23
+
24
+ # Report url
25
+ #
26
+ # @return [String]
27
+ def report_url
28
+ @report_url ||= url(full_prefix)
29
+ end
30
+
31
+ # Latest report url
32
+ #
33
+ # @return [String]
34
+ def latest_report_url
35
+ @latest_report_url ||= url(prefix)
36
+ end
37
+
38
+ # Download allure history
39
+ #
40
+ # @return [void]
41
+ def download_history
42
+ HISTORY.each do |file_name|
43
+ file = bucket.file(key(prefix, "history", file_name))
44
+ raise("Allure history from previous runs not found!") unless file
45
+
46
+ file.download(path(results_dir, "history", file_name))
47
+ end
48
+ end
49
+
50
+ # Upload allure history
51
+ #
52
+ # @return [void]
53
+ def upload_history
54
+ upload_to_gcs(report_files.select { |file| file.fnmatch?("*/history/*") }, prefix)
55
+ end
56
+
57
+ # Upload allure report
58
+ #
59
+ # @return [void]
60
+ def upload_report
61
+ upload_to_gcs(report_files, full_prefix)
62
+ end
63
+
64
+ # Upload copy of latest run
65
+ #
66
+ # @return [void]
67
+ def upload_latest_copy
68
+ upload_to_gcs(report_files, prefix)
69
+ end
70
+
71
+ # Upload files to s3
72
+ #
73
+ # @param [Array<Pathname>] files
74
+ # @param [String] key_prefix
75
+ # @return [Array<Hash>]
76
+ def upload_to_gcs(files, key_prefix)
77
+ args = files.map do |file|
78
+ {
79
+ file: file.to_s,
80
+ path: key(key_prefix, file.relative_path_from(report_dir))
81
+ }
82
+ end
83
+
84
+ Parallel.each(args, in_threads: 8) { |obj| bucket.create_file(obj[:file], obj[:path]) }
85
+ end
86
+
87
+ # Fabricate key for s3 object
88
+ #
89
+ # @param [String] *args
90
+ # @return [String]
91
+ def key(*args)
92
+ args.compact.join("/")
93
+ end
94
+
95
+ # Report url
96
+ #
97
+ # @param [String] path_prefix
98
+ # @return [String]
99
+ def url(path_prefix)
100
+ ["https://storage.googleapis.com", bucket_name, path_prefix, "index.html"].compact.join("/")
101
+ end
102
+ end
103
+ end
104
+ end
@@ -10,8 +10,8 @@ module Publisher
10
10
  # S3 client
11
11
  #
12
12
  # @return [Aws::S3::Client]
13
- def s3
14
- @s3 ||= Aws::S3::Client.new(region: ENV["AWS_REGION"] || "us-east-1")
13
+ def client
14
+ @client ||= Aws::S3::Client.new(region: ENV["AWS_REGION"] || "us-east-1")
15
15
  rescue Aws::Sigv4::Errors::MissingCredentialsError
16
16
  raise(<<~MSG.strip)
17
17
  missing aws credentials, provide credentials with one of the following options:
@@ -20,14 +20,6 @@ module Publisher
20
20
  MSG
21
21
  end
22
22
 
23
- # Validate if client is properly configured
24
- # and raise error if it is not
25
- #
26
- # @return [void]
27
- def check_client_configured
28
- s3
29
- end
30
-
31
23
  # Report url
32
24
  #
33
25
  # @return [String]
@@ -45,18 +37,16 @@ module Publisher
45
37
  # Add allure history
46
38
  #
47
39
  # @return [void]
48
- def add_history
49
- super do
50
- HISTORY.each do |file|
51
- s3.get_object(
52
- response_target: path(results_dir, "history", file),
53
- key: key(prefix, "history", file),
54
- bucket: bucket
55
- )
56
- end
57
- rescue Aws::S3::Errors::NoSuchKey
58
- raise("Allure history from previous runs not found!")
40
+ def download_history
41
+ HISTORY.each do |file|
42
+ client.get_object(
43
+ response_target: path(results_dir, "history", file),
44
+ key: key(prefix, "history", file),
45
+ bucket: bucket_name
46
+ )
59
47
  end
48
+ rescue Aws::S3::Errors::NoSuchKey
49
+ raise("Allure history from previous runs not found!")
60
50
  end
61
51
 
62
52
  # Upload allure history
@@ -89,12 +79,12 @@ module Publisher
89
79
  args = files.map do |file|
90
80
  {
91
81
  body: File.new(file),
92
- bucket: bucket,
82
+ bucket: bucket_name,
93
83
  key: key(key_prefix, file.relative_path_from(report_dir))
94
84
  }
95
85
  end
96
86
 
97
- Parallel.each(args, in_threads: 8) { |obj| s3.put_object(obj) }
87
+ Parallel.each(args, in_threads: 8) { |obj| client.put_object(obj) }
98
88
  end
99
89
 
100
90
  # Fabricate key for s3 object
@@ -110,7 +100,7 @@ module Publisher
110
100
  # @param [String] path_prefix
111
101
  # @return [String]
112
102
  def url(path_prefix)
113
- ["http://#{bucket}.s3.amazonaws.com", path_prefix, "index.html"].compact.join("/")
103
+ ["http://#{bucket_name}.s3.amazonaws.com", path_prefix, "index.html"].compact.join("/")
114
104
  end
115
105
  end
116
106
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Publisher
4
- VERSION = "0.0.4"
4
+ VERSION = "0.0.5"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: allure-report-publisher
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.4
4
+ version: 0.0.5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andrejs Cunskis
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-05-05 00:00:00.000000000 Z
11
+ date: 2021-05-06 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: aws-sdk-s3
@@ -58,6 +58,20 @@ dependencies:
58
58
  - - "~>"
59
59
  - !ruby/object:Gem::Version
60
60
  version: '4.17'
61
+ - !ruby/object:Gem::Dependency
62
+ name: google-cloud-storage
63
+ requirement: !ruby/object:Gem::Requirement
64
+ requirements:
65
+ - - "~>"
66
+ - !ruby/object:Gem::Version
67
+ version: '1.31'
68
+ type: :runtime
69
+ prerelease: false
70
+ version_requirements: !ruby/object:Gem::Requirement
71
+ requirements:
72
+ - - "~>"
73
+ - !ruby/object:Gem::Version
74
+ version: '1.31'
61
75
  - !ruby/object:Gem::Dependency
62
76
  name: octokit
63
77
  requirement: !ruby/object:Gem::Requirement
@@ -139,17 +153,17 @@ files:
139
153
  - README.md
140
154
  - bin/allure-report-publisher
141
155
  - lib/allure_report_publisher.rb
142
- - lib/allure_report_publisher/commands/base.rb
143
- - lib/allure_report_publisher/commands/upload_s3.rb
156
+ - lib/allure_report_publisher/commands/upload.rb
144
157
  - lib/allure_report_publisher/commands/version.rb
145
158
  - lib/allure_report_publisher/lib/helpers/helpers.rb
146
159
  - lib/allure_report_publisher/lib/helpers/spinner.rb
147
- - lib/allure_report_publisher/lib/providers/_base.rb
160
+ - lib/allure_report_publisher/lib/providers/_provider.rb
148
161
  - lib/allure_report_publisher/lib/providers/github.rb
149
162
  - lib/allure_report_publisher/lib/providers/gitlab.rb
150
163
  - lib/allure_report_publisher/lib/report_generator.rb
151
164
  - lib/allure_report_publisher/lib/uploaders/_uploader.rb
152
- - lib/allure_report_publisher/lib/uploaders/s3_uploader.rb
165
+ - lib/allure_report_publisher/lib/uploaders/gcs.rb
166
+ - lib/allure_report_publisher/lib/uploaders/s3.rb
153
167
  - lib/allure_report_publisher/version.rb
154
168
  homepage: https://github.com/andrcuns/allure-report-uploader
155
169
  licenses:
@@ -1,21 +0,0 @@
1
- module Publisher
2
- module Commands
3
- # Common arguments and options definition
4
- #
5
- module CommonOptions
6
- def self.included(mod)
7
- mod.instance_eval do
8
- option :color, type: :boolean, desc: "Toggle color output, default: false"
9
- option :update_pr,
10
- type: :boolean,
11
- default: false,
12
- desc: "Update pull request description with url to allure report"
13
- option :copy_latest,
14
- type: :boolean,
15
- default: false,
16
- desc: "Keep copy of latest report at base prefix path"
17
- end
18
- end
19
- end
20
- end
21
- end
@@ -1,41 +0,0 @@
1
- module Publisher
2
- module Commands
3
- # Upload allure report
4
- #
5
- class UploadS3 < Dry::CLI::Command
6
- include CommonOptions
7
- include Helpers
8
-
9
- desc "Generate and upload allure report"
10
-
11
- option :results_glob, desc: "Allure results files glob. Required: true"
12
- option :bucket, desc: "Bucket name. Required: true"
13
- option :prefix, desc: "Optional prefix for report path. Required: false"
14
-
15
- example [
16
- "--results-glob='path/to/allure-result/**/*' --bucket=my-bucket",
17
- "--results-glob='path/to/allure-result/**/*' --bucket=my-bucket --project=my-project/prs"
18
- ]
19
-
20
- def call(**args)
21
- validate_args(args)
22
- Helpers.pastel(force_color: args[:color])
23
-
24
- Uploaders::S3
25
- .new(**args.slice(:results_glob, :bucket, :prefix, :copy_latest, :update_pr))
26
- .execute
27
- end
28
-
29
- private
30
-
31
- # Validate required args
32
- #
33
- # @param [Hash] args
34
- # @return [void]
35
- def validate_args(args)
36
- error("Missing argument --results-glob!") unless args[:results_glob]
37
- error("Missing argument --bucket!") unless args[:bucket]
38
- end
39
- end
40
- end
41
- end