kangaru 0.1.0 → 0.1.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Gemfile.lock +1 -1
- data/README.md +2 -0
- data/Steepfile +2 -0
- data/kangaru.gemspec +7 -1
- data/lib/kangaru/application.rb +5 -1
- data/lib/kangaru/concerns/configurable.rb +1 -1
- data/lib/kangaru/controller.rb +4 -4
- data/lib/kangaru/database.rb +1 -1
- data/lib/kangaru/initialisers/rspec/kangaru_helper.rb +18 -0
- data/lib/kangaru/initialisers/rspec/request_helper.rb +72 -0
- data/lib/kangaru/initialisers/rspec.rb +7 -1
- data/lib/kangaru/injected_methods.rb +5 -5
- data/lib/kangaru/router.rb +5 -4
- data/lib/kangaru/version.rb +1 -1
- data/lib/kangaru.rb +3 -3
- data/sig/class.rbs +3 -0
- data/sig/kangaru/application.rbs +34 -0
- data/sig/kangaru/argument_parser.rbs +17 -0
- data/sig/kangaru/components/component.rbs +9 -0
- data/sig/kangaru/concerns/attributes_concern.rbs +25 -0
- data/sig/kangaru/concerns/concern.rbs +15 -0
- data/sig/kangaru/concerns/configurable.rbs +15 -0
- data/sig/kangaru/concerns/validatable.rbs +28 -0
- data/sig/kangaru/config.rbs +27 -0
- data/sig/kangaru/configurators/application_configurator.rbs +7 -0
- data/sig/kangaru/configurators/configurator.rbs +14 -0
- data/sig/kangaru/configurators/database_configurator.rbs +9 -0
- data/sig/kangaru/configurators/external_configurator.rbs +6 -0
- data/sig/kangaru/configurators/open_configurator.rbs +11 -0
- data/sig/kangaru/configurators/request_configurator.rbs +7 -0
- data/sig/kangaru/configurators.rbs +7 -0
- data/sig/kangaru/controller.rbs +23 -0
- data/sig/kangaru/database.rbs +31 -0
- data/sig/kangaru/inflectors/class_inflector.rbs +6 -0
- data/sig/kangaru/inflectors/constant_inflector.rbs +7 -0
- data/sig/kangaru/inflectors/constantiser.rbs +9 -0
- data/sig/kangaru/inflectors/human_inflector.rbs +6 -0
- data/sig/kangaru/inflectors/inflector.rbs +47 -0
- data/sig/kangaru/inflectors/inflector_macros.rbs +23 -0
- data/sig/kangaru/inflectors/path_inflector.rbs +7 -0
- data/sig/kangaru/inflectors/screaming_snakecase_inflector.rbs +6 -0
- data/sig/kangaru/inflectors/snakecase_inflector.rbs +6 -0
- data/sig/kangaru/inflectors/tokeniser.rbs +14 -0
- data/sig/kangaru/initialiser.rbs +9 -0
- data/sig/kangaru/initialisers/rspec.rbs +6 -0
- data/sig/kangaru/injected_methods.rbs +17 -0
- data/sig/kangaru/model.rbs +16 -0
- data/sig/kangaru/patches/constantise.rbs +9 -0
- data/sig/kangaru/patches/inflections.rbs +15 -0
- data/sig/kangaru/patches/source.rbs +9 -0
- data/sig/kangaru/patches/symboliser.rbs +13 -0
- data/sig/kangaru/path_parser.rbs +19 -0
- data/sig/kangaru/paths.rbs +35 -0
- data/sig/kangaru/renderer.rbs +9 -0
- data/sig/kangaru/request.rbs +24 -0
- data/sig/kangaru/request_builder.rbs +21 -0
- data/sig/kangaru/router.rbs +26 -0
- data/sig/kangaru/validation/attribute_validator.rbs +21 -0
- data/sig/kangaru/validation/error.rbs +20 -0
- data/sig/kangaru/validators/required_validator.rbs +9 -0
- data/sig/kangaru/validators/validator.rbs +20 -0
- data/sig/kangaru.rbs +29 -0
- metadata +56 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 15146a85b29524ce8435963bbc25601017d72cafef5cf69331b920219bad4113
|
4
|
+
data.tar.gz: de9a21f5cb27508169c1fec64b60f7a2aeacbb0beaac0b3fa1392288ea5f7728
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 03d7d75d0b7c98d7ea7cfa74390fe9bd16ad8d0c02ee7d9e5cc61499b8f545fb90cbf0b8a0361851088b59066f91c0ca24f429747c084d9984ededdd233c5363
|
7
|
+
data.tar.gz: 9ec21c22c2f17b8943e546060fe872d08f43c38038970abdfdafb867eff1a7d134931069ae03eae832171ab280433bf236ca22635c3fa1c59d0bd76382dfa6c4
|
data/Gemfile.lock
CHANGED
data/README.md
CHANGED
@@ -2,6 +2,8 @@
|
|
2
2
|
|
3
3
|
Kangaru is an open-source framework written in Ruby for building powerful and efficient command line applications. This project aims to make it easier for developers to create complex CLI programs with minimal effort, by providing a set of useful tools and libraries in a configurable ecosystem.
|
4
4
|
|
5
|
+
> Note: This software is currently in beta mode, meaning it may contain bugs and be subject to changes. Please exercise caution when using this software and report any issues you encounter. The first production-ready release of Kangaru will be version 1.0.0.
|
6
|
+
|
5
7
|
## Features
|
6
8
|
|
7
9
|
- MVC architecture drawing heavy inspiration from Rails
|
data/Steepfile
CHANGED
data/kangaru.gemspec
CHANGED
@@ -7,14 +7,20 @@ Gem::Specification.new do |spec|
|
|
7
7
|
spec.email = ["71787007+apexatoll@users.noreply.github.com"]
|
8
8
|
|
9
9
|
spec.summary = "A lightweight framework for building command line interfaces"
|
10
|
+
spec.homepage = "https://github.com/apexatoll/kangaru"
|
10
11
|
spec.license = "MIT"
|
11
12
|
spec.required_ruby_version = ">= 3.2.0"
|
12
13
|
|
13
14
|
spec.files = Dir.chdir(__dir__) do
|
14
15
|
`git ls-files`.split("\n").reject do |f|
|
15
|
-
f == __FILE__ || f.match?(/\A(bin|
|
16
|
+
f == __FILE__ || f.match?(/\A(bin|spec|\.git|\.github)/)
|
16
17
|
end
|
17
18
|
end
|
19
|
+
|
20
|
+
spec.metadata["homepage_uri"] = spec.homepage
|
21
|
+
spec.metadata["source_code_uri"] = spec.homepage
|
22
|
+
spec.metadata["changelog_uri"] = "#{spec.homepage}/releases"
|
23
|
+
|
18
24
|
spec.bindir = "bin"
|
19
25
|
spec.executables = []
|
20
26
|
spec.require_paths = ["lib"]
|
data/lib/kangaru/application.rb
CHANGED
@@ -16,6 +16,10 @@ module Kangaru
|
|
16
16
|
@config ||= Config.new
|
17
17
|
end
|
18
18
|
|
19
|
+
def router
|
20
|
+
@router ||= Router.new(namespace:)
|
21
|
+
end
|
22
|
+
|
19
23
|
# If called with no env, the config will be applied regardless of current
|
20
24
|
# env. If multiple configure calls matching the current env are made, the
|
21
25
|
# most recent calls will overwrite older changes.
|
@@ -39,7 +43,7 @@ module Kangaru
|
|
39
43
|
def run!(*argv)
|
40
44
|
request = RequestBuilder.new(argv).build
|
41
45
|
|
42
|
-
|
46
|
+
router.resolve(request)
|
43
47
|
end
|
44
48
|
|
45
49
|
def_delegators :paths, :view_path
|
data/lib/kangaru/controller.rb
CHANGED
@@ -13,7 +13,7 @@ module Kangaru
|
|
13
13
|
end
|
14
14
|
|
15
15
|
def execute
|
16
|
-
public_send(request.action)
|
16
|
+
return unless public_send(request.action)
|
17
17
|
|
18
18
|
renderer_for(request.action.to_s).render(binding)
|
19
19
|
end
|
@@ -30,7 +30,7 @@ module Kangaru
|
|
30
30
|
private
|
31
31
|
|
32
32
|
def view_path(file)
|
33
|
-
Kangaru.application
|
33
|
+
Kangaru.application!.view_path(self.class.path, file)
|
34
34
|
end
|
35
35
|
|
36
36
|
def renderer_for(file)
|
@@ -43,9 +43,9 @@ module Kangaru
|
|
43
43
|
# within the application namespace by delegating const lookups to said
|
44
44
|
# namespace if the constant is not in scope from the current class.
|
45
45
|
def self.const_missing(const)
|
46
|
-
return super unless Kangaru.application
|
46
|
+
return super unless Kangaru.application!.namespace.const_defined?(const)
|
47
47
|
|
48
|
-
Kangaru.application
|
48
|
+
Kangaru.application!.namespace.const_get(const)
|
49
49
|
end
|
50
50
|
|
51
51
|
private_class_method :const_missing
|
data/lib/kangaru/database.rb
CHANGED
@@ -0,0 +1,18 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Initialisers
|
3
|
+
module RSpec
|
4
|
+
module KangaruHelper
|
5
|
+
def run_in_transaction(&block)
|
6
|
+
database = Kangaru.application&.database
|
7
|
+
|
8
|
+
return block.call if database.nil?
|
9
|
+
|
10
|
+
database.transaction do
|
11
|
+
block.call
|
12
|
+
database.rollback_on_exit
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,72 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Initialisers
|
3
|
+
module RSpec
|
4
|
+
module RequestHelper
|
5
|
+
attr_reader :request
|
6
|
+
|
7
|
+
def stub_output(&block)
|
8
|
+
stdout = $stdout
|
9
|
+
stderr = $stderr
|
10
|
+
$stdout = File.open(File::NULL, "w")
|
11
|
+
$stderr = File.open(File::NULL, "w")
|
12
|
+
|
13
|
+
block.call
|
14
|
+
|
15
|
+
$stdout = stdout
|
16
|
+
$stderr = stderr
|
17
|
+
end
|
18
|
+
|
19
|
+
def resolve(path, params:)
|
20
|
+
@request = Kangaru::Request.new(path:, params:)
|
21
|
+
|
22
|
+
Kangaru.application.router.resolve(request)
|
23
|
+
end
|
24
|
+
|
25
|
+
def view_path(name)
|
26
|
+
Kangaru.application!.view_path(described_class.path, name.to_s)
|
27
|
+
end
|
28
|
+
|
29
|
+
if Object.const_defined?(:RSpec)
|
30
|
+
extend ::RSpec::Matchers::DSL
|
31
|
+
|
32
|
+
matcher :render_template do |name|
|
33
|
+
supports_block_expectations
|
34
|
+
|
35
|
+
match do |action|
|
36
|
+
renderer = instance_double(Kangaru::Renderer, render: nil)
|
37
|
+
allow(Kangaru::Renderer).to receive(:new).and_return(renderer)
|
38
|
+
expect(Kangaru::Renderer).not_to have_received(:new)
|
39
|
+
|
40
|
+
action.call
|
41
|
+
|
42
|
+
expect(Kangaru::Renderer)
|
43
|
+
.to have_received(:new)
|
44
|
+
.with(view_path(name))
|
45
|
+
.once
|
46
|
+
|
47
|
+
expect(renderer)
|
48
|
+
.to have_received(:render)
|
49
|
+
.once
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
if Object.const_defined?(:RSpec)
|
56
|
+
::RSpec.configure do |config|
|
57
|
+
file_path = %r{spec/.*/controllers/}
|
58
|
+
|
59
|
+
config.define_derived_metadata(file_path:) do |metadata|
|
60
|
+
metadata[:type] = :request
|
61
|
+
end
|
62
|
+
|
63
|
+
config.include RequestHelper, type: :request
|
64
|
+
|
65
|
+
config.around(type: :request) do |spec|
|
66
|
+
stub_output { spec.run }
|
67
|
+
end
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
@@ -2,8 +2,14 @@ module Kangaru
|
|
2
2
|
module Initialisers
|
3
3
|
module RSpec
|
4
4
|
if Object.const_defined?(:RSpec)
|
5
|
-
::RSpec.configure do
|
5
|
+
::RSpec.configure do |config|
|
6
6
|
Kangaru.env = :test
|
7
|
+
|
8
|
+
config.include KangaruHelper
|
9
|
+
|
10
|
+
config.around do |spec|
|
11
|
+
run_in_transaction { spec.run }
|
12
|
+
end
|
7
13
|
end
|
8
14
|
end
|
9
15
|
end
|
@@ -1,23 +1,23 @@
|
|
1
1
|
module Kangaru
|
2
2
|
module InjectedMethods
|
3
3
|
def run!(*argv)
|
4
|
-
Kangaru.application
|
4
|
+
Kangaru.application!.run!(*argv)
|
5
5
|
end
|
6
6
|
|
7
7
|
def config
|
8
|
-
Kangaru.application
|
8
|
+
Kangaru.application!.config
|
9
9
|
end
|
10
10
|
|
11
11
|
def configure(env = nil, &)
|
12
|
-
Kangaru.application
|
12
|
+
Kangaru.application!.configure(env, &)
|
13
13
|
end
|
14
14
|
|
15
15
|
def apply_config!
|
16
|
-
Kangaru.application
|
16
|
+
Kangaru.application!.apply_config!
|
17
17
|
end
|
18
18
|
|
19
19
|
def database
|
20
|
-
Kangaru.application
|
20
|
+
Kangaru.application!.database
|
21
21
|
end
|
22
22
|
end
|
23
23
|
end
|
data/lib/kangaru/router.rb
CHANGED
@@ -5,15 +5,16 @@ module Kangaru
|
|
5
5
|
|
6
6
|
attr_reader :request, :namespace
|
7
7
|
|
8
|
-
def initialize(
|
9
|
-
@request = request
|
8
|
+
def initialize(namespace: Object)
|
10
9
|
@namespace = namespace
|
10
|
+
end
|
11
|
+
|
12
|
+
def resolve(request)
|
13
|
+
@request = request
|
11
14
|
|
12
15
|
validate_controller_defined!
|
13
16
|
validate_action_defined!
|
14
|
-
end
|
15
17
|
|
16
|
-
def resolve
|
17
18
|
controller_class.new(request).execute
|
18
19
|
end
|
19
20
|
|
data/lib/kangaru/version.rb
CHANGED
data/lib/kangaru.rb
CHANGED
@@ -29,10 +29,10 @@ module Kangaru
|
|
29
29
|
end
|
30
30
|
|
31
31
|
class << self
|
32
|
-
|
32
|
+
attr_accessor :application
|
33
33
|
|
34
|
-
def application
|
35
|
-
|
34
|
+
def application!
|
35
|
+
application || raise("application not set")
|
36
36
|
end
|
37
37
|
|
38
38
|
def env=(value)
|
data/sig/class.rbs
ADDED
@@ -0,0 +1,34 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class Application
|
3
|
+
extend Forwardable
|
4
|
+
|
5
|
+
attr_reader paths: Paths
|
6
|
+
attr_reader namespace: Module
|
7
|
+
attr_reader config: Config
|
8
|
+
attr_reader database: Database?
|
9
|
+
attr_reader router: Router
|
10
|
+
|
11
|
+
def initialize: (source: String, namespace: Module) -> void
|
12
|
+
|
13
|
+
def configure: (?Symbol?) { (Config) -> void } -> void
|
14
|
+
|
15
|
+
def configured?: -> bool
|
16
|
+
|
17
|
+
def apply_config!: -> void
|
18
|
+
|
19
|
+
def run!: (*String) -> void
|
20
|
+
|
21
|
+
# Delegated to paths
|
22
|
+
def view_path: (*String, ?ext: Symbol?) -> Pathname
|
23
|
+
|
24
|
+
private
|
25
|
+
|
26
|
+
@configured: bool
|
27
|
+
|
28
|
+
def current_env?: (Symbol?) -> bool
|
29
|
+
|
30
|
+
attr_reader autoloader: Zeitwerk::Loader
|
31
|
+
|
32
|
+
def setup_database!: -> Database?
|
33
|
+
end
|
34
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class ArgumentParser
|
3
|
+
attr_reader tokens: Array[String]
|
4
|
+
|
5
|
+
def initialize: (*String) -> void
|
6
|
+
|
7
|
+
def parse: -> Hash[Symbol, untyped]
|
8
|
+
|
9
|
+
private
|
10
|
+
|
11
|
+
def grouped_argument_tokens: -> Array[Array[String]]
|
12
|
+
|
13
|
+
def parse_key: (String) -> Symbol
|
14
|
+
|
15
|
+
def parse_value: (Array[untyped]) -> untyped
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Concerns
|
3
|
+
module AttributesConcern
|
4
|
+
extend Concern
|
5
|
+
|
6
|
+
module ClassMethods
|
7
|
+
def attributes: -> Array[Symbol]
|
8
|
+
|
9
|
+
def defaults: -> Hash[Symbol, untyped]
|
10
|
+
|
11
|
+
def set_default: (**untyped) -> void
|
12
|
+
|
13
|
+
@defaults: Hash[Symbol, untyped]
|
14
|
+
end
|
15
|
+
|
16
|
+
extend ClassMethods
|
17
|
+
|
18
|
+
attr_reader defaults: Hash[Symbol, untyped]
|
19
|
+
|
20
|
+
def instance_methods: -> Array[Symbol]
|
21
|
+
|
22
|
+
def initialize: (**untyped) -> void
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Concerns
|
3
|
+
module Concern : Module
|
4
|
+
@included: untyped
|
5
|
+
|
6
|
+
def append_features: (untyped) -> void
|
7
|
+
|
8
|
+
def class_methods: { [self: singleton(Class)] -> void } -> void
|
9
|
+
|
10
|
+
def included: (?untyped?) ?{ -> void } -> void
|
11
|
+
|
12
|
+
def evaluate_concern_blocks!: (untyped) -> void
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Concerns
|
3
|
+
module Configurable
|
4
|
+
extend Concern
|
5
|
+
extend ClassMethods
|
6
|
+
|
7
|
+
module ClassMethods
|
8
|
+
def configurator_name: -> String
|
9
|
+
end
|
10
|
+
|
11
|
+
def name: -> String
|
12
|
+
def config: [C < Configurators::Configurator] -> C
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Concerns
|
3
|
+
module Validatable
|
4
|
+
type validations = Hash[Symbol, Hash[Symbol, untyped]]
|
5
|
+
|
6
|
+
extend Concern
|
7
|
+
extend ClassMethods
|
8
|
+
|
9
|
+
attr_reader validation_rules: validations
|
10
|
+
|
11
|
+
module ClassMethods
|
12
|
+
attr_reader validation_rules: validations
|
13
|
+
|
14
|
+
def validates: (Symbol, **untyped) -> void
|
15
|
+
end
|
16
|
+
|
17
|
+
attr_reader errors: Array[Validation::Error]
|
18
|
+
|
19
|
+
def validate: -> void
|
20
|
+
|
21
|
+
def valid?: -> bool
|
22
|
+
|
23
|
+
private
|
24
|
+
|
25
|
+
def validator_for: (Symbol) -> Validation::AttributeValidator
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class Config
|
3
|
+
type configurator = Configurators::Configurator
|
4
|
+
|
5
|
+
attr_reader configurators: Hash[Symbol, configurator]
|
6
|
+
|
7
|
+
def initialize: -> void
|
8
|
+
|
9
|
+
def serialise: -> Hash[Symbol, Hash[Symbol, untyped]]
|
10
|
+
|
11
|
+
def import_external_config!: -> void
|
12
|
+
|
13
|
+
def for: (String) -> untyped
|
14
|
+
|
15
|
+
# Configurators
|
16
|
+
attr_reader application: Configurators::ApplicationConfigurator
|
17
|
+
attr_reader database: Configurators::DatabaseConfigurator
|
18
|
+
attr_reader external: Configurators::ExternalConfigurator
|
19
|
+
attr_reader request: Configurators::RequestConfigurator
|
20
|
+
|
21
|
+
private
|
22
|
+
|
23
|
+
def set_configurators!: -> Hash[Symbol, configurator]
|
24
|
+
|
25
|
+
def external_config_exists?: -> bool
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Configurators
|
3
|
+
class Configurator
|
4
|
+
include Concerns::AttributesConcern
|
5
|
+
extend Concerns::AttributesConcern::ClassMethods
|
6
|
+
|
7
|
+
def self.key: -> Symbol
|
8
|
+
|
9
|
+
def self.name: -> String
|
10
|
+
|
11
|
+
def serialise: -> Hash[Symbol, untyped]
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class Controller
|
3
|
+
extend Forwardable
|
4
|
+
|
5
|
+
SUFFIX: String
|
6
|
+
|
7
|
+
attr_reader request: Request
|
8
|
+
|
9
|
+
def initialize: (Request) -> void
|
10
|
+
|
11
|
+
def execute: -> void
|
12
|
+
|
13
|
+
def self.path: -> String
|
14
|
+
|
15
|
+
def params: -> Hash[Symbol, untyped]
|
16
|
+
|
17
|
+
private
|
18
|
+
|
19
|
+
def view_path: (String) -> Pathname
|
20
|
+
|
21
|
+
def renderer_for: (String) -> Renderer
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,31 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class Database
|
3
|
+
extend Forwardable
|
4
|
+
|
5
|
+
include Concerns::AttributesConcern
|
6
|
+
extend Concerns::AttributesConcern::ClassMethods
|
7
|
+
|
8
|
+
PLUGINS: Array[Symbol]
|
9
|
+
|
10
|
+
attr_accessor adaptor: Symbol
|
11
|
+
attr_accessor path: String
|
12
|
+
attr_accessor migration_path: String
|
13
|
+
|
14
|
+
attr_reader handler: Sequel::Database
|
15
|
+
|
16
|
+
def setup!: -> void
|
17
|
+
|
18
|
+
def migrate!: -> void
|
19
|
+
|
20
|
+
# Delegated to handler
|
21
|
+
def rollback_on_exit: -> void
|
22
|
+
def tables: -> Array[Symbol]
|
23
|
+
def transaction: { -> void } -> void
|
24
|
+
|
25
|
+
private
|
26
|
+
|
27
|
+
def migrations_exist?: -> bool
|
28
|
+
|
29
|
+
def setup_sqlite!: -> Sequel::Database
|
30
|
+
end
|
31
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Inflectors
|
3
|
+
class Inflector
|
4
|
+
type token_groups = Array[Array[String]]
|
5
|
+
|
6
|
+
extend InflectorMacros
|
7
|
+
|
8
|
+
DEFAULT_GROUP_JOINER: String
|
9
|
+
|
10
|
+
attr_reader string: String
|
11
|
+
|
12
|
+
def initialize: (String) -> void
|
13
|
+
|
14
|
+
def inflect: -> String
|
15
|
+
|
16
|
+
def self.inflect: (String) -> String
|
17
|
+
|
18
|
+
private
|
19
|
+
|
20
|
+
attr_reader tokeniser: Tokeniser
|
21
|
+
|
22
|
+
def class_attribute: (Symbol) -> untyped
|
23
|
+
|
24
|
+
def input_filter: -> untyped
|
25
|
+
|
26
|
+
def token_transformer: -> untyped
|
27
|
+
|
28
|
+
def token_joiner: -> untyped
|
29
|
+
|
30
|
+
def group_joiner: -> untyped
|
31
|
+
|
32
|
+
def post_processor: -> untyped
|
33
|
+
|
34
|
+
def filter_input: (String) -> String
|
35
|
+
|
36
|
+
def transform_and_join_tokens: (Array[Array[String]]) -> Array[String]
|
37
|
+
|
38
|
+
def transform_token: (String) -> String
|
39
|
+
|
40
|
+
def join_tokens: (Array[String]) -> String
|
41
|
+
|
42
|
+
def join_groups: (Array[String]) -> String
|
43
|
+
|
44
|
+
def post_process: (String) -> String
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Inflectors
|
3
|
+
module InflectorMacros
|
4
|
+
@input_filter: untyped
|
5
|
+
@token_transformer: untyped
|
6
|
+
@token_joiner: untyped
|
7
|
+
@group_joiner: untyped
|
8
|
+
@post_processor: untyped
|
9
|
+
|
10
|
+
def inherited: (Class) -> void
|
11
|
+
|
12
|
+
def filter_input_with: (Regexp) -> void
|
13
|
+
|
14
|
+
def transform_tokens_with: (?Symbol?) ?{ (String) -> String } -> void
|
15
|
+
|
16
|
+
def join_tokens_with: (String) -> void
|
17
|
+
|
18
|
+
def join_groups_with: (String) -> void
|
19
|
+
|
20
|
+
def post_process_with: (?Symbol?) ?{ (String) -> String } -> void
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module InjectedMethods
|
3
|
+
interface _InjectedMethods
|
4
|
+
def run!: (*String) -> void
|
5
|
+
|
6
|
+
def config: -> Config
|
7
|
+
|
8
|
+
def configure: (?Symbol?) { (Config) -> void } -> void
|
9
|
+
|
10
|
+
def apply_config!: -> void
|
11
|
+
|
12
|
+
def database: -> Database?
|
13
|
+
end
|
14
|
+
|
15
|
+
include _InjectedMethods
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module Kangaru
|
2
|
+
# This is a hacky fix to ensure that the definition of Model via Class.new is
|
3
|
+
# typed to be the same as if it was called with `class Model; end`.
|
4
|
+
# This is to prevent the inherited hook trying to find a `models` database
|
5
|
+
# table when Sequel::Model is inherited in the conventional way.
|
6
|
+
class Class
|
7
|
+
def self.new: (untyped) { -> void } -> singleton(Model)
|
8
|
+
end
|
9
|
+
|
10
|
+
class Model < Sequel::Model
|
11
|
+
include Concerns::Validatable
|
12
|
+
extend Concerns::Validatable::ClassMethods
|
13
|
+
|
14
|
+
def self.enum: (Symbol, **Integer) -> void
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,13 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Patches
|
3
|
+
module Symboliser : Enumerable[untyped]
|
4
|
+
class ::Hash[unchecked out K, unchecked out V]
|
5
|
+
def symbolise: -> Hash[Symbol, untyped]
|
6
|
+
end
|
7
|
+
|
8
|
+
class Array[unchecked out Elem]
|
9
|
+
def symbolise: -> Hash[Symbol, untyped]
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class PathParser
|
3
|
+
attr_reader path: String
|
4
|
+
|
5
|
+
def initialize: (String) -> void
|
6
|
+
|
7
|
+
def controller: -> String?
|
8
|
+
|
9
|
+
def action: -> Symbol?
|
10
|
+
|
11
|
+
def id: -> Integer?
|
12
|
+
|
13
|
+
private
|
14
|
+
|
15
|
+
MATCHERS: Hash[Symbol, Regexp]
|
16
|
+
|
17
|
+
def match: (Symbol, ?cast: Symbol) -> untyped
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class Paths
|
3
|
+
attr_reader source: Pathname
|
4
|
+
attr_reader dir: Pathname
|
5
|
+
attr_reader name: String
|
6
|
+
|
7
|
+
def initialize: (source: String) -> void
|
8
|
+
|
9
|
+
def gem_path: (*String, ?ext: Symbol?) -> Pathname
|
10
|
+
|
11
|
+
def lib_path: (*String, ?ext: Symbol?) -> Pathname
|
12
|
+
|
13
|
+
def path: (*String, ?ext: Symbol?) -> Pathname
|
14
|
+
|
15
|
+
def view_path: (*String, ?ext: Symbol?) -> Pathname
|
16
|
+
|
17
|
+
def collapsed_dirs: -> Array[String]
|
18
|
+
|
19
|
+
private
|
20
|
+
|
21
|
+
MODELS_DIRNAME: String
|
22
|
+
VIEWS_DIRNAME: String
|
23
|
+
CONTROLLERS_DIRNAME: String
|
24
|
+
|
25
|
+
attr_reader gem_dir: Pathname
|
26
|
+
attr_reader lib_dir: Pathname
|
27
|
+
attr_reader app_dir: Pathname
|
28
|
+
|
29
|
+
attr_reader models_dir: Pathname
|
30
|
+
attr_reader views_dir: Pathname
|
31
|
+
attr_reader controllers_dir: Pathname
|
32
|
+
|
33
|
+
def build_path: (*String, dir: Pathname, ext: Symbol?) -> Pathname
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class Request
|
3
|
+
include Concerns::Configurable
|
4
|
+
|
5
|
+
DEFAULT_CONTROLLER: String
|
6
|
+
|
7
|
+
DEFAULT_ACTION: Symbol
|
8
|
+
|
9
|
+
attr_reader path: String
|
10
|
+
attr_reader params: Hash[Symbol, untyped]
|
11
|
+
|
12
|
+
def initialize: (path: String, params: Hash[Symbol, untyped]) -> void
|
13
|
+
|
14
|
+
def controller: -> String
|
15
|
+
|
16
|
+
def action: -> Symbol
|
17
|
+
|
18
|
+
private
|
19
|
+
|
20
|
+
attr_reader path_parser: PathParser
|
21
|
+
|
22
|
+
def default_controller: -> String
|
23
|
+
end
|
24
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class RequestBuilder
|
3
|
+
ARGUMENT_TOKEN: Regexp
|
4
|
+
|
5
|
+
attr_reader tokens: Array[String]
|
6
|
+
|
7
|
+
def initialize: (Array[String]) -> void
|
8
|
+
|
9
|
+
def build: -> Request
|
10
|
+
|
11
|
+
private
|
12
|
+
|
13
|
+
def path: -> String
|
14
|
+
|
15
|
+
def params: -> Hash[Symbol, untyped]
|
16
|
+
|
17
|
+
def path_tokens: -> Array[String]
|
18
|
+
|
19
|
+
def param_tokens: -> Array[String]
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
module Kangaru
|
2
|
+
class Router
|
3
|
+
extend Forwardable
|
4
|
+
|
5
|
+
attr_reader request: Request
|
6
|
+
attr_reader namespace: Module
|
7
|
+
|
8
|
+
def initialize: (?namespace: Module) -> void
|
9
|
+
|
10
|
+
def resolve: (Request) -> void
|
11
|
+
|
12
|
+
private
|
13
|
+
|
14
|
+
@controller_class: untyped
|
15
|
+
|
16
|
+
# Delegated to command
|
17
|
+
def controller_name: -> String
|
18
|
+
def action: -> Symbol
|
19
|
+
|
20
|
+
def controller_class: -> untyped
|
21
|
+
|
22
|
+
def validate_controller_defined!: -> void
|
23
|
+
|
24
|
+
def validate_action_defined!: -> void
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Validation
|
3
|
+
class AttributeValidator
|
4
|
+
attr_reader model: untyped
|
5
|
+
attr_reader attribute: Symbol
|
6
|
+
|
7
|
+
def initialize: (model: untyped, attribute: Symbol) -> void
|
8
|
+
|
9
|
+
def validate: (Symbol, **untyped) -> void
|
10
|
+
|
11
|
+
private
|
12
|
+
|
13
|
+
def validator_name: (Symbol) -> String
|
14
|
+
|
15
|
+
def load_validator: (
|
16
|
+
validator: Symbol,
|
17
|
+
params: Hash[Symbol, untyped]
|
18
|
+
) -> Validators::Validator
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Validation
|
3
|
+
class Error
|
4
|
+
MESSAGES: Hash[Symbol, String]
|
5
|
+
|
6
|
+
attr_reader attribute: Symbol
|
7
|
+
attr_reader type: Symbol
|
8
|
+
|
9
|
+
def initialize: (attribute: Symbol, type: Symbol) -> void
|
10
|
+
|
11
|
+
def full_message: -> String
|
12
|
+
|
13
|
+
private
|
14
|
+
|
15
|
+
def human_attribute: -> String
|
16
|
+
|
17
|
+
def message: -> String
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module Kangaru
|
2
|
+
module Validators
|
3
|
+
class Validator
|
4
|
+
attr_reader model: untyped
|
5
|
+
attr_reader attribute: Symbol
|
6
|
+
attr_reader params: Hash[Symbol, untyped]
|
7
|
+
attr_reader value: untyped
|
8
|
+
|
9
|
+
def initialize: (
|
10
|
+
model: untyped,
|
11
|
+
attribute: Symbol,
|
12
|
+
params: Hash[Symbol, untyped]
|
13
|
+
) -> void
|
14
|
+
|
15
|
+
def validate: -> void
|
16
|
+
|
17
|
+
def add_error!: (Symbol) -> void
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
data/sig/kangaru.rbs
ADDED
@@ -0,0 +1,29 @@
|
|
1
|
+
module Kangaru
|
2
|
+
VERSION: String
|
3
|
+
|
4
|
+
COLLAPSED_DIRS: Array[String]
|
5
|
+
DEFAULT_ENV: Symbol
|
6
|
+
INFLECTIONS: Hash[String, String]
|
7
|
+
|
8
|
+
extend ClassMethods
|
9
|
+
|
10
|
+
module ClassMethods
|
11
|
+
@loader: Zeitwerk::Loader
|
12
|
+
|
13
|
+
attr_accessor application: Application?
|
14
|
+
attr_accessor env: Symbol
|
15
|
+
|
16
|
+
def application!: -> Application
|
17
|
+
|
18
|
+
def env?: (Symbol) -> bool
|
19
|
+
|
20
|
+
def eager_load: (Module) -> void
|
21
|
+
|
22
|
+
def test?: -> bool
|
23
|
+
end
|
24
|
+
|
25
|
+
# Included in target applications that extend Kangaru::Initialiser.
|
26
|
+
interface _ApplicationMethods
|
27
|
+
include InjectedMethods::_InjectedMethods
|
28
|
+
end
|
29
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: kangaru
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Chris Welham
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-11-
|
11
|
+
date: 2023-11-08 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: colorize
|
@@ -128,6 +128,8 @@ files:
|
|
128
128
|
- lib/kangaru/inflectors/tokeniser.rb
|
129
129
|
- lib/kangaru/initialiser.rb
|
130
130
|
- lib/kangaru/initialisers/rspec.rb
|
131
|
+
- lib/kangaru/initialisers/rspec/kangaru_helper.rb
|
132
|
+
- lib/kangaru/initialisers/rspec/request_helper.rb
|
131
133
|
- lib/kangaru/injected_methods.rb
|
132
134
|
- lib/kangaru/model.rb
|
133
135
|
- lib/kangaru/patches/constantise.rb
|
@@ -147,10 +149,60 @@ files:
|
|
147
149
|
- lib/kangaru/version.rb
|
148
150
|
- rbs_collection.lock.yaml
|
149
151
|
- rbs_collection.yaml
|
150
|
-
|
152
|
+
- sig/class.rbs
|
153
|
+
- sig/kangaru.rbs
|
154
|
+
- sig/kangaru/application.rbs
|
155
|
+
- sig/kangaru/argument_parser.rbs
|
156
|
+
- sig/kangaru/components/component.rbs
|
157
|
+
- sig/kangaru/concerns/attributes_concern.rbs
|
158
|
+
- sig/kangaru/concerns/concern.rbs
|
159
|
+
- sig/kangaru/concerns/configurable.rbs
|
160
|
+
- sig/kangaru/concerns/validatable.rbs
|
161
|
+
- sig/kangaru/config.rbs
|
162
|
+
- sig/kangaru/configurators.rbs
|
163
|
+
- sig/kangaru/configurators/application_configurator.rbs
|
164
|
+
- sig/kangaru/configurators/configurator.rbs
|
165
|
+
- sig/kangaru/configurators/database_configurator.rbs
|
166
|
+
- sig/kangaru/configurators/external_configurator.rbs
|
167
|
+
- sig/kangaru/configurators/open_configurator.rbs
|
168
|
+
- sig/kangaru/configurators/request_configurator.rbs
|
169
|
+
- sig/kangaru/controller.rbs
|
170
|
+
- sig/kangaru/database.rbs
|
171
|
+
- sig/kangaru/inflectors/class_inflector.rbs
|
172
|
+
- sig/kangaru/inflectors/constant_inflector.rbs
|
173
|
+
- sig/kangaru/inflectors/constantiser.rbs
|
174
|
+
- sig/kangaru/inflectors/human_inflector.rbs
|
175
|
+
- sig/kangaru/inflectors/inflector.rbs
|
176
|
+
- sig/kangaru/inflectors/inflector_macros.rbs
|
177
|
+
- sig/kangaru/inflectors/path_inflector.rbs
|
178
|
+
- sig/kangaru/inflectors/screaming_snakecase_inflector.rbs
|
179
|
+
- sig/kangaru/inflectors/snakecase_inflector.rbs
|
180
|
+
- sig/kangaru/inflectors/tokeniser.rbs
|
181
|
+
- sig/kangaru/initialiser.rbs
|
182
|
+
- sig/kangaru/initialisers/rspec.rbs
|
183
|
+
- sig/kangaru/injected_methods.rbs
|
184
|
+
- sig/kangaru/model.rbs
|
185
|
+
- sig/kangaru/patches/constantise.rbs
|
186
|
+
- sig/kangaru/patches/inflections.rbs
|
187
|
+
- sig/kangaru/patches/source.rbs
|
188
|
+
- sig/kangaru/patches/symboliser.rbs
|
189
|
+
- sig/kangaru/path_parser.rbs
|
190
|
+
- sig/kangaru/paths.rbs
|
191
|
+
- sig/kangaru/renderer.rbs
|
192
|
+
- sig/kangaru/request.rbs
|
193
|
+
- sig/kangaru/request_builder.rbs
|
194
|
+
- sig/kangaru/router.rbs
|
195
|
+
- sig/kangaru/validation/attribute_validator.rbs
|
196
|
+
- sig/kangaru/validation/error.rbs
|
197
|
+
- sig/kangaru/validators/required_validator.rbs
|
198
|
+
- sig/kangaru/validators/validator.rbs
|
199
|
+
homepage: https://github.com/apexatoll/kangaru
|
151
200
|
licenses:
|
152
201
|
- MIT
|
153
|
-
metadata:
|
202
|
+
metadata:
|
203
|
+
homepage_uri: https://github.com/apexatoll/kangaru
|
204
|
+
source_code_uri: https://github.com/apexatoll/kangaru
|
205
|
+
changelog_uri: https://github.com/apexatoll/kangaru/releases
|
154
206
|
post_install_message:
|
155
207
|
rdoc_options: []
|
156
208
|
require_paths:
|