geet 0.23.0 → 0.24.0

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.
Files changed (54) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/ci.yml +16 -2
  3. data/.gitignore +0 -1
  4. data/.ruby-version +1 -0
  5. data/Gemfile +3 -6
  6. data/bin/geet +2 -8
  7. data/geet.gemspec +4 -4
  8. data/lib/geet/commandline/configuration.rb +0 -1
  9. data/lib/geet/commandline/editor.rb +0 -2
  10. data/lib/geet/git/repository.rb +12 -21
  11. data/lib/geet/github/abstract_issue.rb +0 -6
  12. data/lib/geet/github/api_interface.rb +0 -1
  13. data/lib/geet/github/issue.rb +0 -3
  14. data/lib/geet/github/milestone.rb +0 -2
  15. data/lib/geet/github/pr.rb +0 -3
  16. data/lib/geet/github/user.rb +0 -3
  17. data/lib/geet/gitlab/pr.rb +3 -1
  18. data/lib/geet/helpers/json_helper.rb +4 -0
  19. data/lib/geet/helpers/os_helper.rb +21 -7
  20. data/lib/geet/helpers/services_workflow_helper.rb +12 -0
  21. data/lib/geet/helpers/summary_helper.rb +7 -0
  22. data/lib/geet/services/abstract_create_issue.rb +5 -5
  23. data/lib/geet/services/add_upstream_repo.rb +6 -0
  24. data/lib/geet/services/close_milestones.rb +0 -2
  25. data/lib/geet/services/comment_pr.rb +0 -3
  26. data/lib/geet/services/create_gist.rb +0 -4
  27. data/lib/geet/services/create_issue.rb +0 -4
  28. data/lib/geet/services/create_pr.rb +4 -6
  29. data/lib/geet/services/list_issues.rb +0 -3
  30. data/lib/geet/services/merge_pr.rb +0 -2
  31. data/lib/geet/services/open_pr.rb +0 -3
  32. data/lib/geet/services/open_repo.rb +0 -2
  33. data/lib/geet/shared/http_error.rb +8 -2
  34. data/lib/geet/shared/repo_permissions.rb +7 -2
  35. data/lib/geet/shared/selection.rb +3 -2
  36. data/lib/geet/utils/attributes_selection_manager.rb +15 -4
  37. data/lib/geet/utils/git_client.rb +4 -1
  38. data/lib/geet/utils/manual_list_selection.rb +39 -14
  39. data/lib/geet/utils/string_matching_selection.rb +5 -0
  40. data/lib/geet/version.rb +1 -1
  41. data/lib/geet.rb +11 -0
  42. data/sorbet/config +3 -1
  43. data/sorbet/rbi/gems/{rbs@3.9.5.rbi → rbs@4.0.0.dev.5.rbi} +2013 -680
  44. data/sorbet/rbi/gems/require-hooks@0.2.2.rbi +110 -0
  45. data/sorbet/rbi/gems/{spoom@1.6.3.rbi → spoom@1.7.11.rbi} +1139 -2246
  46. data/sorbet/rbi/gems/{tapioca@0.16.11.rbi → tapioca@0.17.10.rbi} +721 -835
  47. data/sorbet/rbi/gems/tsort@0.2.0.rbi +393 -0
  48. data/sorbet/rbi/gems/tty-prompt@0.23.1.rbi +3300 -2
  49. data/sorbet/rbi/gems/zeitwerk@2.7.4.rbi +1196 -0
  50. data/sorbet/rbi/shims/unresolved_gem_constants.rbi +4 -0
  51. data/spec/integration/create_pr_spec.rb +157 -147
  52. data/spec/integration/merge_pr_spec.rb +84 -85
  53. data/spec/spec_helper.rb +1 -1
  54. metadata +40 -6
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: f36daf3a9f93bc19c635672aa0dacd0c661680aff4ab62042c7bb9743d9283c0
4
- data.tar.gz: 43eb3b1315136af98b85d828f352ae8b7556cc5049bf2d23e8d4b2396728027e
3
+ metadata.gz: eeb2fbfeebdf5fad15d266e1c4b30fb5554f0418057b5fe279a4395149e9b4a2
4
+ data.tar.gz: 78b4a9f2de093f896d494de393991980e9c619d10ce979a9b9b0941fff39381d
5
5
  SHA512:
6
- metadata.gz: 10993b5f5d10122cf60ac37de56600bd5ea131b82cfb78e40cd468a56b34eba3b2f101ee1ec8bb8b78c3d419c5a9569006d1bec2be01bbc78e6d2fed80a1eab9
7
- data.tar.gz: fedbbf26a35167056c4c1bb0800aa9f233174ab2b850ff8467c27bdec3b5ae79c0c3258983b5e5ea3efb4739516cd97e634c70f35ad0b627e38ed9624b95485f
6
+ metadata.gz: 17409c6c638abc9e27ffbae3af34bec526484c2baf084ddc7adff5beaf91ef3355377cb8bc515afc54fd97b3dc67090a26422891733638cacf3efadd26e4fdf4
7
+ data.tar.gz: f6498c9223f91625dd85117322bef311a74b3bd027b9e4d51cb3e4bdea076418822e9637e56de9a462713eba218aaba33380509d23ddc115f04c7075ec6f3c3f
@@ -5,11 +5,14 @@ on: [pull_request]
5
5
  jobs:
6
6
  test:
7
7
  runs-on: ubuntu-latest
8
+ env:
9
+ GITHUB_API_TOKEN: foo
10
+ GITLAB_API_TOKEN: bar
8
11
  strategy:
9
12
  matrix:
10
- ruby-version: [head, 3.4, 3.3, 3.2]
13
+ ruby-version: [head, 4.0, 3.4, 3.3, 3.2]
11
14
  fail-fast: false
12
- continue-on-error: ${{ endsWith(matrix.ruby, 'head') || matrix.ruby == 'debug' }}
15
+ continue-on-error: ${{ endsWith(matrix['ruby-version'], 'head') || matrix['ruby-version'] == 'debug' }}
13
16
  steps:
14
17
  - uses: actions/checkout@v5
15
18
  - uses: ruby/setup-ruby@v1
@@ -18,3 +21,14 @@ jobs:
18
21
  bundler-cache: true
19
22
  - run: bundle install
20
23
  - run: bundle exec rspec
24
+ sorbet:
25
+ runs-on: ubuntu-latest
26
+ steps:
27
+ - uses: actions/checkout@v5
28
+ with:
29
+ fetch-depth: ${{ env.REPO_FETCH_DEPTH }}
30
+ - uses: ruby/setup-ruby@v1
31
+ with:
32
+ bundler-cache: true
33
+ - name: Sorbet
34
+ run: bundle exec srb typecheck
data/.gitignore CHANGED
@@ -1,4 +1,3 @@
1
- /.ruby-version
2
1
  /.ruby-gemset
3
2
  /Gemfile.lock
4
3
  /test_repos
data/.ruby-version ADDED
@@ -0,0 +1 @@
1
+ 3.4.6
data/Gemfile CHANGED
@@ -4,18 +4,15 @@ source 'https://rubygems.org'
4
4
 
5
5
  gemspec
6
6
 
7
- gem 'sorbet-runtime'
8
-
9
7
  group :development do
10
- gem 'sorbet'
11
8
  gem 'byebug'
12
- gem 'rubocop', '~> 1.35.0', require: :false
9
+ gem 'rubocop', '~> 1.35.0', require: false
13
10
  gem 'spoom', require: false
14
- gem 'tapioca', require: false
11
+ gem 'tapioca', '>= 0.17.10', require: false
15
12
  end
16
13
 
17
14
  group :test do
18
15
  gem 'rspec', '~> 3.13.0'
19
- gem 'vcr', '~> 6.1.0'
16
+ gem 'vcr', '~> 6.4.0'
20
17
  gem 'webmock', '~> 3.1.1'
21
18
  end
data/bin/geet CHANGED
@@ -2,14 +2,8 @@
2
2
  # frozen_string_literal: true
3
3
 
4
4
  require 'simple_scripting/configuration'
5
- require_relative '../lib/geet/commandline/configuration'
6
- require_relative '../lib/geet/commandline/commands'
7
- require_relative '../lib/geet/commandline/editor'
8
- require_relative '../lib/geet/git/repository'
9
- require_relative '../lib/geet/helpers/summary_helper'
10
- require_relative '../lib/geet/shared/selection'
11
- require_relative '../lib/geet/utils/git_client'
12
- Dir[File.join(__dir__, '../lib/geet/services/*.rb')].each { |filename| require filename }
5
+ require 'tmpdir'
6
+ require_relative '../lib/geet'
13
7
 
14
8
  class GeetLauncher
15
9
  include Geet
data/geet.gemspec CHANGED
@@ -1,8 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- $LOAD_PATH << File.expand_path('lib', __dir__)
4
-
5
- require 'geet/version'
3
+ require_relative 'lib/geet/version'
6
4
 
7
5
  Gem::Specification.new do |s|
8
6
  s.name = 'geet'
@@ -10,7 +8,7 @@ Gem::Specification.new do |s|
10
8
  s.platform = Gem::Platform::RUBY
11
9
  s.required_ruby_version = '>= 3.2.0'
12
10
  s.authors = ['Saverio Miroddi']
13
- s.date = '2025-10-29'
11
+ s.date = '2026-01-13'
14
12
  s.email = ['saverio.pub2@gmail.com']
15
13
  s.homepage = 'https://github.com/saveriomiroddi/geet'
16
14
  s.summary = 'Commandline interface for performing SCM host operations, eg. create a PR on GitHub'
@@ -20,7 +18,9 @@ Gem::Specification.new do |s|
20
18
  s.add_runtime_dependency 'base64', '~> 0.3.0'
21
19
  s.add_runtime_dependency 'ostruct', '~> 0.6.3'
22
20
  s.add_runtime_dependency 'simple_scripting', '~> 0.14.0'
21
+ s.add_runtime_dependency 'sorbet-runtime', '= 0.6.12883'
23
22
  s.add_runtime_dependency 'tty-prompt', '~> 0.23.1'
23
+ s.add_runtime_dependency 'zeitwerk', '~> 2.7'
24
24
 
25
25
  s.add_development_dependency 'rake', '~> 12.3'
26
26
 
@@ -1,7 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require 'simple_scripting/argv'
4
- require_relative 'commands'
5
4
 
6
5
  module Geet
7
6
  module Commandline
@@ -2,8 +2,6 @@
2
2
 
3
3
  require 'tempfile'
4
4
 
5
- require_relative '../helpers/os_helper'
6
-
7
5
  module Geet
8
6
  module Commandline
9
7
  class Editor
@@ -1,7 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../utils/git_client'
4
-
5
3
  module Geet
6
4
  module Git
7
5
  # This class represents, for convenience, both the local and the remote repository, but the
@@ -122,31 +120,24 @@ module Geet
122
120
  def attempt_provider_call(class_name, meth, *args)
123
121
  module_name = provider_name.capitalize
124
122
 
125
- require_provider_modules
126
-
127
123
  full_class_name = "Geet::#{module_name}::#{class_name}"
128
124
 
129
- if Kernel.const_defined?(full_class_name)
130
- klass = Kernel.const_get(full_class_name)
131
-
132
- if !klass.respond_to?(meth)
133
- raise "The functionality invoked (#{class_name}.#{meth}) is not currently supported!"
134
- end
135
-
136
- # Can't use ruby2_keywords, because the method definitions use named keyword arguments.
137
- #
138
- kwargs = args.last.is_a?(Hash) ? args.pop : {}
139
-
140
- klass.send(meth, *args, **kwargs)
141
- else
125
+ # Use const_get directly to trigger Zeitwerk autoloading
126
+ begin
127
+ klass = Object.const_get(full_class_name)
128
+ rescue NameError
142
129
  raise "The class referenced (#{full_class_name}) is not currently supported!"
143
130
  end
144
- end
145
131
 
146
- def require_provider_modules
147
- files_pattern = "#{__dir__}/../#{provider_name}/*.rb"
132
+ if !klass.respond_to?(meth)
133
+ raise "The functionality invoked (#{class_name}.#{meth}) is not currently supported!"
134
+ end
135
+
136
+ # Can't use ruby2_keywords, because the method definitions use named keyword arguments.
137
+ #
138
+ kwargs = args.last.is_a?(Hash) ? args.pop : {}
148
139
 
149
- Dir[files_pattern].each { |filename| require filename }
140
+ klass.send(meth, *args, **kwargs)
150
141
  end
151
142
 
152
143
  # WARNINGS
@@ -2,12 +2,6 @@
2
2
 
3
3
  module Geet
4
4
  module Github
5
- # It seems that autoloading will be deprecated, but it's currently the cleanest solution
6
- # to the legitimate problem of AbstractIssue needing Issue/PR to be loaded (due to :list),
7
- # and viceversa (due to class definition).
8
- autoload :Issue, File.expand_path('issue', __dir__)
9
- autoload :PR, File.expand_path('pr', __dir__)
10
-
11
5
  # For clarity, in this class we keep only the identical logic between the subclasses, but
12
6
  # other methods could be moved in here at some complexity cost.
13
7
  class AbstractIssue
@@ -3,7 +3,6 @@
3
3
  require 'uri'
4
4
  require 'net/http'
5
5
  require 'json'
6
- require_relative '../shared/http_error'
7
6
 
8
7
  module Geet
9
8
  module Github
@@ -2,9 +2,6 @@
2
2
 
3
3
  module Geet
4
4
  module Github
5
- # See AbstractIssue for the circular dependency issue notes.
6
- autoload :AbstractIssue, File.expand_path('abstract_issue', __dir__)
7
-
8
5
  class Issue < Geet::Github::AbstractIssue
9
6
  def self.create(title, description, api_interface, **)
10
7
  api_path = 'issues'
@@ -1,7 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../helpers/json_helper'
4
-
5
3
  module Geet
6
4
  module Github
7
5
  class Milestone
@@ -2,9 +2,6 @@
2
2
 
3
3
  module Geet
4
4
  module Github
5
- # See AbstractIssue for the circular dependency issue notes.
6
- autoload :AbstractIssue, File.expand_path('abstract_issue', __dir__)
7
-
8
5
  class PR < AbstractIssue
9
6
  # See https://developer.github.com/v3/pulls/#create-a-pull-request
10
7
  #
@@ -1,8 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../shared/repo_permissions'
4
- require_relative '../shared/http_error'
5
-
6
3
  module Geet
7
4
  module Github
8
5
  class User
@@ -40,7 +40,9 @@ module Geet
40
40
 
41
41
  # See https://docs.gitlab.com/ee/api/merge_requests.html#accept-mr
42
42
  #
43
- def merge
43
+ def merge(merge_method: nil)
44
+ raise ArgumentError, "GitLab does not support the merge_method parameter" if merge_method
45
+
44
46
  api_path = "projects/#{@api_interface.path_with_namespace(encoded: true)}/merge_requests/#{number}/merge"
45
47
 
46
48
  @api_interface.send_request(api_path, http_method: :put)
@@ -1,3 +1,4 @@
1
+ # typed: strict
1
2
  # frozen_string_literal: true
2
3
 
3
4
  require 'time'
@@ -5,10 +6,13 @@ require 'time'
5
6
  module Geet
6
7
  module Helpers
7
8
  module JsonHelper
9
+ extend T::Sig
10
+
8
11
  # Most common Json time format.
9
12
  #
10
13
  # Returns nil if nil is passed.
11
14
  #
15
+ sig { params(timestamp: T.nilable(String)).returns(T.nilable(Date)) }
12
16
  def parse_iso_8601_timestamp(timestamp)
13
17
  Time.iso8601(timestamp).to_date if timestamp
14
18
  end
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+ # typed: true
2
3
 
3
4
  require 'English'
4
5
  require 'open3'
@@ -7,6 +8,11 @@ require 'shellwords'
7
8
  module Geet
8
9
  module Helpers
9
10
  module OsHelper
11
+ extend T::Sig
12
+
13
+ include Kernel # for Sorbet compatibility
14
+
15
+ sig { params(file_or_url: String).void }
10
16
  def open_file_with_default_application(file_or_url)
11
17
  open_command = case
12
18
  when ENV["WSL_DISTRO_NAME"]
@@ -29,12 +35,16 @@ module Geet
29
35
  # On non-interactive runs, the stdout content is returned, stripped of the surrounding
30
36
  # whitespaces.
31
37
  #
32
- # description: optional string, to make the error clearer.
33
- # interactive: set when required; in this case, a different API will be used (`system()`
34
- # instead of `popen3`).
35
- # silent_stderr: don't print the stderr output
36
- # allow_error: don't raise error on failure
37
- #
38
+ sig {
39
+ params(
40
+ command: String,
41
+ description: T.nilable(String), # specify to make the error clearer
42
+ interactive: T::Boolean, # set when required; in this case, a different API will be used (`system()`
43
+ # instead of `popen3`)
44
+ silent_stderr: T::Boolean, # don't print the stderr output
45
+ allow_error: T::Boolean # don't raise error on failure
46
+ ).returns(T.nilable(String))
47
+ }
38
48
  def execute_command(command, description: nil, interactive: false, silent_stderr: false, allow_error: false)
39
49
  description_message = " on #{description}" if description
40
50
 
@@ -45,6 +55,8 @@ module Geet
45
55
  raise "Error#{description_message} (exit status: #{$CHILD_STATUS.exitstatus})"
46
56
  end
47
57
  else
58
+ result = ""
59
+
48
60
  Open3.popen3(command) do |_, stdout, stderr, wait_thread|
49
61
  stdout_content = stdout.read
50
62
  stderr_content = stderr.read
@@ -56,8 +68,10 @@ module Geet
56
68
  raise "Error#{description_message}: #{error_message}"
57
69
  end
58
70
 
59
- stdout_content.strip
71
+ result = stdout_content.strip
60
72
  end
73
+
74
+ result
61
75
  end
62
76
  end
63
77
  end
@@ -1,3 +1,4 @@
1
+ # typed: strict
1
2
  # frozen_string_literal: true
2
3
 
3
4
  require 'English'
@@ -9,10 +10,21 @@ module Geet
9
10
  # Helper for services common workflow, for example, find the merge head.
10
11
  #
11
12
  module ServicesWorkflowHelper
13
+ include Kernel
14
+ extend T::Sig
15
+
16
+ sig { void }
17
+ def initialize
18
+ @repository = T.let(T.unsafe(nil), Git::Repository)
19
+ @git_client = T.let(T.unsafe(nil), Utils::GitClient)
20
+ @out = T.let(T.unsafe(nil), IO)
21
+ end
22
+
12
23
  # Expect to find only one.
13
24
  #
14
25
  # Requires: @out, @repository.
15
26
  #
27
+ sig { returns(T.any(Geet::Github::PR, Geet::Gitlab::PR)) }
16
28
  def checked_find_branch_pr
17
29
  owner = if @repository.upstream?
18
30
  @repository.authenticated_user.username
@@ -1,16 +1,23 @@
1
+ # typed: strict
1
2
  # frozen_string_literal: true
2
3
 
3
4
  module Geet
4
5
  module Helpers
5
6
  module SummaryHelper
7
+ include Kernel
8
+ extend T::Sig
9
+
6
10
  # Split the summary in title and description.
7
11
  # The description is optional, but the title mandatory.
8
12
  #
13
+ sig { params(summary: String).returns([String, String]) }
9
14
  def split_summary(summary)
10
15
  raise "Missing title in summary!" if summary.to_s.strip.empty?
11
16
 
12
17
  title, description = summary.split(/\r|\n/, 2)
13
18
 
19
+ raise "Title missing" if title.nil?
20
+
14
21
  # The title may have a residual newline char; the description may not be present,
15
22
  # or have multiple blank lines.
16
23
  [title.strip, description.to_s.strip]
@@ -1,17 +1,17 @@
1
1
  # frozen_string_literal: true
2
+ # typed: strict
2
3
 
4
+ require 'stringio'
3
5
  require 'tmpdir'
4
6
 
5
- require_relative '../helpers/os_helper'
6
- require_relative '../utils/attributes_selection_manager'
7
- require_relative '../utils/manual_list_selection'
8
- require_relative '../utils/string_matching_selection'
9
-
10
7
  module Geet
11
8
  module Services
12
9
  class AbstractCreateIssue
10
+ extend T::Sig
11
+
13
12
  include Geet::Helpers::OsHelper
14
13
 
14
+ sig { params(repository: T.untyped, out: T.any(IO, StringIO)).void }
15
15
  def initialize(repository, out: $stdout)
16
16
  @repository = repository
17
17
  @out = out
@@ -1,18 +1,23 @@
1
1
  # frozen_string_literal: true
2
+ # typed: strict
2
3
 
3
4
  module Geet
4
5
  module Services
5
6
  # Add the upstream repository to the current repository (configuration).
6
7
  #
7
8
  class AddUpstreamRepo
9
+ extend T::Sig
10
+
8
11
  DEFAULT_GIT_CLIENT = Utils::GitClient.new
9
12
 
13
+ sig { params(repository: T.untyped, out: T.any(IO, StringIO), git_client: T.untyped).void }
10
14
  def initialize(repository, out: $stdout, git_client: DEFAULT_GIT_CLIENT)
11
15
  @repository = repository
12
16
  @out = out
13
17
  @git_client = git_client
14
18
  end
15
19
 
20
+ sig { void }
16
21
  def execute
17
22
  raise "Upstream remote already existing!" if @git_client.remote_defined?(Utils::GitClient::UPSTREAM_NAME)
18
23
 
@@ -31,6 +36,7 @@ module Geet
31
36
 
32
37
  # Use the same protocol as the main repository.
33
38
  #
39
+ sig { params(parent_path: String).returns((String)) }
34
40
  def compose_parent_url(parent_path)
35
41
  protocol, domain, separator, _, suffix = @git_client.remote_components
36
42
 
@@ -1,7 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../shared/selection'
4
-
5
3
  module Geet
6
4
  module Services
7
5
  class CloseMilestones
@@ -1,8 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../helpers/os_helper'
4
- require_relative '../helpers/services_workflow_helper'
5
-
6
3
  module Geet
7
4
  module Services
8
5
  # Add a comment to the PR for the current branch.
@@ -1,9 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../helpers/os_helper'
4
- require_relative '../github/api_interface'
5
- require_relative '../github/gist'
6
-
7
3
  module Geet
8
4
  module Services
9
5
  class CreateGist
@@ -1,9 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative 'abstract_create_issue'
4
- require_relative '../shared/repo_permissions'
5
- require_relative '../shared/selection'
6
-
7
3
  module Geet
8
4
  module Services
9
5
  class CreateIssue < AbstractCreateIssue
@@ -1,12 +1,8 @@
1
1
  # frozen_string_literal: true
2
+ # typed: true
2
3
 
3
4
  require 'io/console' # stdlib
4
5
 
5
- require_relative 'abstract_create_issue'
6
- require_relative '../shared/repo_permissions'
7
- require_relative '../shared/selection'
8
- require_relative 'add_upstream_repo'
9
-
10
6
  module Geet
11
7
  module Services
12
8
  class CreatePr < AbstractCreateIssue
@@ -87,7 +83,9 @@ module Geet
87
83
  selection_manager.select_attributes
88
84
  end
89
85
 
90
- def sync_with_remote_branch
86
+ # `input` is a Sorbet workaround (error 7001).
87
+ #
88
+ def sync_with_remote_branch(input: T.untyped)
91
89
  # Fetching doesn't have a real world case when there isn't a remote branch. It's also not generally
92
90
  # useful when there is a remote branch, however, since a force push is an option, it's important
93
91
  # to be 100% sure of the current diff.
@@ -1,8 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../utils/attributes_selection_manager'
4
- require_relative '../shared/selection'
5
-
6
3
  module Geet
7
4
  module Services
8
5
  class ListIssues
@@ -1,7 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../helpers/services_workflow_helper'
4
-
5
3
  module Geet
6
4
  module Services
7
5
  # Merges the PR for the current branch.
@@ -1,8 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../helpers/os_helper'
4
- require_relative '../helpers/services_workflow_helper'
5
-
6
3
  module Geet
7
4
  module Services
8
5
  # Open in the browser the PR for the current branch.
@@ -1,7 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../helpers/os_helper'
4
-
5
3
  module Geet
6
4
  module Services
7
5
  # Open in the browser the current repository.
@@ -1,12 +1,18 @@
1
+ # frozen_string_literal: true
2
+ # typed: strict
3
+
1
4
  module Geet
2
5
  module Shared
3
6
  class HttpError < RuntimeError
4
- # Integer.
7
+ extend T::Sig
8
+
9
+ sig { returns(Integer) }
5
10
  attr_reader :code
6
11
 
12
+ sig { params(message: String, code: T.any(Integer, String)).void }
7
13
  def initialize(message, code)
8
14
  super(message)
9
- @code = code.to_i
15
+ @code = T.let(code.to_i, Integer)
10
16
  end
11
17
  end
12
18
  end
@@ -1,24 +1,29 @@
1
1
  # frozen_string_literal: true
2
+ # typed: strict
2
3
 
3
4
  module Geet
4
5
  module Shared
5
6
  module RepoPermissions
7
+ extend T::Sig
8
+
6
9
  PERMISSION_ADMIN = 'admin'
7
10
  PERMISSION_WRITE = 'write'
8
11
  PERMISSION_READ = 'read'
9
12
  PERMISSION_NONE = 'none'
10
13
 
14
+ ALL_PERMISSIONS = T.let(T.unsafe(nil), T::Array[String]) if defined?(T::sig)
11
15
  ALL_PERMISSIONS = [
12
16
  PERMISSION_ADMIN,
13
17
  PERMISSION_WRITE,
14
18
  PERMISSION_READ,
15
19
  PERMISSION_NONE,
16
- ]
20
+ ].freeze
17
21
 
18
22
  # Not worth creating a Permission class at this stage.
19
23
  #
24
+ sig { params(subject_permission: String, object_permission: String).returns(T::Boolean) }
20
25
  def permission_greater_or_equal_to?(subject_permission, object_permission)
21
- ALL_PERMISSIONS.index(subject_permission) <= ALL_PERMISSIONS.index(object_permission)
26
+ T.must(ALL_PERMISSIONS.index(subject_permission)) <= T.must(ALL_PERMISSIONS.index(object_permission))
22
27
  end
23
28
  end
24
29
  end
@@ -1,11 +1,12 @@
1
1
  # frozen_string_literal: true
2
+ # typed: strict
2
3
 
3
4
  module Geet
4
5
  module Shared
5
6
  module Selection
6
- MANUAL_LIST_SELECTION_FLAG = '-'.freeze
7
+ MANUAL_LIST_SELECTION_FLAG = '-'
7
8
  # Don't select anything; return the null value.
8
- SKIP_LIST_SELECTION_FLAG = ''.freeze
9
+ SKIP_LIST_SELECTION_FLAG = ''
9
10
 
10
11
  SELECTION_SINGLE = :single
11
12
  SELECTION_MULTIPLE = :multiple