schemable 0.1.1 → 0.1.3

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: 23d1aa40009aa3403271634f66a3bde5b008708f20d65854f623760fe7be1a1c
4
- data.tar.gz: 2afc50495c89114cf8215eeb3793d3abc30f4339b81cd19dc2372eb5dc7196fb
3
+ metadata.gz: 61661d657d9eb811ae32e778d400c824664209bf63f0602e9425c0749af794d7
4
+ data.tar.gz: b19b40efeb1550826ec20d6dad94d3abdd8eca92ed211837198f91a8eb3be37f
5
5
  SHA512:
6
- metadata.gz: 1e5e2039c722547d1464572d4afed575c63f15fde2c3320b01d9e20884e2044673a792ab0716c5a5f87769df4e58af40c79e29683c2fae11f816533dae13bb68
7
- data.tar.gz: dbd6c7b1ac35ce5045e1ed2a00eafffb0758fb03937942e6bb435c1dafb1b06c6f9db756295faf9ed5db99f90dbd202f47921b0e0d22f3beb90592342e763cd1
6
+ metadata.gz: f8dff9116105d5e6bf59a22d08f76c631eabc0fd04964d59ac9d54d3f9e8d2fd538e50720e38f48172817b895798c037a148d8bcfa1536e1fa052035537b9c4f
7
+ data.tar.gz: bbe13dd62692efe72f6311f30fd4a00e4314b4aa557227d7b1bcb40e5f9643c35285d810292069bbf4a2317cff25f88158584e10141e604f3be8822fe6dcb75a
data/.rubocop.yml CHANGED
@@ -108,10 +108,24 @@ Metrics/AbcSize:
108
108
  Metrics/MethodLength:
109
109
  Enabled: false
110
110
  Metrics/CyclomaticComplexity:
111
- Max: 15
111
+ Enabled: false
112
112
  Metrics/PerceivedComplexity:
113
- Max: 15
113
+ Enabled: false
114
114
  Lint/DuplicateMethods: # Disables duplicate methods warning
115
115
  Enabled: false
116
116
  Gemspec/RequiredRubyVersion: # Disables required ruby version warning
117
117
  Enabled: false
118
+ Metrics/ParameterLists: # Disables parameter lists warning
119
+ Enabled: false
120
+ Lint/NextWithoutAccumulator: # Disables next without accumulator warning
121
+ Enabled: false
122
+ Lint/ShadowingOuterLocalVariable: # Disables shadowing outer local variable warning
123
+ Enabled: false
124
+ Metrics/ModuleLength: # Disables module length warning
125
+ Enabled: false
126
+ Layout/EmptyLinesAroundClassBody: # Disables empty lines around class body warning
127
+ Enabled: false
128
+ Layout/HeredocIndentation: # Disables heredoc indentation warning
129
+ Enabled: false
130
+ Layout/ClosingHeredocIndentation: # Disables closing heredoc indentation warning
131
+ Enabled: false
data/Gemfile CHANGED
@@ -1,14 +1,15 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- source "https://rubygems.org"
3
+ source 'https://rubygems.org'
4
4
 
5
5
  gemspec
6
6
 
7
- gem "rake", "~> 13.0"
8
- gem "rspec", "~> 3.0"
9
- gem "rubocop", "~> 1.21"
7
+ gem 'rake', '~> 13.0.6'
8
+ gem 'rspec', '~> 3.12'
9
+ gem 'rubocop', '~> 1.55'
10
+ gem 'rubocop-rails', '~> 2.20.2'
10
11
 
11
12
  group :development, :test do
12
- gem 'jsonapi-rails', '~> 0.4.1'
13
13
  gem 'factory_bot_rails', '~> 6.2'
14
- end
14
+ gem 'jsonapi-rails', '~> 0.4.1'
15
+ end
data/Gemfile.lock CHANGED
@@ -1,9 +1,9 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- schemable (0.1.0)
5
- factory_bot_rails (>= 6.2.0)
6
- jsonapi-rails (>= 0.4.1)
4
+ schemable (0.1.3)
5
+ factory_bot_rails (~> 6.2.0)
6
+ jsonapi-rails (~> 0.4.1)
7
7
 
8
8
  GEM
9
9
  remote: https://rubygems.org/
@@ -51,6 +51,7 @@ GEM
51
51
  jsonapi-renderer (0.2.2)
52
52
  jsonapi-serializable (0.3.1)
53
53
  jsonapi-renderer (~> 0.2.0)
54
+ language_server-protocol (3.17.0.3)
54
55
  loofah (2.21.2)
55
56
  crass (~> 1.0.2)
56
57
  nokogiri (>= 1.12.0)
@@ -59,8 +60,9 @@ GEM
59
60
  nokogiri (1.14.4-x86_64-linux)
60
61
  racc (~> 1.4)
61
62
  parallel (1.23.0)
62
- parser (3.2.2.1)
63
+ parser (3.2.2.3)
63
64
  ast (~> 2.4.1)
65
+ racc
64
66
  racc (1.6.2)
65
67
  rack (2.2.7)
66
68
  rack-test (2.1.0)
@@ -79,8 +81,8 @@ GEM
79
81
  zeitwerk (~> 2.5)
80
82
  rainbow (3.1.1)
81
83
  rake (13.0.6)
82
- regexp_parser (2.8.0)
83
- rexml (3.2.5)
84
+ regexp_parser (2.8.1)
85
+ rexml (3.2.6)
84
86
  rspec (3.12.0)
85
87
  rspec-core (~> 3.12.0)
86
88
  rspec-expectations (~> 3.12.0)
@@ -94,18 +96,23 @@ GEM
94
96
  diff-lcs (>= 1.2.0, < 2.0)
95
97
  rspec-support (~> 3.12.0)
96
98
  rspec-support (3.12.0)
97
- rubocop (1.51.0)
99
+ rubocop (1.55.0)
98
100
  json (~> 2.3)
101
+ language_server-protocol (>= 3.17.0)
99
102
  parallel (~> 1.10)
100
- parser (>= 3.2.0.0)
103
+ parser (>= 3.2.2.3)
101
104
  rainbow (>= 2.2.2, < 4.0)
102
105
  regexp_parser (>= 1.8, < 3.0)
103
106
  rexml (>= 3.2.5, < 4.0)
104
- rubocop-ast (>= 1.28.0, < 2.0)
107
+ rubocop-ast (>= 1.28.1, < 2.0)
105
108
  ruby-progressbar (~> 1.7)
106
109
  unicode-display_width (>= 2.4.0, < 3.0)
107
- rubocop-ast (1.28.1)
110
+ rubocop-ast (1.29.0)
108
111
  parser (>= 3.2.1.0)
112
+ rubocop-rails (2.20.2)
113
+ activesupport (>= 4.2.0)
114
+ rack (>= 1.1)
115
+ rubocop (>= 1.33.0, < 2.0)
109
116
  ruby-progressbar (1.13.0)
110
117
  thor (1.2.2)
111
118
  tzinfo (2.0.6)
@@ -119,9 +126,10 @@ PLATFORMS
119
126
  DEPENDENCIES
120
127
  factory_bot_rails (~> 6.2)
121
128
  jsonapi-rails (~> 0.4.1)
122
- rake (~> 13.0)
123
- rspec (~> 3.0)
124
- rubocop (~> 1.21)
129
+ rake (~> 13.0.6)
130
+ rspec (~> 3.12)
131
+ rubocop (~> 1.55)
132
+ rubocop-rails (~> 2.20.2)
125
133
  schemable!
126
134
 
127
135
  BUNDLED WITH
data/README.md CHANGED
@@ -1,24 +1,180 @@
1
1
  # Schemable
2
2
 
3
- TODO: Delete this and the text below, and describe your gem
4
-
5
- Welcome to your new gem! In this directory, you'll find the files you need to be able to package up your Ruby library into a gem. Put your Ruby code in the file `lib/schemable`. To experiment with that code, run `bin/console` for an interactive prompt.
3
+ The Schemable gem provides a simple way to define a schema for a Rails model in [JSONAPI](https://jsonapi.org/) format. It can automatically generate a schema for a model based on the model's factory and the model's attributes. It is also highly customizable, allowing you to modify the schema to your liking by overriding the default methods.
6
4
 
7
5
  ## Installation
8
6
 
9
- TODO: Replace `UPDATE_WITH_YOUR_GEM_NAME_PRIOR_TO_RELEASE_TO_RUBYGEMS_ORG` with your gem name right after releasing it to RubyGems.org. Please do not do it earlier due to security reasons. Alternatively, replace this section with instructions to install your gem from git if you don't plan to release to RubyGems.org.
7
+ Add this line to your application's Gemfile:
8
+
9
+ ```ruby
10
+ gem 'schemable'
11
+ ```
10
12
 
11
- Install the gem and add to the application's Gemfile by executing:
13
+ And then execute:
12
14
 
13
- $ bundle add UPDATE_WITH_YOUR_GEM_NAME_PRIOR_TO_RELEASE_TO_RUBYGEMS_ORG
15
+ $ bundle install
14
16
 
15
- If bundler is not being used to manage dependencies, install the gem by executing:
17
+ Or install it yourself as:
16
18
 
17
- $ gem install UPDATE_WITH_YOUR_GEM_NAME_PRIOR_TO_RELEASE_TO_RUBYGEMS_ORG
19
+ $ gem install schemable
18
20
 
19
21
  ## Usage
20
22
 
21
- TODO: Write usage instructions here
23
+ The installation command above will install the Schemable gem and its dependencies. However, in order for Schemable to work, you must also add the following files to your Rails application:
24
+
25
+ - `app/helpers/serializers_helper.rb` - This file contains the `serializers_map` helper method, which is used to map a model to its serializer.
26
+ - `spec/swagger/common_definitions.rb` - This file contains the `aggregate` method, which is used to aggregate the schemas of all the models in your application into a single place. This file is recommeded, but not required. If you do not use this file, you will need to manually aggregate the schemas of all the models in your application into a single place.
27
+
28
+ To generate these files, run the following command:
29
+
30
+ ```ruby
31
+ rails g schemable:install
32
+ ```
33
+
34
+ ### Generating Definition Files
35
+
36
+ The Schemable gem provides a generator that can be used to generate definition files for your models. To generate a definition file for a model, run the following command:
37
+
38
+ ```ruby
39
+ rails g schemable:model --model_name <model_name>
40
+ ```
41
+
42
+ This will generate a definition file for the specified model in the `lib/swagger/definitions` directory. The definition file will be named `<model_name>.rb`. This file will have the bare minimum code required to generate a schema for the model. You can then modify the definition file to your liking by overriding the default methods. For example, you can add or remove attributes from the schema, or you can add or remove relationships from the schema. You can also add custom attributes to the schema. For more information on how to customize the schema, see the [Customizing the Schema](#customizing-the-schema) section below.
43
+
44
+ ## Customizing the Schema
45
+
46
+ The Schemable gem provides a number of methods that can be used to customize the schema. These methods are defined in the `Schemable` module of the gem. To customize the schema, simply override the default methods in the definition file for the model. The following is a list of the methods that can be overridden:
47
+
48
+ | WARNING: please read the method inline documentation before overriding to avoid any unexpected behavior. |
49
+ | -------------------------------------------------------------------------------------------------------- |
50
+
51
+ The list of methods that can be overridden are as follows:
52
+
53
+ | Method Name | Description |
54
+ | -------------------------------- | ---------------------------------------------------------------------------------------------------------- |
55
+ | `serializer` | Returns the serializer class. |
56
+ | `attributes` | Returns the attributes that are auto generated from the model. |
57
+ | `relationships` | Returns the relationships in the format of { belongs_to: {}, has_many: {} }. |
58
+ | `array_type` | Returns the type of arrays in the model that needs to be manually defined. |
59
+ | `optional_request_attributes` | Returns the attributes that are optional in the request schema. |
60
+ | `nullable_attributes` | Returns the attributes that are nullable in the request/response schema. |
61
+ | `additional_request_attributes` | Returns the attributes that are additional in the request schema. |
62
+ | `additional_response_attributes` | Returns the attributes that are additional in the response schema. |
63
+ | `additional_response_relations` | Returns the relationships that are additional in the response schema (Appended to relationships). |
64
+ | `additional_response_included` | Returns the included that are additional in the response schema (Appended to included). |
65
+ | `excluded_request_attributes` | Returns the attributes that are excluded from the request schema. |
66
+ | `excluded_response_attributes` | Returns the attributes that are excluded from the response schema. |
67
+ | `excluded_response_relations` | Returns the relationships that are excluded from the response schema. |
68
+ | `excluded_response_included` | (not implemented yet) Returns the included that are excluded from the response schema. |
69
+ | `nested_relationships` | Returns the relationships to be further expanded in the response schema. |
70
+ | `model` | Returns the model class (Constantized from the definition class name). |
71
+ | `model_name` | Returns the model name. Used for schema type naming. |
72
+ | `definitions` | Returns the generated schemas in JSONAPI format (It is recommended to override this method to your liking) |
73
+
74
+ The following is an example of a definition file for a model that has been customized:
75
+
76
+ <Details>
77
+ <Summary>Click to view the example</Summary>
78
+
79
+ ```ruby
80
+ module Swagger
81
+ module Definitions
82
+ class UserApplication
83
+
84
+ include Schemable
85
+ include SerializersHelper
86
+
87
+ attr_accessor :instance
88
+
89
+ def initialize
90
+ @instance ||= JSONAPI::Serializable::Renderer.new.render(FactoryBot.create(:user, :with_user_application_applicants), class: serializers_map, include: [])
91
+ end
92
+
93
+ def serializer
94
+ V1::UserApplicationSerializer
95
+ end
96
+
97
+ def relationships
98
+ {
99
+ belongs_to: {
100
+ category: Swagger::Definitions::Category,
101
+ },
102
+ has_many: {
103
+ applicants: Swagger::Definitions::Applicant,
104
+ }
105
+ }
106
+ end
107
+
108
+ def array_types
109
+ {
110
+ applicant_ids:
111
+ {
112
+ type: :array,
113
+ items:
114
+ {
115
+ type: :string
116
+ },
117
+ nullable: true
118
+ }
119
+ }
120
+ end
121
+
122
+ def excluded_request_attributes
123
+ %i[id updated_at created_at applicant_ids comment]
124
+ end
125
+
126
+ def additional_request_attributes
127
+ {
128
+ applicants_attributes:
129
+ {
130
+ type: :array,
131
+ items: {
132
+ anyOf: [
133
+ {
134
+ type: :object,
135
+ properties: Swagger::Definitions::Applicant.new.request_schema.as_json['properties']['data']['properties']
136
+ }
137
+ ]
138
+ }
139
+ }
140
+ }
141
+ end
142
+
143
+ def additional_response_attributes
144
+ {
145
+ comment: { type: :object, properties: {}, nullable: true }
146
+ }
147
+ end
148
+
149
+ def nested_relationships
150
+ {
151
+ applicants: {
152
+ belongs_to: {
153
+ district: Swagger::Definitions::District,
154
+ province: Swagger::Definitions::Province,
155
+ },
156
+ has_many: {
157
+ attachments: Swagger::Definitions::Upload,
158
+ }
159
+ }
160
+ }
161
+ end
162
+
163
+ def self.definitions
164
+ schema_instance = self.new
165
+ [
166
+ "#{schema_instance.model}Request": schema_instance.camelize_keys(schema_instance.request_schema),
167
+ "#{schema_instance.model}Response": schema_instance.camelize_keys(schema_instance.response_schema(expand: true, exclude_from_expansion: [:category], multi: true)),
168
+ "#{schema_instance.model}ResponseExpanded": schema_instance.camelize_keys(schema_instance.response_schema(expand: true, nested: true))
169
+ ]
170
+ end
171
+ end
172
+ end
173
+ end
174
+
175
+ ```
176
+
177
+ </Details>
22
178
 
23
179
  ## Development
24
180
 
data/Rakefile CHANGED
@@ -1,11 +1,11 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require "bundler/gem_tasks"
4
- require "rspec/core/rake_task"
3
+ require 'bundler/gem_tasks'
4
+ require 'rspec/core/rake_task'
5
5
 
6
6
  RSpec::Core::RakeTask.new(:spec)
7
7
 
8
- require "rubocop/rake_task"
8
+ require 'rubocop/rake_task'
9
9
 
10
10
  RuboCop::RakeTask.new
11
11
 
@@ -4,8 +4,8 @@ module Schemable
4
4
  source_root File.expand_path('../../templates', __dir__)
5
5
  class_option :model_name, type: :string, default: 'Model', desc: 'Name of the model'
6
6
 
7
- def initialize(*)
8
- super(*)
7
+ def initialize(*args)
8
+ super(*args)
9
9
  end
10
10
 
11
11
  def copy_initializer
@@ -4,15 +4,15 @@ module Schemable
4
4
  source_root File.expand_path('../../templates', __dir__)
5
5
  class_option :model_name, type: :string, default: 'Model', desc: 'Name of the model'
6
6
 
7
- def initialize(*)
8
- super(*)
7
+ def initialize(*args)
8
+ super(*args)
9
9
 
10
10
  @model_name = options[:model_name]
11
11
  @model_name != 'Model' || raise('Model name is required')
12
12
  end
13
13
 
14
14
  def copy_initializer
15
- target_path = "lib/swagger/definitions/#{@model_name.underscore.downcase.singlurize}.rb"
15
+ target_path = "lib/swagger/definitions/#{@model_name.underscore.downcase.singularize}.rb"
16
16
 
17
17
  if Rails.root.join(target_path).exist?
18
18
  say_status('skipped', 'Model definition already exists')
@@ -29,15 +29,19 @@ module Swagger
29
29
  attr_accessor :instance
30
30
 
31
31
  def initialize
32
- @instance ||= JSONAPI::Serializable::Renderer.new.render(FactoryBot.create(:#{@model_name.underscore.downcase.singlurize}), class: serializers_map, include: [])
32
+ @instance ||= JSONAPI::Serializable::Renderer.new.render(FactoryBot.create(:#{@model_name.underscore.downcase.singularize}), class: serializers_map, include: [])
33
33
  end
34
34
 
35
35
  def serializer
36
36
  V1::#{@model_name.classify}Serializer
37
37
  end
38
38
 
39
- def excluded_request_attributes
40
- %i[id updatedAt createdAt]
39
+ def excluded_create_request_attributes
40
+ %i[updated_at created_at]
41
+ end
42
+
43
+ def excluded_update_request_attributes
44
+ %i[updated_at created_at]
41
45
  end
42
46
  end
43
47
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Schemable
4
- VERSION = "0.1.1"
4
+ VERSION = '0.1.3'
5
5
  end