facter 4.2.0 → 4.2.4

Sign up to get free protection for your applications and to get access to all the features.
Files changed (36) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE +202 -0
  3. data/lib/facter/custom_facts/core/file_loader.rb +0 -1
  4. data/lib/facter/custom_facts/core/legacy_facter.rb +0 -2
  5. data/lib/facter/custom_facts/core/resolvable.rb +1 -1
  6. data/lib/facter/custom_facts/util/collection.rb +6 -4
  7. data/lib/facter/custom_facts/util/confine.rb +9 -3
  8. data/lib/facter/custom_facts/util/directory_loader.rb +18 -6
  9. data/lib/facter/custom_facts/util/fact.rb +12 -10
  10. data/lib/facter/custom_facts/util/loader.rb +7 -3
  11. data/lib/facter/custom_facts/util/parser.rb +8 -2
  12. data/lib/facter/custom_facts/util/resolution.rb +5 -1
  13. data/lib/facter/framework/cli/cli.rb +13 -15
  14. data/lib/facter/framework/core/fact/internal/internal_fact_manager.rb +0 -2
  15. data/lib/facter/framework/core/fact_loaders/fact_loader.rb +0 -1
  16. data/lib/facter/framework/core/fact_manager.rb +11 -0
  17. data/lib/facter/framework/logging/logger.rb +61 -0
  18. data/lib/facter/framework/parsers/query_parser.rb +1 -4
  19. data/lib/facter/resolvers/aix/disks.rb +1 -1
  20. data/lib/facter/resolvers/aix/mountpoints.rb +1 -1
  21. data/lib/facter/resolvers/aix/partitions.rb +1 -1
  22. data/lib/facter/resolvers/ec2.rb +8 -1
  23. data/lib/facter/resolvers/linux/networking.rb +0 -1
  24. data/lib/facter/resolvers/lsb_release.rb +1 -2
  25. data/lib/facter/resolvers/macosx/{processor.rb → processors.rb} +21 -21
  26. data/lib/facter/resolvers/networking.rb +3 -1
  27. data/lib/facter/resolvers/os_release.rb +7 -4
  28. data/lib/facter/resolvers/partitions.rb +1 -3
  29. data/lib/facter/resolvers/windows/ffi/kernel_ffi.rb +1 -1
  30. data/lib/facter/util/aix/info_extractor.rb +60 -9
  31. data/lib/facter/util/linux/dhcp.rb +4 -1
  32. data/lib/facter/util/linux/socket_parser.rb +17 -2
  33. data/lib/facter/version.rb +1 -1
  34. data/lib/facter.rb +12 -18
  35. metadata +25 -5
  36. data/lib/facter/custom_facts/core/logging.rb +0 -203
@@ -137,11 +137,17 @@ module LegacyFacter
137
137
  if LegacyFacter.json?
138
138
  JSON.parse(content)
139
139
  else
140
- LegacyFacter.warnonce "Cannot parse JSON data file #{filename} without the json library."
141
- LegacyFacter.warnonce 'Suggested next step is `gem install json` to install the json library.'
140
+ log.warnonce "Cannot parse JSON data file #{filename} without the json library."
141
+ log.warnonce 'Suggested next step is `gem install json` to install the json library.'
142
142
  nil
143
143
  end
144
144
  end
145
+
146
+ private
147
+
148
+ def log
149
+ @log ||= Facter::Log.new(self)
150
+ end
145
151
  end
146
152
 
147
153
  register(JsonParser) do |filename|
@@ -91,7 +91,7 @@ module Facter
91
91
  msg = "Already evaluated #{@name}"
92
92
  msg << " at #{@last_evaluated}" if msg.is_a? String
93
93
  msg << ', reevaluating anyways'
94
- LegacyFacter.warn msg
94
+ log.warn msg
95
95
  end
96
96
 
97
97
  instance_eval(&block)
@@ -171,6 +171,10 @@ module Facter
171
171
 
172
172
  private
173
173
 
174
+ def log
175
+ @log ||= Facter::Log.new(self)
176
+ end
177
+
174
178
  # If the weights are equal, we consider external facts greater tan custom facts
175
179
  def compare_equal_weights(other)
176
180
  # Other is considered greater because self is custom fact and other is external
@@ -97,6 +97,11 @@ module Facter
97
97
  type: :boolean,
98
98
  desc: 'Resolve facts sequentially'
99
99
 
100
+ class_option :puppet,
101
+ type: :boolean,
102
+ aliases: '-p',
103
+ desc: 'Load the Puppet libraries, thus allowing Facter to load Puppet-specific facts.'
104
+
100
105
  desc '--man', 'Display manual.', hide: true
101
106
  map ['--man'] => :man
102
107
  def man(*args)
@@ -111,6 +116,7 @@ module Facter
111
116
 
112
117
  desc 'query', 'Default method', hide: true
113
118
  def query(*args)
119
+ Facter.puppet_facts if options[:puppet]
114
120
  output, status = Facter.to_user_output(@options, *args)
115
121
  puts output
116
122
 
@@ -126,7 +132,7 @@ module Facter
126
132
  Facter.values(@options, args)
127
133
  end
128
134
 
129
- desc '--version, -v', 'Print the version', hide: true
135
+ desc '--version, -v', 'Print the version'
130
136
  map ['--version', '-v'] => :version
131
137
  def version(*_args)
132
138
  puts Facter::VERSION
@@ -156,19 +162,7 @@ module Facter
156
162
  puts cache_groups
157
163
  end
158
164
 
159
- desc '--puppet, -p', 'Load the Puppet libraries, thus allowing Facter to load Puppet-specific facts.'
160
- map ['--puppet', '-p'] => :puppet
161
- def puppet(*args)
162
- Facter.puppet_facts
163
-
164
- output, status = Facter.to_user_output(@options, *args)
165
- puts output
166
-
167
- status = 1 if Facter::Log.errors?
168
- exit status
169
- end
170
-
171
- desc 'help', 'Help for all arguments'
165
+ desc '--help, -h', 'Help for all arguments'
172
166
  def help(*args)
173
167
  help_string = +''
174
168
  help_string << help_header(args)
@@ -205,7 +199,11 @@ module Facter
205
199
  Cli.commands
206
200
  .select { |_k, command_class| command_class.instance_of?(Thor::Command) }
207
201
  .each do |_k, command|
208
- help_command_options << build_option(command['name'], [], command['description'])
202
+ help_command_options << build_option(
203
+ command['name'],
204
+ [command['usage'].split(',')[1]],
205
+ command['description']
206
+ )
209
207
  end
210
208
 
211
209
  help_command_options
@@ -11,10 +11,8 @@ module Facter
11
11
  def resolve_facts(searched_facts)
12
12
  internal_searched_facts = filter_internal_facts(searched_facts)
13
13
  resolved_facts = if Options[:sequential]
14
- log.debug('Resolving facts sequentially')
15
14
  resolve_sequentially(internal_searched_facts)
16
15
  else
17
- log.debug('Resolving fact in parallel')
18
16
  resolve_in_parallel(internal_searched_facts)
19
17
  end
20
18
 
@@ -29,7 +29,6 @@ module Facter
29
29
  end
30
30
 
31
31
  def load_internal_facts(user_query, options)
32
- @log.debug('Loading internal facts')
33
32
  internal_facts = []
34
33
  if user_query || options[:show_legacy]
35
34
  # if we have a user query, then we must search in core facts and legacy facts
@@ -13,6 +13,7 @@ module Facter
13
13
  end
14
14
 
15
15
  def resolve_facts(user_query = [])
16
+ log_resolving_method
16
17
  @options[:user_query] = user_query
17
18
  cache_manager = Facter::CacheManager.new
18
19
 
@@ -40,6 +41,7 @@ module Facter
40
41
  # - load all the core facts, external facts and env facts
41
42
  # - load all custom facts
42
43
  def resolve_fact(user_query)
44
+ log_resolving_method
43
45
  @options[:user_query] = user_query
44
46
  @log.debug("resolving fact with user_query: #{user_query}")
45
47
 
@@ -58,12 +60,21 @@ module Facter
58
60
  end
59
61
 
60
62
  def resolve_core(user_query = [], options = {})
63
+ log_resolving_method
61
64
  @cache_manager = CacheManager.new
62
65
  core_fact(user_query, options)
63
66
  end
64
67
 
65
68
  private
66
69
 
70
+ def log_resolving_method
71
+ if Options[:sequential]
72
+ @log.debugonce('Resolving facts sequentially')
73
+ else
74
+ @log.debugonce('Resolving fact in parallel')
75
+ end
76
+ end
77
+
67
78
  def core_fact(user_query, options)
68
79
  loaded_facts_hash = @fact_loader.load_internal_facts(user_query, options)
69
80
 
@@ -15,8 +15,16 @@ module Facter
15
15
  @@logger = nil
16
16
  @@message_callback = nil
17
17
  @@has_errors = false
18
+ @@debug_messages = []
19
+ @@warn_messages = []
20
+ @@timing = false
18
21
 
19
22
  class << self
23
+ def clear_messages
24
+ @@debug_messages.clear
25
+ @@warn_messages.clear
26
+ end
27
+
20
28
  def on_message(&block)
21
29
  @@message_callback = block
22
30
  end
@@ -47,6 +55,41 @@ module Facter
47
55
  "[#{datetime}] #{severity} #{msg} \n"
48
56
  end
49
57
  end
58
+
59
+ # Print an exception message, and optionally a backtrace if trace is set
60
+
61
+ # Print timing information
62
+ #
63
+ # @param string [String] the time to print
64
+ # @return [void]
65
+ #
66
+ # @api private
67
+ def show_time(string)
68
+ return unless string && timing?
69
+
70
+ if @@message_callback
71
+ @@message_callback.call(:info, string)
72
+ else
73
+ warn("#{GREEN}#{string}#{RESET}")
74
+ end
75
+ end
76
+
77
+ # Enable or disable logging of timing information
78
+ #
79
+ # @param bool [true, false]
80
+ # @return [void]
81
+ #
82
+ # @api private
83
+ def timing(bool)
84
+ @@timing = bool
85
+ end
86
+
87
+ # Returns whether timing output is turned on
88
+ #
89
+ # @api private
90
+ def timing?
91
+ @@timing
92
+ end
50
93
  end
51
94
 
52
95
  def initialize(logged_class)
@@ -68,6 +111,16 @@ module Facter
68
111
  end
69
112
  end
70
113
 
114
+ def debugonce(msg)
115
+ return unless debugging_active?
116
+
117
+ message_string = msg.to_s
118
+ return if @@debug_messages.include? message_string
119
+
120
+ @@debug_messages << message_string
121
+ debug(message_string)
122
+ end
123
+
71
124
  def info(msg)
72
125
  if msg.nil? || msg.empty?
73
126
  empty_message_error(msg)
@@ -88,6 +141,14 @@ module Facter
88
141
  end
89
142
  end
90
143
 
144
+ def warnonce(message)
145
+ message_string = message.to_s
146
+ return if @@warn_messages.include? message_string
147
+
148
+ @@warn_messages << message_string
149
+ warn(message_string)
150
+ end
151
+
91
152
  def error(msg, colorize = false)
92
153
  @@has_errors = true
93
154
 
@@ -24,13 +24,11 @@ module Facter
24
24
  # Returns a list of SearchedFact objects that resolve the users query.
25
25
  def parse(query_list, loaded_fact)
26
26
  matched_facts = []
27
- @log.debug "User query is: #{query_list}"
28
27
  @query_list = query_list
29
28
 
30
29
  return no_user_query(loaded_fact) unless query_list.any?
31
30
 
32
31
  query_list.each do |query|
33
- @log.debug "Query is #{query}"
34
32
  found_facts = search_for_facts(query, loaded_fact)
35
33
  matched_facts << found_facts
36
34
  end
@@ -65,7 +63,6 @@ module Facter
65
63
  end
66
64
 
67
65
  def get_facts_matching_tokens(query_tokens, query_token_range, loaded_fact_hash)
68
- @log.debug "Checking query tokens #{query_tokens[query_token_range].join('.')}"
69
66
  resolvable_fact_list = []
70
67
 
71
68
  loaded_fact_hash.each do |loaded_fact|
@@ -77,7 +74,7 @@ module Facter
77
74
  resolvable_fact_list << searched_fact
78
75
  end
79
76
 
80
- @log.debug "List of resolvable facts: #{resolvable_fact_list.inspect}"
77
+ @log.debug "List of resolvable facts: #{resolvable_fact_list.inspect}" if resolvable_fact_list.any?
81
78
  resolvable_fact_list
82
79
  end
83
80
 
@@ -34,7 +34,7 @@ module Facter
34
34
 
35
35
  return if stdout.empty?
36
36
 
37
- info_size = Facter::Util::Aix::InfoExtractor.extract(stdout, /PP SIZE:|TOTAL PPs:|FREE PPs:|PV STATE:/)
37
+ info_size = Facter::Util::Aix::InfoExtractor.extract(stdout, :lspv)
38
38
 
39
39
  return unless info_size['PV STATE']
40
40
 
@@ -19,7 +19,7 @@ module Facter
19
19
  @fact_list[:mountpoints] = {}
20
20
  output = Facter::Core::Execution.execute('mount', logger: log)
21
21
  output.split("\n").map do |line|
22
- next if line =~ /node|---|procfs|ahafs/
22
+ next if line =~ /\s+node\s+|---|procfs|ahafs/
23
23
 
24
24
  elem = line.split("\s")
25
25
 
@@ -40,7 +40,7 @@ module Facter
40
40
 
41
41
  return if stdout.empty?
42
42
 
43
- info_hash = Facter::Util::Aix::InfoExtractor.extract(stdout, /PPs:|PP SIZE|TYPE:|LABEL:|MOUNT/)
43
+ info_hash = Facter::Util::Aix::InfoExtractor.extract(stdout, :lslv)
44
44
  size_bytes = compute_size(info_hash)
45
45
 
46
46
  part_info = {
@@ -51,7 +51,7 @@ module Facter
51
51
 
52
52
  def get_data_from(url)
53
53
  headers = {}
54
- headers['X-aws-ec2-metadata-token'] = Facter::Util::Resolvers::AwsToken.get if ENV['AWS_IMDSv2']
54
+ headers['X-aws-ec2-metadata-token'] = v2_token if v2_token
55
55
  Facter::Util::Resolvers::Http.get_request(url, headers, { session: determine_session_timeout })
56
56
  end
57
57
 
@@ -59,6 +59,13 @@ module Facter
59
59
  session_env = ENV['EC2_SESSION_TIMEOUT']
60
60
  session_env ? session_env.to_i : EC2_SESSION_TIMEOUT
61
61
  end
62
+
63
+ def v2_token
64
+ @v2_token ||= begin
65
+ token = Facter::Util::Resolvers::AwsToken.get
66
+ token == '' ? nil : token
67
+ end
68
+ end
62
69
  end
63
70
  end
64
71
  end
@@ -44,7 +44,6 @@ module Facter
44
44
 
45
45
  parse_ip_command_line(line, mtu_and_indexes)
46
46
  end
47
- log.debug("Associated MTU and index in ip command: #{mtu_and_indexes}")
48
47
  mtu_and_indexes
49
48
  end
50
49
 
@@ -25,8 +25,7 @@ module Facter
25
25
  end
26
26
 
27
27
  def lsb_release_installed?
28
- output = Facter::Core::Execution.execute('which lsb_release', logger: log)
29
- @fact_list[:lsb_release_installed] = !output.empty?
28
+ @fact_list[:lsb_release_installed] = !Facter::Core::Execution.which('lsb_release').nil?
30
29
  end
31
30
 
32
31
  def read_lsb_release_file
@@ -29,42 +29,42 @@ module Facter
29
29
 
30
30
  def read_processor_data(fact_name)
31
31
  output = Facter::Core::Execution.execute("sysctl #{ITEMS.values.join(' ')}", logger: log)
32
- build_fact_list(output.split("\n"))
32
+ processors_hash = Hash[*output.split("\n").collect { |v| [v.split(': ')[0], v.split(': ')[1]] }.flatten]
33
+ build_fact_list(processors_hash)
33
34
  @fact_list[fact_name]
34
35
  end
35
36
 
36
- def build_fact_list(processors_data)
37
- build_logical_count(processors_data[0])
38
- build_physical_count(processors_data[1])
39
- build_models(processors_data[2])
40
- build_speed(processors_data[3])
41
- build_cores_per_socket(processors_data[4])
42
- build_threads_per_core(processors_data[5], processors_data[4])
37
+ def build_fact_list(hash)
38
+ build_logical_count(hash)
39
+ build_physical_count(hash)
40
+ build_models(hash)
41
+ build_speed(hash)
42
+ build_cores_per_socket(hash)
43
+ build_threads_per_core(hash)
43
44
  end
44
45
 
45
- def build_logical_count(count)
46
- @fact_list[:logicalcount] = count.split(': ')[1].to_i
46
+ def build_logical_count(hash)
47
+ @fact_list[:logicalcount] = hash[ITEMS[:logical_count]].to_i
47
48
  end
48
49
 
49
- def build_physical_count(count)
50
- @fact_list[:physicalcount] = count.split(': ')[1].to_i
50
+ def build_physical_count(hash)
51
+ @fact_list[:physicalcount] = hash[ITEMS[:physical_count]].to_i
51
52
  end
52
53
 
53
- def build_models(model)
54
- brand = model.split(': ').fetch(1)
55
- @fact_list[:models] = Array.new(@fact_list[:logicalcount].to_i, brand)
54
+ def build_models(hash)
55
+ @fact_list[:models] = Array.new(@fact_list[:logicalcount].to_i, hash[ITEMS[:brand]])
56
56
  end
57
57
 
58
- def build_speed(value)
59
- @fact_list[:speed] = value.split(': ')[1].to_i
58
+ def build_speed(hash)
59
+ @fact_list[:speed] = hash[ITEMS[:speed]].to_i
60
60
  end
61
61
 
62
- def build_cores_per_socket(count)
63
- @fact_list[:cores_per_socket] = count.split(': ')[1].to_i
62
+ def build_cores_per_socket(hash)
63
+ @fact_list[:cores_per_socket] = hash[ITEMS[:cores_per_socket]].to_i
64
64
  end
65
65
 
66
- def build_threads_per_core(number_of_threads, number_of_cores)
67
- @fact_list[:threads_per_core] = number_of_threads.split(': ')[1].to_i / number_of_cores.split(': ')[1].to_i
66
+ def build_threads_per_core(hash)
67
+ @fact_list[:threads_per_core] = hash[ITEMS[:threads_per_core]].to_i / hash[ITEMS[:cores_per_socket]].to_i
68
68
  end
69
69
  end
70
70
  end
@@ -37,7 +37,9 @@ module Facter
37
37
 
38
38
  def clean_up_interfaces_response(response)
39
39
  # convert ip ranges into single ip. eg. 10.16.132.213 --> 10.16.132.213 is converted to 10.16.132.213
40
- response.gsub!(/(\d+(\.\d+)*)\s+-->\s+\d+(\.\d+)*/, '\\1')
40
+ # convert ip6 ranges into single ip. eg. 2001:db8:cafe::132:213 -->
41
+ # 2001:db8:cafe::132:213 is converted to 2001:db8:cafe::132:213
42
+ response.gsub!(/([\da-fA-F]+([\.:]+[\da-fA-F]+)*)\s+-->\s+[\da-fA-F]+([\.:]+[\da-fA-F]+)*/, '\\1')
41
43
  end
42
44
 
43
45
  def parse_interfaces_response(response)
@@ -53,12 +53,15 @@ module Facter
53
53
  end
54
54
 
55
55
  def process_name
56
- return unless @fact_list[:name]
56
+ os_name = @fact_list[:name]
57
+ return unless os_name
57
58
 
58
- @fact_list[:name] = if @fact_list[:name].downcase.start_with?('red', 'oracle')
59
- @fact_list[:name].split(' ')[0..1].join
59
+ @fact_list[:name] = if os_name.downcase.start_with?('red', 'oracle', 'arch', 'manjaro')
60
+ os_name = os_name.split(' ')[0..1].join
61
+ os_name = os_name.capitalize if os_name.downcase.start_with?('arch', 'manjaro')
62
+ os_name
60
63
  else
61
- @fact_list[:name].split(' ')[0].strip
64
+ os_name.split(' ')[0].strip
62
65
  end
63
66
  end
64
67