labrat 1.4.0 → 1.5.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.
data/lib/labrat/config.rb CHANGED
@@ -1,215 +1,11 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ # A thin wrapper around FatConfig.
3
4
  module Labrat
4
- # This class is responsible for finding a config files, reading them, and
5
- # returning a Hash to reflect the configuration. We use YAML as the
6
- # configuration format and look for the config file in the standard places.
7
- class Config
8
- # Return a Hash of the YAML-ized config files for app_name directories.
9
- # Config file may be located in either the xdg locations (containing any
10
- # variant of base: base, base.yml, or base.yaml) or in the classic
11
- # locations (/etc/app_namerc, /etc/app_name, ~/.app_namerc~, or
12
- # ~/.app_name/base[.ya?ml]). Return a hash that reflects the merging of
13
- # those files according to the following priorities, from highest to
14
- # lowest:
15
- #
16
- # 1. A config file pointed to by the environment variable APPNAME_CONFIG
17
- # 2. User classic config files
18
- # 3. User xdg config files for app_name,
19
- # 4. A config file pointed to by the environment variable APPNAME_SYS_CONFIG
20
- # 5. System classic config files,
21
- # 6. System xdg config files for for app_name,
22
- #
23
- # If an environment variable is found, the search for xdg and classic
24
- # config files is skipped. Any dir_prefix is pre-pended to search
25
- # locations environment, xdg and classic config paths so you can run this
26
- # on a temporary directory set up for testing.
5
+ module Config
27
6
  def self.read(app_name, base: 'config', dir_prefix: '', xdg: true, verbose: false)
28
- paths = config_paths(app_name, base: base, dir_prefix: dir_prefix, xdg: xdg)
29
- sys_configs = paths[:system]
30
- usr_configs = paths[:user]
31
- merge_configs_from((sys_configs + usr_configs).compact, verbose: verbose)
32
- end
33
-
34
- def self.config_paths(app_name, base: 'config', dir_prefix: '', xdg: true)
35
- sys_configs = []
36
- sys_env_name = "#{app_name.upcase}_SYS_CONFIG"
37
- if ENV[sys_env_name]
38
- sys_fname = File.join(dir_prefix, File.expand_path(ENV[sys_env_name]))
39
- sys_configs << sys_fname if File.readable?(sys_fname)
40
- else
41
- sys_configs +=
42
- if xdg
43
- find_xdg_sys_config_files(app_name, base, dir_prefix)
44
- else
45
- find_classic_sys_config_files(app_name, base, dir_prefix)
46
- end
47
- end
48
-
49
- usr_configs = []
50
- usr_env_name = "#{app_name.upcase}_CONFIG"
51
- if ENV[usr_env_name]
52
- usr_fname = File.join(dir_prefix, File.expand_path(ENV[usr_env_name]))
53
- usr_configs << usr_fname if File.readable?(usr_fname)
54
- else
55
- usr_configs <<
56
- if xdg
57
- find_xdg_user_config_file(app_name, base, dir_prefix)
58
- else
59
- find_classic_user_config_file(app_name, dir_prefix)
60
- end
61
- end
62
- { system: sys_configs.compact, user: usr_configs.compact }
63
- end
64
-
65
- # Merge the settings from the given Array of config files in order from
66
- # lowest priority to highest priority, starting with an empty hash. Any
67
- # values of the top-level hash that are themselves Hashes are merged
68
- # recursively.
69
- def self.merge_configs_from(files = [], verbose: false)
70
- hash = {}
71
- files.each do |f|
72
- next unless File.readable?(f)
73
-
74
- yml_hash = YAML.load_file(f)
75
- next unless yml_hash
76
-
77
- if yml_hash.is_a?(Hash)
78
- yml_hash = yml_hash
79
- else
80
- raise "Error loading file #{f}:\n#{File.read(f)[0..500]}"
81
- end
82
- yml_hash.report("Merging config from file '#{f}") if verbose
83
- hash.deep_merge!(yml_hash)
84
- end
85
- hash
86
- end
87
-
88
- ########################################################################
89
- # XDG config files
90
- ########################################################################
91
-
92
- # From the XDG standard:
93
- # Your application should store and load data and configuration files to/from
94
- # the directories pointed by the following environment variables:
95
- #
96
- # $XDG_CONFIG_HOME (default: "$HOME/.config"): user-specific configuration files.
97
- # $XDG_CONFIG_DIRS (default: "/etc/xdg"): precedence-ordered set of system configuration directories.
98
-
99
- # Return the absolute path names of all XDG system config files for
100
- # app_name with the basename variants of base. Return the lowest priority
101
- # files first, highest last. Prefix the search locations with dir_prefix
102
- # if given.
103
- def self.find_xdg_sys_config_files(app_name, base, dir_prefix)
104
- configs = []
105
- xdg_search_dirs = ENV['XDG_CONFIG_DIRS']&.split(':')&.reverse || ['/etc/xdg']
106
- xdg_search_dirs.each do |dir|
107
- dir = File.expand_path(File.join(dir, app_name))
108
- dir = File.join(dir_prefix, dir) unless dir_prefix.nil? || dir_prefix.strip.empty?
109
- base = app_name if base.nil? || base.strip.empty?
110
- base_candidates = [
111
- base.to_s,
112
- "#{base}.yml",
113
- "#{base}.yaml",
114
- "#{base}.cfg",
115
- "#{base}.config"
116
- ]
117
- config_fname = base_candidates.find { |b| File.readable?(File.join(dir, b)) }
118
- configs << File.join(dir, config_fname) if config_fname
119
- end
120
- configs
121
- end
122
-
123
- # Return the absolute path name of any XDG user config files for app_name
124
- # with the basename variants of base. The XDG_CONFIG_HOME environment
125
- # variable for the user configs is intended to be the name of a single xdg
126
- # config directory, not a list of colon-separated directories as for the
127
- # system config. Return the name of a config file for this app in
128
- # XDG_CONFIG_HOME (or ~/.config by default). Prefix the search location
129
- # with dir_prefix if given.
130
- def self.find_xdg_user_config_file(app_name, base, dir_prefix)
131
- dir_prefix ||= ''
132
- base ||= base&.strip || app_name
133
- xdg_search_dir = ENV['XDG_CONFIG_HOME'] || ['~/.config']
134
- dir = File.expand_path(File.join(xdg_search_dir, app_name))
135
- dir = File.join(dir_prefix, dir) unless dir_prefix.strip.empty?
136
- return unless Dir.exist?(dir)
137
-
138
- base_candidates = [
139
- base.to_s,
140
- "#{base}.yml",
141
- "#{base}.yaml",
142
- "#{base}.cfg",
143
- "#{base}.config"
144
- ]
145
- config_fname = base_candidates.find { |b| File.readable?(File.join(dir, b)) }
146
- if config_fname
147
- File.join(dir, config_fname)
148
- end
149
- end
150
-
151
- ########################################################################
152
- # Classic config files
153
- ########################################################################
154
-
155
- # Return the absolute path names of all "classic" system config files for
156
- # app_name with the basename variants of base. Return the lowest priority
157
- # files first, highest last. Prefix the search locations with dir_prefix
158
- # if given.
159
- def self.find_classic_sys_config_files(app_name, base, dir_prefix)
160
- dir_prefix ||= ''
161
- configs = []
162
- env_config = ENV["#{app_name.upcase}_SYS_CONFIG"]
163
- if env_config && File.readable?(config = File.join(dir_prefix, File.expand_path(env_config)))
164
- configs = [config]
165
- elsif File.readable?(config = File.join(dir_prefix, "/etc/#{app_name}"))
166
- configs = [config]
167
- elsif File.readable?(config = File.join(dir_prefix, "/etc/#{app_name}rc"))
168
- configs = [config]
169
- else
170
- dir = File.join(dir_prefix, "/etc/#{app_name}")
171
- if Dir.exist?(dir)
172
- base = app_name if base.nil? || base.strip.empty?
173
- base_candidates = [
174
- base.to_s + "#{base}.yml",
175
- "#{base}.yaml",
176
- "#{base}.cfg",
177
- "#{base}.config"
178
- ]
179
- config = base_candidates.find { |b| File.readable?(File.join(dir, b)) }
180
- configs = [File.join(dir, config)] if config
181
- end
182
- end
183
- configs
184
- end
185
-
186
- # Return the absolute path names of all "classic" system config files for
187
- # app_name with the basename variants of base. Return the lowest priority
188
- # files first, highest last. Prefix the search locations with dir_prefix if
189
- # given.
190
- def self.find_classic_user_config_file(app_name, dir_prefix)
191
- dir_prefix ||= ''
192
- config_fname = nil
193
- env_config = ENV["#{app_name.upcase}_CONFIG"]
194
- if env_config && File.readable?(config = File.join(dir_prefix, File.expand_path(env_config)))
195
- config_fname = config
196
- elsif Dir.exist?(config_dir = File.join(dir_prefix, File.expand_path("~/.#{app_name}")))
197
- base_candidates = ["config.yml", "config.yaml", "config"]
198
- base_fname = base_candidates.find { |b| File.readable?(File.join(config_dir, b)) }
199
- config_fname = File.join(config_dir, base_fname)
200
- elsif Dir.exist?(config_dir = File.join(dir_prefix, File.expand_path('~/')))
201
- base_candidates = [
202
- ".#{app_name}",
203
- ".#{app_name}rc",
204
- ".#{app_name}.yml",
205
- ".#{app_name}.yaml",
206
- ".#{app_name}.cfg",
207
- ".#{app_name}.config"
208
- ]
209
- base_fname = base_candidates.find { |b| File.readable?(File.join(config_dir, b)) }
210
- config_fname = File.join(config_dir, base_fname)
211
- end
212
- config_fname
7
+ reader = FatConfig::Reader.new(app_name, xdg:, root_prefix: dir_prefix)
8
+ reader.read(verbose:)
213
9
  end
214
10
  end
215
11
  end
@@ -4,26 +4,26 @@ module Labrat
4
4
  module LabelDb
5
5
  class << self
6
6
  # Module-level variable to hold the merged database.
7
- attr_accessor :db
7
+ attr_accessor :db, :reader
8
8
  end
9
9
 
10
10
  # Read in the Labrat database of label settings, merging system and user
11
11
  # databases.
12
12
  def self.read(dir_prefix: '')
13
- reader = FatConfig::Reader.new('labrat', root_prefix: dir_prefix)
14
- self.db = reader.read('labeldb')
13
+ self.reader = FatConfig::Reader.new('labrat', root_prefix: dir_prefix)
14
+ self.db = reader.read('labeldb').transform_keys(&:downcase)
15
15
  end
16
16
 
17
17
  # Return a hash of config settings for the label named by labname.
18
18
  def self.[](labname)
19
19
  read unless db
20
- db[labname.to_sym] || {}
20
+ db[labname.to_sym] || db[labname.downcase.to_sym] || {}
21
21
  end
22
22
 
23
23
  # Set a runtime configuration for a single labelname.
24
24
  def self.[]=(labname, config = {})
25
25
  read unless db
26
- db[labname.to_sym] = config
26
+ db[labname.to_sym.downcase] = config
27
27
  end
28
28
 
29
29
  # Return an Array of label names.
@@ -37,13 +37,11 @@ module Labrat
37
37
  end
38
38
 
39
39
  def self.system_db_paths(dir_prefix = '')
40
- paths = Config.config_paths('labrat', base: 'labeldb', dir_prefix: dir_prefix)
41
- paths[:system]
40
+ reader.config_paths[:system]
42
41
  end
43
42
 
44
43
  def self.user_db_paths(dir_prefix = '')
45
- paths = Config.config_paths('labrat', base: 'labeldb', dir_prefix: dir_prefix)
46
- paths[:user]
44
+ reader.config_paths[:user]
47
45
  end
48
46
  end
49
47
  end
@@ -1,7 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Labrat
4
- def self.read_label_texts(fname, nlsep)
4
+ def self.read_label_texts(fname, nl_sep)
5
5
  file =
6
6
  if fname
7
7
  ofname = fname
@@ -22,20 +22,20 @@ module Labrat
22
22
 
23
23
  if /\A\s*\z/.match?(line)
24
24
  # At blank line record any accumulated label into texts, but remove
25
- # the nlsep from the end.
25
+ # the nl_sep from the end.
26
26
  if label
27
- texts << label.sub(/#{Regexp.quote(nlsep)}\z/, '')
27
+ texts << label.sub(/#{Regexp.quote(nl_sep)}\z/, '')
28
28
  label = nil
29
29
  end
30
30
  else
31
31
  # Append a non-blank line to the current label, creating it if
32
32
  # necessary.
33
33
  label ||= +''
34
- label << line.chomp + nlsep
34
+ label << line.chomp + nl_sep
35
35
  end
36
36
  end
37
37
  # Last label in the file.
38
- texts << label.sub(/#{Regexp.quote(nlsep)}\z/, '') if label
38
+ texts << label.sub(/#{Regexp.quote(nl_sep)}\z/, '') if label
39
39
  texts
40
40
  end
41
41
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Labrat
4
- VERSION = "1.4.0"
4
+ VERSION = "1.5.0"
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: labrat
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.4.0
4
+ version: 1.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Daniel E. Doherty
@@ -37,20 +37,34 @@ dependencies:
37
37
  - - ">="
38
38
  - !ruby/object:Gem::Version
39
39
  version: 0.4.2
40
+ - !ruby/object:Gem::Dependency
41
+ name: matrix
42
+ requirement: !ruby/object:Gem::Requirement
43
+ requirements:
44
+ - - ">="
45
+ - !ruby/object:Gem::Version
46
+ version: '0'
47
+ type: :runtime
48
+ prerelease: false
49
+ version_requirements: !ruby/object:Gem::Requirement
50
+ requirements:
51
+ - - ">="
52
+ - !ruby/object:Gem::Version
53
+ version: '0'
40
54
  - !ruby/object:Gem::Dependency
41
55
  name: prawn
42
56
  requirement: !ruby/object:Gem::Requirement
43
57
  requirements:
44
- - - "~>"
58
+ - - "<="
45
59
  - !ruby/object:Gem::Version
46
- version: '2.0'
60
+ version: '2.5'
47
61
  type: :runtime
48
62
  prerelease: false
49
63
  version_requirements: !ruby/object:Gem::Requirement
50
64
  requirements:
51
- - - "~>"
65
+ - - "<="
52
66
  - !ruby/object:Gem::Version
53
- version: '2.0'
67
+ version: '2.5'
54
68
  description: |2+
55
69
 
56
70
  Labrat is a linux command-line program for quickly printing labels. Labrat uses
@@ -146,7 +160,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
146
160
  - !ruby/object:Gem::Version
147
161
  version: '0'
148
162
  requirements: []
149
- rubygems_version: 4.0.3
163
+ rubygems_version: 4.0.0
150
164
  specification_version: 4
151
165
  summary: Command-line and Emacs label print software.
152
166
  test_files: []