gem_hadar 2.10.0 → 2.11.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 +4 -4
- data/.all_images.yml +1 -1
- data/Rakefile +2 -1
- data/gem_hadar.gemspec +6 -5
- data/lib/gem_hadar/changelog_generator.rb +292 -0
- data/lib/gem_hadar/github.rb +1 -2
- data/lib/gem_hadar/ollama_support.rb +72 -0
- data/lib/gem_hadar/prompt_template.rb +46 -0
- data/lib/gem_hadar/rvm_config.rb +0 -3
- data/lib/gem_hadar/utils.rb +81 -41
- data/lib/gem_hadar/version.rb +1 -1
- data/lib/gem_hadar/version_spec.rb +144 -0
- data/lib/gem_hadar/warn.rb +0 -2
- data/lib/gem_hadar.rb +183 -120
- metadata +23 -3
data/lib/gem_hadar/utils.rb
CHANGED
|
@@ -1,67 +1,107 @@
|
|
|
1
1
|
require 'pathname'
|
|
2
2
|
|
|
3
|
-
# A module that provides utility methods for
|
|
4
|
-
# specification compliance.
|
|
3
|
+
# A module that provides utility methods for GemHadar
|
|
5
4
|
#
|
|
6
|
-
# This module
|
|
7
|
-
#
|
|
8
|
-
#
|
|
9
|
-
#
|
|
10
|
-
#
|
|
11
|
-
#
|
|
12
|
-
# @example Determining the XDG configuration directory
|
|
13
|
-
# config_dir = GemHadar::Utils.xdg_config_home
|
|
14
|
-
#
|
|
15
|
-
# @example Retrieving configuration file contents
|
|
16
|
-
# config_content = GemHadar::Utils.xdg_config('myapp', 'default_value')
|
|
5
|
+
# This module contains helper methods for common operations within the GemHadar
|
|
6
|
+
# framework, including XDG configuration directory handling, user input
|
|
7
|
+
# prompts, and memoization capabilities. It serves as a collection of reusable
|
|
8
|
+
# utilities that support various aspects of gem automation and configuration
|
|
9
|
+
# management.
|
|
17
10
|
module GemHadar::Utils
|
|
18
|
-
# The xdg_config_home method determines the
|
|
19
|
-
# directory.
|
|
11
|
+
# The xdg_config_home method determines the XDG configuration directory path.
|
|
20
12
|
#
|
|
21
|
-
#
|
|
22
|
-
#
|
|
23
|
-
# XDG_CONFIG_HOME
|
|
24
|
-
# variable
|
|
13
|
+
# This method returns the path to the XDG configuration directory, which is used
|
|
14
|
+
# to store user-specific configuration files for applications. It first checks
|
|
15
|
+
# the XDG_CONFIG_HOME environment variable and returns its value if set.
|
|
16
|
+
# If the environment variable is not set, it falls back to the default
|
|
17
|
+
# configuration directory within the user's home directory, typically
|
|
18
|
+
# ~/.config.
|
|
25
19
|
#
|
|
26
|
-
# @return [ Pathname ] the Pathname object representing the XDG configuration
|
|
20
|
+
# @return [ Pathname ] the Pathname object representing the XDG configuration
|
|
21
|
+
# directory path
|
|
27
22
|
def xdg_config_home
|
|
28
23
|
ENV['XDG_CONFIG_HOME'].full? { Pathname.new(_1) } ||
|
|
29
24
|
Pathname.new(ENV.fetch('HOME')) + '.config'
|
|
30
25
|
end
|
|
31
26
|
|
|
27
|
+
# The xdg_config_dir method constructs the path to the XDG configuration
|
|
28
|
+
# directory for a specific application.
|
|
29
|
+
#
|
|
30
|
+
# This method takes an application name and returns the full path to the
|
|
31
|
+
# configuration directory for that application within the XDG configuration
|
|
32
|
+
# home directory.
|
|
33
|
+
#
|
|
34
|
+
# @param app [ String ] the name of the application to get the configuration
|
|
35
|
+
# directory for
|
|
36
|
+
#
|
|
37
|
+
# @return [ Pathname ] the Pathname object representing the application's
|
|
38
|
+
# configuration directory path
|
|
39
|
+
def xdg_config_dir(app)
|
|
40
|
+
xdg_config_home + app
|
|
41
|
+
end
|
|
42
|
+
|
|
32
43
|
# The xdg_config_filename method constructs the full path to a configuration
|
|
33
|
-
# file
|
|
44
|
+
# file within the XDG configuration directory for a specific application.
|
|
34
45
|
#
|
|
35
|
-
#
|
|
36
|
-
#
|
|
37
|
-
#
|
|
38
|
-
# defaults to using the HOME environment variable to construct the path
|
|
39
|
-
# within the standard .config directory.
|
|
46
|
+
# This method takes an application name and a filename, then combines them
|
|
47
|
+
# with the XDG configuration directory path to create the full path to a
|
|
48
|
+
# configuration file.
|
|
40
49
|
#
|
|
50
|
+
# @param app [ String ] the name of the application to get the configuration
|
|
51
|
+
# directory for
|
|
41
52
|
# @param name [ String ] the name of the configuration file
|
|
42
53
|
#
|
|
43
|
-
# @return [
|
|
44
|
-
|
|
45
|
-
|
|
54
|
+
# @return [ Pathname ] the Pathname object representing the full path to the
|
|
55
|
+
# configuration file
|
|
56
|
+
def xdg_config_filename(app, name)
|
|
57
|
+
xdg_config_dir(app) + name
|
|
46
58
|
end
|
|
47
59
|
|
|
48
|
-
|
|
49
|
-
#
|
|
50
|
-
# the XDG Base Directory specification.
|
|
60
|
+
# The xdg_config method retrieves configuration content from XDG
|
|
61
|
+
# configuration directories
|
|
51
62
|
#
|
|
52
|
-
#
|
|
53
|
-
#
|
|
54
|
-
#
|
|
63
|
+
# This method checks for the existence of a configuration file within the XDG
|
|
64
|
+
# configuration directory structure for the specified application. If the
|
|
65
|
+
# file exists, it reads and returns the file's content. If the file does not
|
|
66
|
+
# exist, it returns the provided default value instead.
|
|
55
67
|
#
|
|
56
|
-
# @param
|
|
57
|
-
#
|
|
68
|
+
# @param app [ String ] the name of the application to get the configuration
|
|
69
|
+
# directory for
|
|
70
|
+
# @param name [ String ] the name of the configuration file
|
|
71
|
+
# @param default [ String ] the default value to return if the configuration
|
|
72
|
+
# file does not exist
|
|
58
73
|
#
|
|
59
|
-
# @return [ String ] the content of the configuration file or the default
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
74
|
+
# @return [ String ] the content of the configuration file or the default
|
|
75
|
+
# value if the file does not exist
|
|
76
|
+
def xdg_config(app, name, default)
|
|
77
|
+
if xdg_config_filename(app, name).exist?
|
|
78
|
+
File.read(xdg_config_filename(app, name))
|
|
63
79
|
else
|
|
64
80
|
default
|
|
65
81
|
end
|
|
66
82
|
end
|
|
83
|
+
memoize method: :xdg_config
|
|
84
|
+
|
|
85
|
+
# The ask? method prompts the user with a message and reads their input It
|
|
86
|
+
# returns a MatchData object if the input matches the provided pattern.
|
|
87
|
+
#
|
|
88
|
+
# @param prompt [ String ] the message to display to the user
|
|
89
|
+
# @param pattern [ Regexp ] the regular expression to match against the input
|
|
90
|
+
#
|
|
91
|
+
# @return [ MatchData, nil ] the result of the pattern match or nil if no match
|
|
92
|
+
def ask?(prompt, pattern, default: nil)
|
|
93
|
+
if prompt.include?('%{default}')
|
|
94
|
+
if default.present?
|
|
95
|
+
prompt = prompt % { default: ", default is #{default.inspect}" }
|
|
96
|
+
else
|
|
97
|
+
prompt = prompt % { default: '' }
|
|
98
|
+
end
|
|
99
|
+
end
|
|
100
|
+
STDOUT.print prompt
|
|
101
|
+
answer = STDIN.gets.chomp
|
|
102
|
+
default.present? && answer.blank? and answer = default
|
|
103
|
+
if answer =~ pattern
|
|
104
|
+
$~
|
|
105
|
+
end
|
|
106
|
+
end
|
|
67
107
|
end
|
data/lib/gem_hadar/version.rb
CHANGED
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
# A class that represents a version specification for a gem.
|
|
2
|
+
#
|
|
3
|
+
# This class provides functionality to parse and manipulate version strings,
|
|
4
|
+
# including handling of semantic versioning formats and optional 'v' prefixes.
|
|
5
|
+
# It supports creating version specifications from various input formats and
|
|
6
|
+
# provides methods to access the underlying version information and string
|
|
7
|
+
# representation.
|
|
8
|
+
#
|
|
9
|
+
# @example Creating a version specification
|
|
10
|
+
# version_spec = GemHadar::VersionSpec['1.2.3']
|
|
11
|
+
#
|
|
12
|
+
# @example Checking if a version is a HEAD reference
|
|
13
|
+
# version_spec = GemHadar::VersionSpec['HEAD']
|
|
14
|
+
# version_spec.head? # => true
|
|
15
|
+
#
|
|
16
|
+
# @example Getting the version tag with appropriate prefixing
|
|
17
|
+
# version_spec = GemHadar::VersionSpec['1.2.3']
|
|
18
|
+
# version_spec.tag # => 'v1.2.3'
|
|
19
|
+
#
|
|
20
|
+
# @example Comparing versions
|
|
21
|
+
# version1 = GemHadar::VersionSpec['1.2.3']
|
|
22
|
+
# version2 = GemHadar::VersionSpec['1.2.4']
|
|
23
|
+
# version1.version < version2.version # => true
|
|
24
|
+
class GemHadar::VersionSpec
|
|
25
|
+
class << self
|
|
26
|
+
# The [] method creates a new VersionSpec instance from a specification.
|
|
27
|
+
#
|
|
28
|
+
# This factory method attempts to extract version information from the
|
|
29
|
+
# provided specification, handling both gem specifications and version
|
|
30
|
+
# strings. It supports optional prefix handling for the resulting version
|
|
31
|
+
# string.
|
|
32
|
+
#
|
|
33
|
+
# @param spec [Object] the specification to parse, typically a String or Gem::Specification
|
|
34
|
+
#
|
|
35
|
+
# @param with_prefix [Boolean] if true, ensures the version string has a 'v' prefix
|
|
36
|
+
#
|
|
37
|
+
# @param without_prefix [Boolean] if true, ensures the version string does not have a 'v' prefix
|
|
38
|
+
#
|
|
39
|
+
# @return [GemHadar::VersionSpec] a new VersionSpec instance
|
|
40
|
+
#
|
|
41
|
+
# @raise [ArgumentError] if both with_prefix and without_prefix are specified simultaneously
|
|
42
|
+
def [](spec, with_prefix: nil, without_prefix: nil)
|
|
43
|
+
!(with_prefix && without_prefix) or
|
|
44
|
+
raise ArgumentError, 'with_prefix and without_prefix is invalid'
|
|
45
|
+
spec.is_a?(self) and return spec
|
|
46
|
+
obj, version = nil, (spec.version rescue nil)
|
|
47
|
+
if version
|
|
48
|
+
;
|
|
49
|
+
elsif /\Av?(\d+\.\d+\.\d+)\z/ =~ spec
|
|
50
|
+
begin
|
|
51
|
+
version = Tins::StringVersion::Version.new($1)
|
|
52
|
+
rescue ArgumentError
|
|
53
|
+
end
|
|
54
|
+
end
|
|
55
|
+
spec = spec.to_s
|
|
56
|
+
if version
|
|
57
|
+
if with_prefix
|
|
58
|
+
spec = spec.sub(/\A(?!v)/, 'v')
|
|
59
|
+
elsif without_prefix
|
|
60
|
+
spec = spec.sub(/\Av?/, '')
|
|
61
|
+
end
|
|
62
|
+
end
|
|
63
|
+
obj = new(spec, version)
|
|
64
|
+
obj.freeze
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
private_class_method :new
|
|
68
|
+
end
|
|
69
|
+
|
|
70
|
+
# Initializes a new VersionSpec instance.
|
|
71
|
+
#
|
|
72
|
+
# @param string [String] the original string representation of the version
|
|
73
|
+
# @param version [Tins::StringVersion::Version, nil] the parsed version object or nil if parsing failed
|
|
74
|
+
def initialize(string, version)
|
|
75
|
+
@string, @version = string, version
|
|
76
|
+
end
|
|
77
|
+
|
|
78
|
+
# Retrieves the parsed version object.
|
|
79
|
+
#
|
|
80
|
+
# @return [Tins::StringVersion::Version, nil] the parsed version object or nil if parsing failed
|
|
81
|
+
attr_reader :version
|
|
82
|
+
|
|
83
|
+
# Checks if a version object was successfully parsed.
|
|
84
|
+
#
|
|
85
|
+
# @return [Boolean] true if version was parsed successfully, false otherwise
|
|
86
|
+
def version?
|
|
87
|
+
!!@version
|
|
88
|
+
end
|
|
89
|
+
|
|
90
|
+
# The head? method checks if the version string represents a HEAD reference.
|
|
91
|
+
#
|
|
92
|
+
# This method returns true if the internal string representation of the version
|
|
93
|
+
# spec is exactly 'HEAD', indicating that it refers to the latest commit
|
|
94
|
+
# rather than a specific tagged version.
|
|
95
|
+
#
|
|
96
|
+
# @return [ Boolean ] true if the version string is 'HEAD', false otherwise
|
|
97
|
+
def head?
|
|
98
|
+
@string == 'HEAD'
|
|
99
|
+
end
|
|
100
|
+
|
|
101
|
+
# The tag method returns the version tag string with appropriate prefixing.
|
|
102
|
+
#
|
|
103
|
+
# This method checks if the version represents a HEAD reference and returns
|
|
104
|
+
# the raw string representation if so. Otherwise, it returns the version
|
|
105
|
+
# string with a 'v' prefix added to it.
|
|
106
|
+
#
|
|
107
|
+
# @return [ String ] the version tag string, either as-is for HEAD or with 'v' prefix added
|
|
108
|
+
def tag
|
|
109
|
+
head? ? to_s : with_prefix
|
|
110
|
+
end
|
|
111
|
+
|
|
112
|
+
# The untag method returns the version string without a 'v' prefix.
|
|
113
|
+
#
|
|
114
|
+
# This method checks if the version represents a HEAD reference and returns
|
|
115
|
+
# the raw string representation if so. Otherwise, it returns the version
|
|
116
|
+
# string with the 'v' prefix removed.
|
|
117
|
+
#
|
|
118
|
+
# @return [ String ] the version string without 'v' prefix or the raw string
|
|
119
|
+
# if it represents a HEAD reference
|
|
120
|
+
def untag
|
|
121
|
+
head? ? to_s : without_prefix
|
|
122
|
+
end
|
|
123
|
+
|
|
124
|
+
# Returns the original string representation.
|
|
125
|
+
#
|
|
126
|
+
# @return [String] the original version string
|
|
127
|
+
def to_s
|
|
128
|
+
@string.to_s
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
# Removes the 'v' prefix from the version string if present.
|
|
132
|
+
#
|
|
133
|
+
# @return [String] the version string without 'v' prefix
|
|
134
|
+
def without_prefix
|
|
135
|
+
to_s.sub(/\Av/, '')
|
|
136
|
+
end
|
|
137
|
+
|
|
138
|
+
# Adds a 'v' prefix to the version string if not already present.
|
|
139
|
+
#
|
|
140
|
+
# @return [String] the version string with 'v' prefix
|
|
141
|
+
def with_prefix
|
|
142
|
+
to_s.sub(/\A(?!v)/, 'v')
|
|
143
|
+
end
|
|
144
|
+
end
|
data/lib/gem_hadar/warn.rb
CHANGED
|
@@ -43,8 +43,6 @@ class GemHadar
|
|
|
43
43
|
# within this method itself.
|
|
44
44
|
#
|
|
45
45
|
# @param msgs [ Array<Object> ] the array of message objects to display as failures
|
|
46
|
-
#
|
|
47
|
-
# @return [ void ]
|
|
48
46
|
def fail(*msgs)
|
|
49
47
|
msgs.map! do |a|
|
|
50
48
|
a.respond_to?(:to_str) ? color(196) { a.to_str } : a
|