feiku 0.1.1 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 3297b4de9084be2ec8060291c0e38b91b3b23a99408f31db1df9f216e547b01d
4
- data.tar.gz: 206266a45fc4dd2da0b6ac92b2a508c1cc9698fa77c5c5d4e0f5ee386614fee4
3
+ metadata.gz: 8fdd3bcaa1c2a95a6c3bebedae5573c41669e27f3af1aab25fcb0afcd579846b
4
+ data.tar.gz: b0da6fc6c0193929662a0e85adef3752f36dfb915c5c4224940fb6eccbc51940
5
5
  SHA512:
6
- metadata.gz: be412a317663c1229e1d4ba42473934d8742ecaade40fff46dae6fdf8da7ea884a34cac1df0b80c07a63fc41abb2710e8559eb18e3f1b2ccd2fa4f3b942295a1
7
- data.tar.gz: 33cb68c3f37854435e28d50ad4fa279971faf125590e3a4bf1a59c12b097df271eac43eba73501b588bf01170c04828c709972553ceeb95e46fc136a1f80c2ee
6
+ metadata.gz: 138a371ac72af75e4d9351026986763f087a589b0bc8eb667cab1b3c600e16e9e7f56e804d89f68805cc951822edcf23bbbac957718824a4f74e0d89caaaab26
7
+ data.tar.gz: 165b15cd7b8b9d87a577c428a4e2fa8678d597737d5df59fc9f0ecc8599bcfad248e7c218a8956aac3c63348feed92f77a05294a0909d64a080803e8b6edbb29
data/.rubocop.yml CHANGED
@@ -1,6 +1,14 @@
1
1
  AllCops:
2
+ Exclude:
3
+ - 'feiku.gemspec'
4
+ - 'vendor/**/*'
5
+ NewCops: enable
2
6
  TargetRubyVersion: 3.0
3
7
 
8
+ Metrics:
9
+ Exclude:
10
+ - 'test/**/*'
11
+
4
12
  Style/StringLiterals:
5
13
  EnforcedStyle: double_quotes
6
14
 
data/CHANGELOG.md CHANGED
@@ -1,5 +1,10 @@
1
1
  ## [Unreleased]
2
2
 
3
+ ## [0.2.0] - 2024-10-13
4
+
5
+ - Introduce Faker compatibility
6
+ - Enable unique generation
7
+
3
8
  ## [0.1.0] - 2024-08-23
4
9
 
5
10
  - Initial release
@@ -0,0 +1,32 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Feiku
4
+ # MetaProxy is a class just for const_missing
5
+ class MetaProxy
6
+ def self.const_missing(name)
7
+ Proxy.new(name)
8
+ end
9
+ end
10
+
11
+ # Proxy is a simple blank object to invoke method_missing
12
+ class Proxy < BasicObject
13
+ def initialize(name)
14
+ @name = name
15
+ end
16
+
17
+ private
18
+
19
+ def method_missing(meth)
20
+ generator = ::Feiku.lookup(@name, meth)
21
+ raise ArgumentError, "No generator found for #{@name}.#{meth}" unless generator
22
+
23
+ generator.generate
24
+ end
25
+
26
+ def respond_to_missing?(meth)
27
+ !!::Feiku.lookup(@name, meth)
28
+ end
29
+ end
30
+ end
31
+
32
+ Faker = Feiku::MetaProxy
@@ -11,23 +11,26 @@ module Feiku
11
11
  class Generator
12
12
  RANDOM_STRING = [*"a".."z", *"A".."Z"].freeze
13
13
  RANDOM_INTEGER = [*0..9].freeze
14
- def initialize(format:, value:, length:, pool_size: 0)
14
+ def initialize(format:, value:, length:, pool_size: 0, &block) # rubocop:disable Metrics/MethodLength
15
15
  @length = length
16
16
  @value = value
17
17
  @format, @size = if value.is_a?(Hash)
18
18
  [format, value.size]
19
19
  else
20
20
  n = 0
21
- format.gsub!(/%\{[^}]+\}/) { n += 1 and "%s" }
22
- [format, n]
21
+ f = format.gsub(/%\{[^}]+\}/) { n += 1 and "%s" }
22
+ [f, n]
23
23
  end
24
24
  @pool = pool_size.zero? ? nil : Array.new(pool_size) { _generate }
25
+ self.class.class_eval(&block) if block_given?
25
26
  end
26
27
 
27
28
  def generate
28
29
  @pool.nil? ? _generate : @pool.sample
29
30
  end
30
31
 
32
+ private
33
+
31
34
  def _generate
32
35
  @fillings = case @value
33
36
  when :string, :integer
data/lib/feiku/unit.rb CHANGED
@@ -11,25 +11,34 @@ module Feiku
11
11
  @data_type = data_type
12
12
  @length = length
13
13
  @unique = false
14
+ @uniqueness_pool = []
14
15
  end
15
16
 
16
- def generate(max_attempt: 10, &block)
17
+ def generate(max_attempt: 1000, &block)
17
18
  length = @length.is_a?(Integer) ? @length : @length.to_a.sample
18
19
  generated = _generate(length)
19
- return generated if check_success_with(generated, block) && check_uniqueness(generated)
20
+ if check_success_with(generated, block) && check_uniqueness(generated)
21
+ @uniqueness_pool << generated
22
+ return generated
23
+ end
24
+
25
+ try_until_success(length, max_attempt, &block)
26
+ end
20
27
 
28
+ def try_until_success(length, max_attempt, &block)
21
29
  attempt_count = 0
22
30
  while attempt_count <= max_attempt
23
31
  item = _generate(length)
24
- return item if check_success_with(item) && check_uniqueness(item)
32
+ if check_success_with(item, block) && check_uniqueness(item)
33
+ @uniqueness_pool << item
34
+ return item
35
+ end
36
+
37
+ attempt_count += 1
25
38
  end
26
39
  raise Feiku::Error, "Cannot generate correct data within given attempt times: #{max_attempt}"
27
40
  end
28
41
 
29
- def filter_result(generated, &block)
30
- generated = _generate(length) until block.call(generated)
31
- end
32
-
33
42
  def unique
34
43
  @unique = true
35
44
  self
@@ -46,8 +55,7 @@ module Feiku
46
55
  def check_uniqueness(item)
47
56
  return true unless @unique
48
57
 
49
- # TODO
50
- item == 42
58
+ @uniqueness_pool.none? { |pool_item| pool_item == item }
51
59
  end
52
60
 
53
61
  def _generate(length)
@@ -58,7 +66,8 @@ module Feiku
58
66
  else raise Feiku::Error
59
67
  end
60
68
  end
69
+ Username = Unit.new(data_type: :alphanumeric, length: 2..10)
70
+ Firstname = Unit.new(data_type: ->(l) { Feiku::Unit::RANDOM_STRING.sample(l).join.capitalize }, length: 3..8)
71
+ Lastname = Firstname
61
72
  end
62
-
63
- Username = Unit.new(data_type: :alphanumeric, length: 2..10)
64
73
  end
data/lib/feiku/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Feiku
4
- VERSION = "0.1.1"
4
+ VERSION = "0.2.0"
5
5
  end
data/lib/feiku.rb CHANGED
@@ -3,17 +3,41 @@
3
3
  require_relative "feiku/version"
4
4
  require_relative "feiku/generator"
5
5
  require_relative "feiku/unit"
6
+ require_relative "feiku/faker_compat"
6
7
 
7
8
  # Toplevel
8
9
  module Feiku
10
+ @faker_compat_registry = {}
11
+
9
12
  class Error < StandardError; end
10
13
 
11
- def self.register(module_name, format:, value:, length: nil, pool_size: 0)
12
- const_set(module_name, Generator.new(format: format, value: value, length: length, pool_size: pool_size))
14
+ # Primary interface to add fake data definition
15
+ def self.register(module_name, format:, value:, length: nil, pool_size: 0, faker_compat: nil) # rubocop:disable Metrics/ParameterLists
16
+ generator = Generator.new(format: format, value: value, length: length, pool_size: pool_size)
17
+ @faker_compat_registry.update(faker_compat => generator) if faker_compat
18
+ remove_const(module_name) if const_defined?(module_name)
19
+ const_set(module_name, generator)
13
20
  end
14
- end
15
21
 
16
- Feiku.register(:Domain, format: "%<name>s.example", value: { name: Feiku::Username })
17
- Feiku.register(:Email,
18
- format: "%<name>s@%<domain>s",
19
- value: { name: Feiku::Username, domain: Feiku::Domain })
22
+ # An interface for Faker compatibility
23
+ def self.lookup(module_name, method_name)
24
+ @faker_compat_registry.fetch("#{module_name}.#{method_name}")
25
+ end
26
+
27
+ register(:Name, format: "%<first_name>s %<last_name>s",
28
+ value: { first_name: Unit::Firstname, last_name: Unit::Lastname },
29
+ faker_compat: "Name.name")
30
+ register(:Firstname, format: "%<name>s", value: { name: Unit::Firstname }, faker_compat: "Name.first_name")
31
+ register(:Middlename, format: "%<name>s", value: { name: Unit::Firstname }, faker_compat: "Name.middle_name")
32
+ register(:Lastname, format: "%<name>s", value: { name: Unit::Firstname }, faker_compat: "Name.last_name")
33
+ register(:NameWithMiddle, format: "%<first_name>s %<middle_name>s %<last_name>s",
34
+ value: {
35
+ first_name: Unit::Firstname,
36
+ middle_name: Unit::Firstname,
37
+ last_name: Unit::Lastname
38
+ },
39
+ faker_compat: "Name.name_with_middle")
40
+ register(:Domain, format: "%<name>s.example", value: { name: Unit::Username })
41
+ register(:Email, format: "%<name>s@%<domain>s",
42
+ value: { name: Unit::Username, domain: Domain })
43
+ end
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: feiku
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.1
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - OKURA Masafumi
8
8
  bindir: exe
9
9
  cert_chain: []
10
- date: 2024-09-19 00:00:00.000000000 Z
10
+ date: 2024-10-13 00:00:00.000000000 Z
11
11
  dependencies: []
12
12
  description: Feiku (pronounced as "fake") is a tool to generate fake data. Unlike
13
13
  other solutions, it doesn't use YAML file to define data. Instead, it generates
@@ -25,6 +25,7 @@ files:
25
25
  - README.md
26
26
  - Rakefile
27
27
  - lib/feiku.rb
28
+ - lib/feiku/faker_compat.rb
28
29
  - lib/feiku/generator.rb
29
30
  - lib/feiku/unit.rb
30
31
  - lib/feiku/version.rb