lapidario 0.3alpha.0 → 0.3beta.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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 20d6caf8e33b92cf05ac97c0aabbc067056c319c1f346f0b7dc18df4e15a53bc
4
- data.tar.gz: f5523dcf45fea5d35c4a7fbb67bcf181d23b800cb56fb682a3f29a9929f14c71
3
+ metadata.gz: 41f5cc564d0ff9a994570ecb899125c0dbf719aefa1de77c5a011f79c6cdb3a5
4
+ data.tar.gz: c5d4c5b3844a346b1aa55b4aca8feaf4d58cbee443f5b1f19ad60ed9a2472ebb
5
5
  SHA512:
6
- metadata.gz: 8ac1f42c2addf85814d1344a6cb0421cdd1484d2fb698ef13613897cda236a18ddc4966b6f2ad2649176b6bd79ec6cb19860792476c13feafa04a7e7684233be
7
- data.tar.gz: 40f1b5d1889669bdb91949ef52aaab82b6f40e5c84cb8d35f2f683a4ed5a13ff36546ae5fa726433644362e55e2e7a4fe0c3d7a1f0230aca5228404d514996af
6
+ metadata.gz: 5d8a1c25939106175845ab619a80568426054d68cc6dc20b545c07992a1b6e7e6b9c2845f4035aa085feb02b2a36a6809fd56888a4404348c9f93fa0b114655c
7
+ data.tar.gz: 57d50d3eeedef2f863e8e105e1dc300c08c0ec0cbfc5c5dd75a210b681c3786a53eebf9f9b6ec7b921db375dda128a29d233ab1a098dfa9411e86c2823795764
data/Gemfile CHANGED
@@ -1,16 +1,2 @@
1
- # frozen_string_literal: true
2
-
3
- source "https://rubygems.org"
4
-
5
- # Specify your gem's dependencies in lapidario.gemspec
6
- gemspec
7
-
8
- group :development, :test do
9
- gem "pry", "~> 0.14", require: true
10
-
11
- gem "rake", "~> 13.0"
12
-
13
- gem "rspec", "~> 3.0"
14
-
15
- gem "rubocop", "~> 1.21"
16
- end
1
+ gem "rails", "6.0.0"
2
+ gem "rspec", "3.10.0"
data/README.md CHANGED
@@ -1,41 +1,46 @@
1
1
  # Lapidario
2
+ 'Lapidario' is a noun that is derived from the Latin 'lapidarius,' which means "of or relating to engraved stones or inscriptions." It can also mean "one who engraves stones or inscriptions".
3
+ It is also a Gemfile and Gemfile.lock static analyzer made to help with edition and management of Gemfiles.
4
+ The idea for it was conceived while upgrading gem versions for a lot of Rails microservices at once.
5
+ Its main use is to make a Gemfile better reflect the current state of versions used in a project, and also to specify or maintain explicit gem versions in order to better avoid [dependency hell](https://en.wikipedia.org/wiki/Dependency_hell).
2
6
 
3
- TODO: Delete this and the text below, and describe your gem
7
+ # Example Workflow #1 : Updating Most Gems
8
+ Let's suppose you have a project that has not been updated in a while. You would like to update every gem version in your gemfile except for, say, RSpec.
9
+ <add # LOCK to the right of rspec, run lapidario reset, run bundle >
4
10
 
5
- Welcome to your new gem! In this directory, you'll find the files you need to be able to package up your Ruby library into a gem. Put your Ruby code in the file `lib/lapidario`. To experiment with that code, run `bin/console` for an interactive prompt.
11
+ # Example Workflow #2 : Performing a Minor Update
6
12
 
7
- ## TO DO:
8
- - [ ] Backup system: keep `Gemfile.original` stashed persistently
9
- - [x] Add option to ignore Gemfile lines with `# LOCK` commented to the right end of the line
10
- - [x] Normalize git gems with rubygems from Gemfile.lock
11
- - [x] Add logic to ignore any comments in Gemfile gem lines
12
- - [ ] Normalize gems from other sources with rubygems from Gemfile.lock
13
13
 
14
14
  ## Installation
15
15
 
16
16
  TODO: Replace `UPDATE_WITH_YOUR_GEM_NAME_PRIOR_TO_RELEASE_TO_RUBYGEMS_ORG` with your gem name right after releasing it to RubyGems.org. Please do not do it earlier due to security reasons. Alternatively, replace this section with instructions to install your gem from git if you don't plan to release to RubyGems.org.
17
17
 
18
- Install the gem and add to the application's Gemfile by executing:
19
-
20
- $ bundle add UPDATE_WITH_YOUR_GEM_NAME_PRIOR_TO_RELEASE_TO_RUBYGEMS_ORG
21
-
22
- If bundler is not being used to manage dependencies, install the gem by executing:
18
+ Install lts version:
19
+ `gem install lapidario`
23
20
 
24
- $ gem install UPDATE_WITH_YOUR_GEM_NAME_PRIOR_TO_RELEASE_TO_RUBYGEMS_ORG
21
+ Install pre-release version:
22
+ `gem install lapidario --pre`
25
23
 
26
24
  ## Usage
27
25
 
28
26
  TODO: Write usage instructions here
29
27
 
28
+ ## TO DO:
29
+ - [x] Backup system: keep `Gemfile.original` stashed persistently
30
+ - [x] Add option to ignore Gemfile lines with `# LOCK` commented to the right end of the line
31
+ - [x] Normalize git gems with rubygems from Gemfile.lock
32
+ - [x] Add logic to ignore any comments in Gemfile gem lines
33
+ - [ ] Normalize gems from other sources (such as GIT) with rubygems from Gemfile.lock
34
+
30
35
  ## Development
31
36
 
32
- 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.
37
+ 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. Run `bin/lapidario` to test changes in CLI integration.
33
38
 
34
39
  To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and the created tag, and push the `.gem` file to [rubygems.org](https://rubygems.org).
35
40
 
36
41
  ## Contributing
37
42
 
38
- Bug reports and pull requests are welcome on GitHub at https://github.com/[USERNAME]/lapidario.
43
+ Bug reports and pull requests are welcome on GitHub at https://github.com/octehren/lapidario.
39
44
 
40
45
  ## License
41
46
 
data/bin/lapidario CHANGED
@@ -3,4 +3,4 @@
3
3
 
4
4
  require_relative "../lib/cli"
5
5
 
6
- Lapidario::CLI.start(ARGV)
6
+ Lapidario::CLI.new(ARGV).start
data/lapidario.gemspec CHANGED
@@ -9,15 +9,15 @@ Gem::Specification.new do |spec|
9
9
  spec.email = ["ehren.dev.mail@gmail.com"]
10
10
 
11
11
  spec.summary = "Auxiliary for bulk updates of gems in a project."
12
- spec.description = "Lapidario is a Gemfile and Gemfile.lock static analyzer that helps with bulk updates of gems in a project. As of version 0.1, run it in a directory with both a Gemfile and Gemfile.lock to hard-code the locked versions in Gemfile.lock to the Gemfile."
13
- spec.homepage = "https://example.com"
12
+ spec.description = "Lapidario is a Gemfile and Gemfile.lock static analyzer that helps with bulk updates and explicit version hard-coding of gems in a project. See https://github.com/octehren/lapidario for more."
13
+ spec.homepage = "https://github.com/octehren/lapidario"
14
14
  spec.license = "MIT"
15
15
  spec.required_ruby_version = ">= 2.6.0"
16
16
 
17
17
  spec.metadata["allowed_push_host"] = "https://rubygems.org"
18
18
 
19
19
  spec.metadata["homepage_uri"] = spec.homepage
20
- spec.metadata["source_code_uri"] = "https://example.com"
20
+ spec.metadata["source_code_uri"] = "https://github.com/octehren/lapidario"
21
21
  spec.metadata["changelog_uri"] = "https://example.com" # Put your gem's CHANGELOG.md URL here.
22
22
 
23
23
  # Specify which files should be added to the gem when it is released.
data/lib/cli.rb CHANGED
@@ -3,41 +3,100 @@ require "optparse"
3
3
  require_relative "lapidario"
4
4
 
5
5
  module Lapidario
6
- module CLI
7
- def self.start(_cmd_args)
8
- if _cmd_args.include?('--help') || _cmd_args.include?('-h')
9
- puts "Usage: lapidario [options]\n\n"
10
- puts "NOTE: if you want to exclude any gem in your Gemfile to the functionality described below, comment 'LOCK' at the end of its line.\nSee examples:\n\n"
11
- puts "Valid example of locking gem line:\n"
12
- puts "gem 'rails', '~> 7.0' # LOCK"
13
- puts "\n\nInvalid example of locking gem line:"
14
- puts "gem 'rails', '~> 7.0' # Not locked, will be taken into account to rebuild Gemfile"
15
- puts "\n\nOptions:"
16
- puts " --help, -h Show help message"
17
- puts " --lock, -l Rebuild Gemfile using versions specified in Gemfile.lock; default sign is '~>' and default depth is 2 (up to minor version, ignores patch)"
18
- puts " --reset, -r Rebuild Gemfile without gem versions"
19
- puts " --full-reset, -fr Rebuild Gemfile, removing all info but gem names"
20
- exit
6
+ class CLI
7
+ def initialize(_cmd_args)
8
+ parse_options(_cmd_args) # will initialize variables below if options are passed
9
+ @project_path_hash ||= { project_path: './' }
10
+ @reset_gemfile ||= false
11
+ @full_reset_gemfile ||= false
12
+ @lock_gemfile ||= true unless @reset_gemfile || @full_reset_gemfile
13
+ @version_depth ||= 2
14
+ @version_sign ||= '~>'
15
+ @save_new_gemfile ||= false
16
+ @save_backup ||= true if @save_backup.nil? # conditional assignment also executes on non-nil falsey values
17
+ end
18
+
19
+ def parse_options(options)
20
+ opt_parser = OptionParser.new do |opts|
21
+ opts.on("-h", "--help", "Show help message") do
22
+ puts "NOTE: if you want to exclude any gem in your Gemfile to the functionality described below, comment 'LOCK' at the end of its line.\nSee examples:\n\n"
23
+ puts "Valid example of locking gem line:\n"
24
+ puts "gem 'rails', '~> 7.0' # LOCK"
25
+ puts "\nInvalid example of locking gem line:"
26
+ puts "gem 'rails', '~> 7.0' # Not locked, will be taken into account to rebuild Gemfile\n\n"
27
+ puts opts
28
+ exit
29
+ end
30
+
31
+ opts.on("-w", "--write", "Writes command output to Gemfile. Backs up previous Gemfile in Gemfile.original, remember to remove it later") do
32
+ @save_new_gemfile = true
33
+ end
34
+
35
+ opts.on("-s", "--skip-backup", "Skips creation of backup Gemfile.original if writing to Gemfile") do
36
+ @save_backup = false
37
+ end
38
+
39
+ opts.on("-d", "--depth NUMBER", "Select depth (major = 1, minor = 2, patch = 3) of version string; min = 1, max = 3, default = 2") do |depth|
40
+ @version_depth = depth.to_i
41
+ end
42
+
43
+ opts.on("-v", "--version-sign NUMBER", "Select sign to use for version specification (default = '~>') (0 = '~>', 1 = '>=', 2 = '<=', 3 = '>', 4 = '<', 5 = no sign)") do |sign|
44
+ @version_sign = Lapidario::Helper.get_version_sign_from_number(sign.to_i)
45
+ end
46
+
47
+ opts.on("-p", "--path STRING", "Define path in which Gemfile and Lockfile are located. Defaults to current directory") do |project_path|
48
+ @project_path_hash = { project_path: project_path }
49
+ end
50
+
51
+ opts.on("-l", "--lock", "Rebuild Gemfile using versions specified in Gemfile.lock; default sign is '~>' and default depth is 2 (major & minor versions, ignores patch)") do
52
+ @lock_gemfile = true
53
+ end
54
+
55
+ opts.on("-r", "--reset", "Rebuild Gemfile without gem versions") do
56
+ @reset_gemfile = true
57
+ end
58
+
59
+ opts.on("-f", "--full-reset", "Rebuild Gemfile, removing all info but gem names") do
60
+ @full_reset_gemfile = true
61
+ end
21
62
  end
22
- puts "cmd args: #{_cmd_args}"
23
- project_path_hash = { project_path: './' }
24
- info_instances = Lapidario.get_gemfile_and_lockfile_info(project_path_hash)
63
+
64
+ # Parse the command-line arguments
65
+ opt_parser.parse!(options)
66
+ end
67
+
68
+ def start
69
+ info_instances = Lapidario.get_gemfile_and_lockfile_info(@project_path_hash)
25
70
  gemfile_info = info_instances[0]
26
71
  lockfile_info = info_instances[1]
27
72
  original_gemfile_lines = gemfile_info.original_gemfile
28
73
  new_gemfile_info = case
29
- when _cmd_args.include?('--reset'), _cmd_args.include?('-r')
30
- Lapidario.hardcode_gemfile_with_empty_versions(gemfile_info, true) # keep_extra_info = true
31
- when _cmd_args.include?('--full-reset'), _cmd_args.include?('-fr')
32
- Lapidario.hardcode_gemfile_with_empty_versions(gemfile_info, false) # keep_extra_info = false
33
- else # default = --lock
34
- Lapidario.hardcode_lockfile_versions_into_gemfile_info(gemfile_info, lockfile_info)
35
- end
74
+ when @reset_gemfile
75
+ Lapidario.hardcode_gemfile_with_empty_versions(gemfile_info, true) # keep_extra_info = true
76
+ when @full_reset_gemfile
77
+ Lapidario.hardcode_gemfile_with_empty_versions(gemfile_info, false) # keep_extra_info = false
78
+ when @lock_gemfile # default = --lock
79
+ Lapidario.hardcode_lockfile_versions_into_gemfile_info(gemfile_info, lockfile_info, @version_sign, @version_depth)
80
+ end
36
81
 
37
82
  new_gemfile = Lapidario.build_new_gemfile(new_gemfile_info, original_gemfile_lines)
38
- puts "New gemfile created:"
83
+ puts "New gemfile created:\n\n================================== GEMFILE START =================================="
39
84
  puts new_gemfile
40
- puts "In case it does not look right, check for Gemfile.original in the same directory."
85
+ puts "================================== GEMFILE END ==================================\n\nIn case it does not look right, check for Gemfile.original in the same directory if you are writing to the Gemfile and did not cancel the backup."
86
+ if @save_new_gemfile
87
+ begin
88
+ save_path = Lapidario::Helper.format_path(@project_path_hash[:project_path], false)
89
+ Lapidario::Helper.save_file(save_path, new_gemfile.join("\n"))
90
+ if @save_backup
91
+ Lapidario::Helper.save_file(save_path + ".original", original_gemfile_lines.join("\n"))
92
+ puts "\n\nSaved backup to #{save_path}.original\n\n"
93
+ end
94
+ rescue => e
95
+ puts "Failed to save file: #{e.message}"
96
+ raise e
97
+ end
98
+ puts "Saved new Gemfile to #{save_path}"
99
+ end
41
100
  end
42
101
  end
43
102
  end
data/lib/gemfile_info.rb CHANGED
@@ -81,7 +81,7 @@ module Lapidario
81
81
  if gi[:current_version] && !gi[:current_version].empty?
82
82
  version_fragment = "#{gi[:current_version]}"
83
83
  version_fragment = "#{gi[:version_sign]} " + version_fragment if gi[:version_sign]
84
- line = line + ", '#{version_fragment}'"
84
+ line = line + ", '#{version_fragment.strip}'"
85
85
  end
86
86
  line = line + ", #{gi[:extra_info]}" if gi[:extra_info] && !gi[:extra_info].empty?
87
87
  line
data/lib/helper.rb CHANGED
@@ -10,6 +10,7 @@ module Lapidario
10
10
  @@DETECT_LOCKFILE_IN_PATH = /\/Gemfile\.lock/
11
11
  # checks 0 or more spaces to the left or 1 or more to the right, also asserting that LOCK is at the end of string
12
12
  @@DETECT_LOCKED_LINE = /\s*LOCK\s*\z/
13
+ @@VERSION_SIGNS = ['~>', '>=', '<=', '>', '<', '']
13
14
 
14
15
  def self.version_fragment?(line_section)
15
16
  line_section.match? @@GEM_VERSION_FRAGMENT
@@ -24,6 +25,11 @@ module Lapidario
24
25
  gemfile_line.match?(/^\s*gem\s+["']([^"']+)["']/)
25
26
  end
26
27
 
28
+ def self.get_version_sign_from_number(version_sign_num)
29
+ raise "Available version signs range from 0 to 5, run `$lapidario --help` for details" if version_sign_num > 5 || version_sign_num < 0
30
+ @@VERSION_SIGNS[version_sign_num]
31
+ end
32
+
27
33
  # formats based on depth; ex: version_fragment = '3.12.4' with depth 2 returns 3.12
28
34
  def self.format_version_based_on_depth(version_fragment, depth = 2)
29
35
  raise Lapidario::Error, "Tried to format #{version_fragment} with inadequate depth '#{depth}'." unless depth >= 1 && depth <= 3
@@ -43,6 +49,7 @@ module Lapidario
43
49
  end
44
50
 
45
51
  def self.save_file(save_path, content)
52
+ content.join("\n") if content.is_a? Array
46
53
  File.write(save_path, content)
47
54
  end
48
55
 
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Lapidario
4
- VERSION = "0.3alpha.0"
4
+ VERSION = "0.3beta.0"
5
5
  end
data/lib/lapidario.rb CHANGED
@@ -64,7 +64,7 @@ module Lapidario
64
64
  if lock_version
65
65
  gem_info[:current_version] = lock_version
66
66
  gem_info[:current_version] = Lapidario::Helper.format_version_based_on_depth(lock_version, default_depth) if default_depth
67
- gem_info[:version_sign] = default_sign if default_sign && !default_sign.empty?
67
+ gem_info[:version_sign] = default_sign
68
68
  end
69
69
  end
70
70
  new_gemfile_info
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: lapidario
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3alpha.0
4
+ version: 0.3beta.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - octehren
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-12-05 00:00:00.000000000 Z
11
+ date: 2023-12-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -39,9 +39,8 @@ dependencies:
39
39
  - !ruby/object:Gem::Version
40
40
  version: '3.12'
41
41
  description: Lapidario is a Gemfile and Gemfile.lock static analyzer that helps with
42
- bulk updates of gems in a project. As of version 0.1, run it in a directory with
43
- both a Gemfile and Gemfile.lock to hard-code the locked versions in Gemfile.lock
44
- to the Gemfile.
42
+ bulk updates and explicit version hard-coding of gems in a project. See https://github.com/octehren/lapidario
43
+ for more.
45
44
  email:
46
45
  - ehren.dev.mail@gmail.com
47
46
  executables:
@@ -68,13 +67,13 @@ files:
68
67
  - lib/lapidario/version.rb
69
68
  - lib/lockfile_info.rb
70
69
  - sig/lapidario.rbs
71
- homepage: https://example.com
70
+ homepage: https://github.com/octehren/lapidario
72
71
  licenses:
73
72
  - MIT
74
73
  metadata:
75
74
  allowed_push_host: https://rubygems.org
76
- homepage_uri: https://example.com
77
- source_code_uri: https://example.com
75
+ homepage_uri: https://github.com/octehren/lapidario
76
+ source_code_uri: https://github.com/octehren/lapidario
78
77
  changelog_uri: https://example.com
79
78
  post_install_message:
80
79
  rdoc_options: []