faker 2.20.0 → 2.23.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 (51) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +123 -0
  3. data/README.md +5 -6
  4. data/lib/faker/blockchain/aeternity.rb +1 -1
  5. data/lib/faker/blockchain/ethereum.rb +1 -1
  6. data/lib/faker/blockchain/tezos.rb +1 -1
  7. data/lib/faker/default/{faker_adjective.rb → adjective.rb} +0 -0
  8. data/lib/faker/default/bank.rb +4 -4
  9. data/lib/faker/default/chile_rut.rb +8 -4
  10. data/lib/faker/default/code.rb +7 -7
  11. data/lib/faker/default/company.rb +4 -4
  12. data/lib/faker/default/file.rb +3 -3
  13. data/lib/faker/default/finance.rb +16 -2
  14. data/lib/faker/default/id_number.rb +106 -1
  15. data/lib/faker/default/internet.rb +24 -3
  16. data/lib/faker/default/markdown.rb +5 -5
  17. data/lib/faker/default/nhs.rb +1 -1
  18. data/lib/faker/default/vehicle.rb +18 -5
  19. data/lib/faker/default/vulnerability_identifier.rb +23 -0
  20. data/lib/faker/japanese_media/kamen_rider.rb +2 -2
  21. data/lib/faker/japanese_media/one_piece.rb +1 -1
  22. data/lib/faker/movies/tron.rb +161 -0
  23. data/lib/faker/sports/mountaineering.rb +22 -0
  24. data/lib/faker/sports/sport.rb +110 -0
  25. data/lib/faker/version.rb +1 -1
  26. data/lib/faker.rb +15 -10
  27. data/lib/helpers/base58.rb +1 -1
  28. data/lib/helpers/unique_generator.rb +13 -11
  29. data/lib/locales/en/australia.yml +3 -4
  30. data/lib/locales/en/computer.yml +23 -4
  31. data/lib/locales/en/dota.yml +113 -0
  32. data/lib/locales/en/file.yml +9 -1
  33. data/lib/locales/en/finance.yml +3 -1
  34. data/lib/locales/en/game.yml +0 -1
  35. data/lib/locales/en/internet.yml +29 -0
  36. data/lib/locales/en/mountaineering.yml +14 -0
  37. data/lib/locales/en/movie.yml +2 -1
  38. data/lib/locales/en/naruto.yml +2 -3
  39. data/lib/locales/en/one_piece.yml +1 -1
  40. data/lib/locales/en/sport.yml +121 -0
  41. data/lib/locales/en/tron.yml +227 -0
  42. data/lib/locales/en/vehicle.yml +2809 -75
  43. data/lib/locales/en-AU.yml +1 -1
  44. data/lib/locales/fr/adjective.yml +266 -0
  45. data/lib/locales/ja/adjective.yml +148 -0
  46. data/lib/locales/ja/dog.yml +1 -0
  47. data/lib/locales/ja/emotion.yml +51 -0
  48. data/lib/locales/ja/naruto.yml +230 -0
  49. data/lib/locales/ja/relationship.yml +10 -0
  50. data/lib/locales/pl.yml +1 -1
  51. metadata +26 -14
@@ -21,7 +21,7 @@ module Faker
21
21
  .chars
22
22
  .insert(3, ' ')
23
23
  .insert(7, ' ')
24
- .join('')
24
+ .join
25
25
  end
26
26
 
27
27
  ##
@@ -9,7 +9,7 @@ module Faker
9
9
  VIN_LETTERS = 'ABCDEFGHJKLMNPRSTUVWXYZ'
10
10
  VIN_MAP = '0123456789X'
11
11
  VIN_WEIGHTS = '8765432X098765432'
12
- VIN_REGEX = /^[A-Z0-9]{3}[A-Z0-9]{5}[A-Z0-9]{1}[A-Z0-9]{1}[A-Z0-0]{1}[A-Z0-9]{1}\d{5}$/.freeze
12
+ VIN_REGEX = /^([A-HJ-NPR-Z0-9]){3}[A-HJ-NPR-Z0-9]{5}[A-HJ-NPR-Z0-9]{1}[A-HJ-NPR-Z0-9]{1}[A-HJ-NPR-Z0-]{1}[A-HJ-NPR-Z0-9]{1}\d{5}$/.freeze
13
13
  SG_CHECKSUM_WEIGHTS = [3, 14, 2, 12, 2, 11, 1].freeze
14
14
  SG_CHECKSUM_CHARS = 'AYUSPLJGDBZXTRMKHEC'
15
15
 
@@ -297,6 +297,19 @@ module Faker
297
297
  "#{plate_number}#{singapore_checksum(plate_number)}"
298
298
  end
299
299
 
300
+ ##
301
+ # Produces a car version
302
+ #
303
+ # @return [String]
304
+ #
305
+ # @example
306
+ # Faker::Vehicle.version #=> "40 TFSI Premium"
307
+ #
308
+ # @faker.version next
309
+ def version
310
+ fetch('vehicle.version')
311
+ end
312
+
300
313
  private
301
314
 
302
315
  def first_eight(number)
@@ -320,7 +333,7 @@ module Faker
320
333
  end
321
334
 
322
335
  def vin_char_to_number(char)
323
- index = VIN_LETTERS.split('').index(char)
336
+ index = VIN_LETTERS.chars.index(char)
324
337
 
325
338
  return char.to_i if index.nil?
326
339
 
@@ -328,14 +341,14 @@ module Faker
328
341
  end
329
342
 
330
343
  def singapore_checksum(plate_number)
331
- padded_alphabets = format('%3s', plate_number[/^[A-Z]+/]).tr(' ', '-').split('')
332
- padded_digits = format('%04d', plate_number[/\d+/]).split('').map(&:to_i)
344
+ padded_alphabets = format('%3s', plate_number[/^[A-Z]+/]).tr(' ', '-').chars
345
+ padded_digits = format('%04d', plate_number[/\d+/]).chars.map(&:to_i)
333
346
  sum = [*padded_alphabets, *padded_digits].each_with_index.reduce(0) do |memo, (char, i)|
334
347
  value = char.is_a?(Integer) ? char : char.ord - 64
335
348
  memo + (SG_CHECKSUM_WEIGHTS[i] * value)
336
349
  end
337
350
 
338
- SG_CHECKSUM_CHARS.split('')[sum % 19]
351
+ SG_CHECKSUM_CHARS.chars[sum % 19]
339
352
  end
340
353
  end
341
354
  end
@@ -0,0 +1,23 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Faker
4
+ class VulnerabilityIdentifier < Base
5
+ class << self
6
+ ##
7
+ # Produces a Common Vulnerabilities and Exposures (CVE) identifier.
8
+ #
9
+ # @param year [Integer] The year-part of the CVE identifier (defaults to the current year)
10
+ # @return [String]
11
+ #
12
+ # @example
13
+ # Faker::VulnerabilityIdentifier.cve #=> "CVE-2021-1337"
14
+ # Faker::VulnerabilityIdentifier.cve(year: 1999) #=> "CVE-1999-0523"
15
+ #
16
+ # @faker.version next
17
+ def cve(year: ::Date.today.year)
18
+ index = rand_in_range(1, 99_999).to_s.rjust(4, '0')
19
+ "CVE-#{year}-#{index}"
20
+ end
21
+ end
22
+ end
23
+ end
@@ -83,14 +83,14 @@ module Faker
83
83
  end
84
84
 
85
85
  def from_eras(*input_eras, field:)
86
- selected_eras = (ERAS & input_eras).yield_self do |selected|
86
+ selected_eras = (ERAS & input_eras).then do |selected|
87
87
  selected.empty? ? eras : selected
88
88
  end.dup
89
89
  yield(selected_eras) if block_given?
90
90
 
91
91
  raise UnavailableInEra, "#{field} is unavailable in the selected eras." if selected_eras.empty?
92
92
 
93
- selected_eras.sample.yield_self do |era|
93
+ selected_eras.sample.then do |era|
94
94
  fetch("kamen_rider.#{era}.#{field}")
95
95
  end
96
96
  end
@@ -79,7 +79,7 @@ module Faker
79
79
  #
80
80
  # @faker.version 1.8.5
81
81
  def akuma_no_mi
82
- fetch('one_piece.akumas_no_mi')
82
+ fetch('one_piece.akuma_no_mi')
83
83
  end
84
84
  end
85
85
  end
@@ -0,0 +1,161 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Faker
4
+ class Movies
5
+ class Tron < Base
6
+ class << self
7
+ ##
8
+ # Produces a character from Tron.
9
+ #
10
+ # @return [String]
11
+ #
12
+ # @example
13
+ # Faker::Movies::Tron.character #=> "Bit"
14
+ #
15
+ # @faker.version next
16
+ def character
17
+ sample(characters)
18
+ end
19
+
20
+ ##
21
+ # Produces a game from Tron.
22
+ #
23
+ # @return [String]
24
+ #
25
+ # @example
26
+ # Faker::Movies::Tron.game #=> "Space Paranoids"
27
+ #
28
+ # @faker.version next
29
+ def game
30
+ sample(games)
31
+ end
32
+
33
+ ##
34
+ # Produces a location from Tron.
35
+ #
36
+ # @return [String]
37
+ #
38
+ # @example
39
+ # Faker::Movies::Tron.location #=> "Flynn's Arcade"
40
+ #
41
+ # @faker.version next
42
+ def location
43
+ sample(locations)
44
+ end
45
+
46
+ ##
47
+ # Produces a program from Tron.
48
+ #
49
+ # @return [String]
50
+ #
51
+ # @example
52
+ # Faker::Movies::Tron.program #=> "Clu"
53
+ #
54
+ # @faker.version next
55
+ def program
56
+ sample(programs)
57
+ end
58
+
59
+ ##
60
+ # Produces a quote from Tron.
61
+ #
62
+ # @param character [String] The name of a character to derive a quote from.
63
+ # @return [String]
64
+ #
65
+ # @example
66
+ # Faker::Movies::Tron.quote #=> "Greetings, Programs!"
67
+ #
68
+ # @example
69
+ # Faker::Movies::Tron.quote(character: "mcp")
70
+ # #=> "End of Line."
71
+ #
72
+ # @faker.version next
73
+ def quote(character: nil)
74
+ quoted_characters = translate('faker.tron.quotes')
75
+
76
+ if character.nil?
77
+ character = sample(quoted_characters.keys).to_s
78
+ else
79
+ character = character.to_s.downcase
80
+
81
+ # check alternate spellings, nicknames, titles of characters
82
+ translate('faker.tron.alternate_character_spellings').each do |k, v|
83
+ character = k.to_s if v.include?(character)
84
+ end
85
+
86
+ raise ArgumentError, "Character for quotes can be left blank or #{quoted_characters.keys.join(', ')}" unless quoted_characters.key?(character.to_sym)
87
+ end
88
+
89
+ fetch("tron.quotes.#{character}")
90
+ end
91
+
92
+ ##
93
+ # Produces a tagline from Tron.
94
+ #
95
+ # @return [String]
96
+ #
97
+ # @example
98
+ # Faker::Movies::Tron.tagline #=> "The Electronic Gladiator"
99
+ #
100
+ # @faker.version next
101
+ def tagline
102
+ sample(taglines)
103
+ end
104
+
105
+ ##
106
+ # Produces a user from Tron.
107
+ #
108
+ # @return [String]
109
+ #
110
+ # @example
111
+ # Faker::Movies::Tron.user #=> "Light Cycle"
112
+ #
113
+ # @faker.version next
114
+ def user
115
+ sample(users)
116
+ end
117
+
118
+ ##
119
+ # Produces a vehicle from Tron.
120
+ #
121
+ # @return [String]
122
+ #
123
+ # @example
124
+ # Faker::Movies::Tron.vehicle #=> "Light Cycle"
125
+ #
126
+ # @faker.version next
127
+ def vehicle
128
+ sample(vehicles)
129
+ end
130
+
131
+ def characters
132
+ translate('faker.tron.characters').values.flatten
133
+ end
134
+
135
+ def games
136
+ fetch_all('tron.games')
137
+ end
138
+
139
+ def locations
140
+ fetch_all('tron.locations')
141
+ end
142
+
143
+ def programs
144
+ fetch_all('tron.characters.programs')
145
+ end
146
+
147
+ def taglines
148
+ fetch_all('tron.taglines')
149
+ end
150
+
151
+ def users
152
+ fetch_all('tron.characters.users')
153
+ end
154
+
155
+ def vehicles
156
+ fetch_all('tron.vehicles')
157
+ end
158
+ end
159
+ end
160
+ end
161
+ end
@@ -0,0 +1,22 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Faker
4
+ class Sports
5
+ class Mountaineering < Base
6
+ class << self
7
+ ##
8
+ # Produces the name of a Mountaineer.
9
+ #
10
+ # @return [String]
11
+ #
12
+ # @example
13
+ # Faker::Sports::Mountaineering.mountaineer #=> "Junko Tabei"
14
+ #
15
+ # @faker.version next
16
+ def mountaineer
17
+ fetch('mountaineering.mountaineer')
18
+ end
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,110 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Faker
4
+ class Sport < Base
5
+ class << self
6
+ ##
7
+ # Produces a sport from the modern olympics or paralympics, summer or winter.
8
+ #
9
+ # @param include_ancient [Boolean] If true, may produce a sport from the ancient olympics
10
+ # @param include_unusual [Boolean] If true, may produce an unusual (definitely not olympic) sport
11
+ #
12
+ # @return [String]
13
+ #
14
+ # @example
15
+ # Faker::Sport.sport #=> "Football"
16
+ # @example
17
+ # Faker::Sport.sport(include_ancient: true) #=> "Chariot racing"
18
+ # @example
19
+ # Faker::Sport.sport(include_unsual: true) #=> "Flugtag/Birdman"
20
+ # @example
21
+ # Faker::Sport.sport(include_ancient:true, include_unusual: true) #=> "Water polo"
22
+ #
23
+ # @faker.version next
24
+ def sport(include_ancient: false, include_unusual: false)
25
+ sports = fetch_all('sport.summer_olympics') + fetch_all('sport.winter_olympics') + fetch_all('sport.summer_paralympics') + fetch_all('sport.winter_paralympics')
26
+ sports << fetch_all('sport.ancient_olympics') if include_ancient
27
+ sports << fetch_all('sport.unusual') if include_unusual
28
+ sample(sports)
29
+ end
30
+
31
+ ##
32
+ # Produces a sport from the summer olympics.
33
+ #
34
+ # @return [String]
35
+ #
36
+ # @example
37
+ # Faker::Sport.summer_olympics_sport #=> "Archery"
38
+ #
39
+ # @faker.version next
40
+ def summer_olympics_sport
41
+ fetch('sport.summer_olympics')
42
+ end
43
+
44
+ ##
45
+ # Produces a sport from the winter olympics.
46
+ #
47
+ # @return [String]
48
+ #
49
+ # @example
50
+ # Faker::Sport.winter_olympics_sport #=> "Bobsleigh"
51
+ #
52
+ # @faker.version next
53
+ def winter_olympics_sport
54
+ fetch('sport.winter_olympics')
55
+ end
56
+
57
+ ##
58
+ # Produces a sport from the summer paralympics.
59
+ #
60
+ # @return [String]
61
+ #
62
+ # @example
63
+ # Faker::Sport.summer_paralympics_sport #=> "Wheelchair Basketball"
64
+ #
65
+ # @faker.version next
66
+ def summer_paralympics_sport
67
+ fetch('sport.summer_paralympics')
68
+ end
69
+
70
+ ##
71
+ # Produces a sport from the winter paralympics.
72
+ #
73
+ # @return [String]
74
+ #
75
+ # @example
76
+ # Faker::Sport.winter_paralympics_sport #=> "Para Ice Hockey"
77
+ #
78
+ # @faker.version next
79
+ def winter_paralympics_sport
80
+ fetch('sport.winter_paralympics')
81
+ end
82
+
83
+ ##
84
+ # Produces an unusual sport.
85
+ #
86
+ # @return [String]
87
+ #
88
+ # @example
89
+ # Faker::Sport.unusual_sport #=> "Camel Jumping"
90
+ #
91
+ # @faker.version next
92
+ def unusual_sport
93
+ fetch('sport.unusual')
94
+ end
95
+
96
+ ##
97
+ # Produces a sport from the ancient olympics.
98
+ #
99
+ # @return [String]
100
+ #
101
+ # @example
102
+ # Faker::Sport.ancient_olympics_sport #=> "Pankration"
103
+ #
104
+ # @faker.version next
105
+ def ancient_olympics_sport
106
+ fetch('sport.ancient_olympics')
107
+ end
108
+ end
109
+ end
110
+ end
data/lib/faker/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Faker # :nodoc:
4
- VERSION = '2.20.0'
4
+ VERSION = '2.23.0'
5
5
  end
data/lib/faker.rb CHANGED
@@ -13,23 +13,26 @@ I18n.reload! if I18n.backend.initialized?
13
13
 
14
14
  module Faker
15
15
  module Config
16
- @locale = nil
17
- @random = nil
18
-
19
16
  class << self
20
- attr_writer :locale, :random
17
+ def locale=(new_locale)
18
+ Thread.current[:faker_config_locale] = new_locale
19
+ end
21
20
 
22
21
  def locale
23
22
  # Because I18n.locale defaults to :en, if we don't have :en in our available_locales, errors will happen
24
- @locale || (I18n.available_locales.include?(I18n.locale) ? I18n.locale : I18n.available_locales.first)
23
+ Thread.current[:faker_config_locale] || (I18n.available_locales.include?(I18n.locale) ? I18n.locale : I18n.available_locales.first)
25
24
  end
26
25
 
27
26
  def own_locale
28
- @locale
27
+ Thread.current[:faker_config_locale]
28
+ end
29
+
30
+ def random=(new_random)
31
+ Thread.current[:faker_config_random] = new_random
29
32
  end
30
33
 
31
34
  def random
32
- @random || Random.new
35
+ Thread.current[:faker_config_random] || Random
33
36
  end
34
37
  end
35
38
  end
@@ -41,6 +44,8 @@ module Faker
41
44
  Letters = ULetters + LLetters
42
45
 
43
46
  class << self
47
+ attr_reader :flexible_key
48
+
44
49
  NOT_GIVEN = Object.new
45
50
 
46
51
  ## by default numerify results do not start with a zero
@@ -87,7 +92,7 @@ module Faker
87
92
  .gsub(/(\\?.)\{(\d+),(\d+)\}/) { |_match| Regexp.last_match(1) * sample(Array(Range.new(Regexp.last_match(2).to_i, Regexp.last_match(3).to_i))) } # A{1,2} becomes A or AA or \d{3} becomes \d\d\d
88
93
  .gsub(/\((.*?)\)/) { |match| sample(match.gsub(/[()]/, '').split('|')) } # (this|that) becomes 'this' or 'that'
89
94
  .gsub(/\[([^\]]+)\]/) { |match| match.gsub(/(\w-\w)/) { |range| sample(Array(Range.new(*range.split('-')))) } } # All A-Z inside of [] become C (or X, or whatever)
90
- .gsub(/\[([^\]]+)\]/) { |_match| sample(Regexp.last_match(1).split('')) } # All [ABC] become B (or A or C)
95
+ .gsub(/\[([^\]]+)\]/) { |_match| sample(Regexp.last_match(1).chars) } # All [ABC] become B (or A or C)
91
96
  .gsub('\d') { |_match| sample(Numbers) }
92
97
  .gsub('\w') { |_match| sample(Letters) }
93
98
  end
@@ -185,9 +190,9 @@ module Faker
185
190
  # girls_name: ["Alice", "Cheryl", "Tatiana"]
186
191
  # Then you can call Faker::Name.girls_name and it will act like #first_name
187
192
  def method_missing(mth, *args, &block)
188
- super unless @flexible_key
193
+ super unless flexible_key
189
194
 
190
- if (translation = translate("faker.#{@flexible_key}.#{mth}"))
195
+ if (translation = translate("faker.#{flexible_key}.#{mth}"))
191
196
  sample(translation)
192
197
  else
193
198
  super
@@ -7,7 +7,7 @@ module Faker
7
7
  base = alphabet.size
8
8
 
9
9
  lv = 0
10
- str.split('').reverse.each_with_index { |v, i| lv += v.unpack1('C') * 256**i }
10
+ str.chars.reverse.each_with_index { |v, i| lv += v.unpack1('C') * 256**i }
11
11
 
12
12
  ret = +''
13
13
  while lv.positive?
@@ -2,16 +2,9 @@
2
2
 
3
3
  module Faker
4
4
  class UniqueGenerator
5
- @marked_unique = Set.new # Holds names of generators with unique values
6
-
7
- class << self
8
- attr_reader :marked_unique
9
- end
10
-
11
5
  def initialize(generator, max_retries)
12
6
  @generator = generator
13
7
  @max_retries = max_retries
14
- @previous_results = Hash.new { |hash, key| hash[key] = Set.new }
15
8
  end
16
9
 
17
10
  def method_missing(name, *arguments)
@@ -20,9 +13,9 @@ module Faker
20
13
  @max_retries.times do
21
14
  result = @generator.public_send(name, *arguments)
22
15
 
23
- next if @previous_results[[name, arguments]].include?(result)
16
+ next if previous_results[[name, arguments]].include?(result)
24
17
 
25
- @previous_results[[name, arguments]] << result
18
+ previous_results[[name, arguments]] << result
26
19
  return result
27
20
  end
28
21
 
@@ -39,8 +32,17 @@ module Faker
39
32
 
40
33
  RetryLimitExceeded = Class.new(StandardError)
41
34
 
35
+ def previous_results
36
+ Thread.current[:faker_unique_generator_previous_results] ||= {}
37
+ Thread.current[:faker_unique_generator_previous_results][@generator] ||= Hash.new { |hash, key| hash[key] = Set.new }
38
+ end
39
+
42
40
  def clear
43
- @previous_results.clear
41
+ previous_results.clear
42
+ end
43
+
44
+ def self.marked_unique
45
+ Thread.current[:faker_unique_generator_marked_unique] ||= Set.new
44
46
  end
45
47
 
46
48
  def self.clear
@@ -51,7 +53,7 @@ module Faker
51
53
  def exclude(name, arguments, values)
52
54
  values ||= []
53
55
  values.each do |value|
54
- @previous_results[[name, arguments]] << value
56
+ previous_results[[name, arguments]] << value
55
57
  end
56
58
  end
57
59
  end
@@ -5,7 +5,6 @@ en:
5
5
  - Brisbane
6
6
  - Sydney
7
7
  - Melbourne
8
- - Brisbane
9
8
  - Perth
10
9
  - Adelaide
11
10
  - Gold Coast
@@ -85,7 +84,7 @@ en:
85
84
  - Cane Toad
86
85
  - Redback Spider
87
86
  - Funnel Web Spider
88
- - Blue Ringed OCtopus
87
+ - Blue Ringed Octopus
89
88
  - Fresh Water Crocodile
90
89
  - Skink
91
90
  - Thorny Devil
@@ -98,11 +97,11 @@ en:
98
97
  - Saltwater Crocodile
99
98
  - Eastern Brown Snake
100
99
  states:
101
- - New South wales
100
+ - New South Wales
102
101
  - Queensland
103
102
  - Western Australia
104
103
  - Northern Territory
105
104
  - South Australia
106
105
  - Australian Capital Territory
107
- - Visctoria
106
+ - Victoria
108
107
  - Tasmania
@@ -4,30 +4,49 @@ en:
4
4
  type:
5
5
  - server
6
6
  - workstation
7
- platform:
7
+ platform:
8
8
  - Linux
9
9
  - macOS
10
10
  - Windows
11
+ - OpenBSD
12
+ - TempleOS
13
+ - Plan 9
11
14
  os:
12
15
  linux:
13
- - RHEL 6.10
16
+ - RHEL 9.0
14
17
  - RHEL 7.7
15
- - CentOS 8
18
+ - RHEL 6.10
19
+ - CentOS 8.5
16
20
  - CentOS 7
17
21
  - CentOS 6
22
+ - Debian 11.4.0
18
23
  - Debian 10.10.3
19
24
  - Debian 9.9.10
20
- - Ubuntu Server 18.04
25
+ - Ubuntu Server 22.04
26
+ - Ubuntu Server 20.04
21
27
  - Ubuntu Server 19.10
28
+ - Ubuntu Server 18.04
29
+ - ArchLinux 2022.08.05
22
30
  - ArchLinux 2020.02.01
31
+ - openSUSE Leap 15.4
23
32
  - openSUSE Leap 15.1
33
+ - Ubuntu Desktop 22.04
34
+ - Ubuntu Desktop 20.04
24
35
  - Ubuntu Desktop 18.04
25
36
  - Ubuntu Desktop 19.10
37
+ openbsd:
38
+ - OpenBSD 7.1
39
+ - OpenBSD 6
40
+ templeos:
41
+ - TempleOS 5.03
42
+ plan 9:
43
+ - Plan 9 Fourth Edition
26
44
  macos:
27
45
  - Catalina (10.15)
28
46
  - Mojave (10.14)
29
47
  - High Sierra (10.13)
30
48
  windows:
49
+ - Windows 11
31
50
  - Windows 10
32
51
  - Windows 8.1
33
52
  - Windows 7