camille 1.0.0 → 1.2.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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: a1ea493a56729858449f5d04a2242a0920a1aff7e345fde52d7fed3061b9cb3e
4
- data.tar.gz: 624ef2a41e1c413e8e288de97f6b464f02ce51d9f2cda9eeed9b7ba4a818aaad
3
+ metadata.gz: 82a091b46cd7266990fb540e54febefd78773260f780283d624fa88321090d81
4
+ data.tar.gz: 33a660f689f967f3be04e9bc70b15214fa28d36c74df223357f66dbe17bce7b1
5
5
  SHA512:
6
- metadata.gz: 3bf2d9199a22c3a1a6f0c81538d93e87f4aacf073c52866fed0d07156f44af98d059c6559071554e275dc754bfd5413284acebf841e59f11659acfa9527827bc
7
- data.tar.gz: 8b249d54deee18c77faebe8da95eda1ff6bae624daf67f9db1e54225951fca9259c5ef58f0c22393806ec5225c007f6962cdb377eff572a2bc20c97bb5c48859
6
+ metadata.gz: 32442ecdc91cd62092d3d49ce67c6cfe2ccedaeb1a285a1e6f44615792ce9408d8d245690cb96ff269853a72d3807080f1bdcb88639439b4e957a4d8ced726f4
7
+ data.tar.gz: 21398e4687f2a7e3f56b06b86ad1c86a80bbe8719c57227a413df09ad7251c28e86af89145b9656243d80c68b9eeb4a9dea412b1a6e67c6189cc6b55d2af943f
data/CHANGELOG.md CHANGED
@@ -1,5 +1,17 @@
1
1
  # Changelog
2
2
 
3
+ ## 1.2.0
4
+
5
+ ### Added
6
+
7
+ * Added `TypeLiteralGenerator` and `SchemaLiteralGenerator` to allow partial endpoint generation with `CodeGenerator`.
8
+
9
+ ## 1.1.0
10
+
11
+ ### Added
12
+
13
+ * Added support for HTTP verbs `put`, `patch` and `delete`.
14
+
3
15
  ## 1.0.0
4
16
 
5
17
  ### Changed
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- camille (0.6.4)
4
+ camille (1.1.0)
5
5
  rails (>= 6.1, < 8.1)
6
6
 
7
7
  GEM
@@ -108,6 +108,7 @@ GEM
108
108
  net-smtp
109
109
  marcel (1.0.4)
110
110
  mini_mime (1.1.5)
111
+ mini_portile2 (2.8.9)
111
112
  minitest (5.25.4)
112
113
  net-imap (0.5.6)
113
114
  date
@@ -119,6 +120,9 @@ GEM
119
120
  net-smtp (0.5.1)
120
121
  net-protocol
121
122
  nio4r (2.7.4)
123
+ nokogiri (1.17.2)
124
+ mini_portile2 (~> 2.8.2)
125
+ racc (~> 1.4)
122
126
  nokogiri (1.17.2-x86_64-linux)
123
127
  racc (~> 1.4)
124
128
  psych (5.2.1)
@@ -210,4 +214,4 @@ DEPENDENCIES
210
214
  rspec-rails
211
215
 
212
216
  BUNDLED WITH
213
- 2.2.33
217
+ 2.7.2
data/README.md CHANGED
@@ -1,5 +1,7 @@
1
1
  # Camille
2
2
 
3
+ ![Gem Version](https://img.shields.io/gem/v/camille)
4
+
3
5
  ## Why?
4
6
 
5
7
  Traditionally, the JSON response from a Rails API server isn't typed. So even if we have TypeScript at the front-end, we still have little guarantee that our back-end would return the correct type and structure of data.
@@ -90,7 +92,7 @@ The `params` type for an endpoint is required to be an object type, or a hash in
90
92
 
91
93
  Camille will automatically add a Rails route for each endpoint. You don't need to do anything other than having the schema file in place.
92
94
 
93
- When defining an endpoint, you can also use `post` instead of `get` for non-idempotent requests. However, no other HTTP verbs are supported, because verbs in RESTful like `patch` and `delete` indicate what we do on resources, but in RPC-style design each request is merely a function call that does not concern RESTful resources.
95
+ When defining an endpoint, you can use any of `get`, `post`, `put`, `patch`, or `delete`.
94
96
 
95
97
  ### Custom types
96
98
 
@@ -1,21 +1,38 @@
1
1
  require 'stringio'
2
2
 
3
3
  module Camille
4
- module CodeGenerator
5
- def self.generate_ts
4
+ class CodeGenerator
5
+ def initialize types_literal_lines: Camille::Types.literal_lines, schemas_literal_lines: Camille::Schemas.literal_lines
6
+ @types_literal_lines = types_literal_lines
7
+ @schemas_literal_lines = schemas_literal_lines
8
+ end
9
+
10
+ def generate_ts
6
11
  io = StringIO.new
7
- io.puts Camille::Configuration.ts_header
8
- io.puts
9
- Camille::Types.literal_lines.each do |line|
10
- io.puts "export #{line}"
11
- end
12
- io.puts
13
- io.print "export default "
14
- Camille::Schemas.literal_lines.each do |line|
15
- io.puts line
16
- end
12
+ generate_header io
13
+ generate_types io
14
+ generate_schemas io
17
15
  io.string
18
16
  end
19
17
 
18
+ private
19
+ def generate_header io
20
+ io.puts Camille::Configuration.ts_header
21
+ io.puts
22
+ end
23
+
24
+ def generate_types io
25
+ @types_literal_lines.each do |line|
26
+ io.puts "export #{line}"
27
+ end
28
+ io.puts
29
+ end
30
+
31
+ def generate_schemas io
32
+ io.print "export default "
33
+ @schemas_literal_lines.each do |line|
34
+ io.puts line
35
+ end
36
+ end
20
37
  end
21
38
  end
@@ -4,7 +4,7 @@ module Camille
4
4
  class MainController < ActionController::Base
5
5
  def endpoints_ts
6
6
  Camille::Loader.check_and_raise_exception
7
- render plain: Camille::CodeGenerator.generate_ts
7
+ render plain: Camille::CodeGenerator.new.generate_ts
8
8
  end
9
9
  end
10
10
  end
@@ -46,5 +46,17 @@ module Camille
46
46
  def self.post name, &block
47
47
  define_endpoint :post, name, &block
48
48
  end
49
+
50
+ def self.put name, &block
51
+ define_endpoint :put, name, &block
52
+ end
53
+
54
+ def self.patch name, &block
55
+ define_endpoint :patch, name, &block
56
+ end
57
+
58
+ def self.delete name, &block
59
+ define_endpoint :delete, name, &block
60
+ end
49
61
  end
50
- end
62
+ end
@@ -0,0 +1,51 @@
1
+ module Camille
2
+ class SchemaLiteralGenerator
3
+ def initialize schemas
4
+ @schemas = schemas
5
+ end
6
+
7
+ def literal_lines
8
+ [
9
+ Camille::Line.new('{'),
10
+ tree_literal_lines(namespace_tree).map(&:do_indent),
11
+ Camille::Line.new('}')
12
+ ]
13
+ end
14
+
15
+ private
16
+ def namespace_tree
17
+ tree = {}
18
+
19
+ @schemas.sort_by(&:klass_name).each do |s|
20
+ path = s.klass_name.split('::')
21
+ *namespaces, schema_name = path
22
+
23
+ level = namespaces.inject(tree) do |level, namespace|
24
+ level[namespace] ||= {}
25
+ level[namespace]
26
+ end
27
+
28
+ level[schema_name] = s
29
+ end
30
+
31
+ tree
32
+ end
33
+
34
+ def tree_literal_lines tree
35
+ tree.map do |key, value|
36
+ if value.is_a? ::Hash
37
+ [
38
+ Camille::Line.new("#{Camille::Configuration.response_key_converter.call(key.to_s)}: {"),
39
+ tree_literal_lines(value).map(&:do_indent),
40
+ Camille::Line.new('},')
41
+ ]
42
+ else
43
+ value.literal_lines.tap do |lines|
44
+ lines.first.prepend("#{Camille::Configuration.response_key_converter.call(key.to_s)}: ")
45
+ lines.last.append(',')
46
+ end
47
+ end
48
+ end.flatten
49
+ end
50
+ end
51
+ end
@@ -1,47 +1,7 @@
1
1
  module Camille
2
2
  module Schemas
3
3
  def self.literal_lines
4
- [
5
- Camille::Line.new('{'),
6
- tree_literal_lines(namespace_tree).map(&:do_indent),
7
- Camille::Line.new('}')
8
- ]
4
+ Camille::SchemaLiteralGenerator.new(Camille::Loader.loaded_schemas).literal_lines
9
5
  end
10
-
11
- private
12
- def self.namespace_tree
13
- tree = {}
14
-
15
- Camille::Loader.loaded_schemas.sort_by(&:klass_name).each do |s|
16
- path = s.klass_name.split('::')
17
- *namespaces, schema_name = path
18
-
19
- level = namespaces.inject(tree) do |level, namespace|
20
- level[namespace] ||= {}
21
- level[namespace]
22
- end
23
-
24
- level[schema_name] = s
25
- end
26
-
27
- tree
28
- end
29
-
30
- def self.tree_literal_lines tree
31
- tree.map do |key, value|
32
- if value.is_a? ::Hash
33
- [
34
- Camille::Line.new("#{Camille::Configuration.response_key_converter.call(key.to_s)}: {"),
35
- tree_literal_lines(value).map(&:do_indent),
36
- Camille::Line.new('},')
37
- ]
38
- else
39
- value.literal_lines.tap do |lines|
40
- lines.first.prepend("#{Camille::Configuration.response_key_converter.call(key.to_s)}: ")
41
- lines.last.append(',')
42
- end
43
- end
44
- end.flatten
45
- end
46
6
  end
47
7
  end
@@ -0,0 +1,14 @@
1
+ module Camille
2
+ class TypeLiteralGenerator
3
+ def initialize types
4
+ @types = types
5
+ end
6
+
7
+ def literal_lines
8
+ @types.sort_by(&:klass_name).map do |type|
9
+ instance = type.new
10
+ Camille::Line.new("type #{instance.literal} = #{instance.underlying.literal}")
11
+ end
12
+ end
13
+ end
14
+ end
data/lib/camille/types.rb CHANGED
@@ -1,10 +1,7 @@
1
1
  module Camille
2
2
  module Types
3
3
  def self.literal_lines
4
- Camille::Loader.loaded_types.sort_by(&:klass_name).map do |type|
5
- instance = type.new
6
- Camille::Line.new("type #{instance.literal} = #{instance.underlying.literal}")
7
- end
4
+ Camille::TypeLiteralGenerator.new(Camille::Loader.loaded_types).literal_lines
8
5
  end
9
6
  end
10
7
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Camille
4
- VERSION = "1.0.0"
4
+ VERSION = "1.2.0"
5
5
  end
data/lib/camille.rb CHANGED
@@ -40,6 +40,8 @@ require_relative "camille/railtie"
40
40
  require_relative "camille/controller"
41
41
  require_relative "camille/loader"
42
42
  require_relative "camille/configuration"
43
+ require_relative "camille/type_literal_generator"
44
+ require_relative "camille/schema_literal_generator"
43
45
  require_relative "camille/code_generator"
44
46
  require_relative "camille/main_controller"
45
47
  require_relative "camille/key_converter"
@@ -57,6 +59,6 @@ module Camille
57
59
  end
58
60
 
59
61
  def self.generate_ts
60
- Camille::CodeGenerator.generate_ts
62
+ Camille::CodeGenerator.new.generate_ts
61
63
  end
62
64
  end
metadata CHANGED
@@ -1,14 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: camille
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.0
4
+ version: 1.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - merely
8
- autorequire:
9
8
  bindir: exe
10
9
  cert_chain: []
11
- date: 2025-04-19 00:00:00.000000000 Z
10
+ date: 1980-01-02 00:00:00.000000000 Z
12
11
  dependencies:
13
12
  - !ruby/object:Gem::Dependency
14
13
  name: rails
@@ -77,11 +76,13 @@ files:
77
76
  - lib/camille/railtie.rb
78
77
  - lib/camille/rendered.rb
79
78
  - lib/camille/schema.rb
79
+ - lib/camille/schema_literal_generator.rb
80
80
  - lib/camille/schemas.rb
81
81
  - lib/camille/syntax.rb
82
82
  - lib/camille/type.rb
83
83
  - lib/camille/type_error.rb
84
84
  - lib/camille/type_error_printer.rb
85
+ - lib/camille/type_literal_generator.rb
85
86
  - lib/camille/types.rb
86
87
  - lib/camille/types/any.rb
87
88
  - lib/camille/types/array.rb
@@ -107,7 +108,6 @@ licenses:
107
108
  metadata:
108
109
  homepage_uri: https://github.com/onyxblade/camille
109
110
  source_code_uri: https://github.com/onyxblade/camille
110
- post_install_message:
111
111
  rdoc_options: []
112
112
  require_paths:
113
113
  - lib
@@ -122,8 +122,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
122
122
  - !ruby/object:Gem::Version
123
123
  version: '0'
124
124
  requirements: []
125
- rubygems_version: 3.5.16
126
- signing_key:
125
+ rubygems_version: 3.6.9
127
126
  specification_version: 4
128
127
  summary: Typed API schema for Rails with TypeScript codegen
129
128
  test_files: []