rbs_active_hash 1.1.1 → 1.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: e2eb5b40b0f8db429b0de00b935811812863b1ea0b28760068bfc34a69bf0f5e
4
- data.tar.gz: 81c7d9ee55d7735c1ff897adb08c8b924bfedee14ab537a35dd187e9679c49f3
3
+ metadata.gz: f12b41b5d7f8ba64d20e27c4f7f21e677cd0ee2fa8f08db13ec5daef40c9b55a
4
+ data.tar.gz: 1a21add9c8606ac60158813d275a2e702353e7d70b61019228f1b1ed152d81f9
5
5
  SHA512:
6
- metadata.gz: af3b784c8dea4a0106aca8f813162f1cb91fafd4a3a892234caa1fb3cfc264222eebe0ba25f74b7b0133d05c96bdf859ce33f08e1ba0fb9356ee4ab0fc609e56
7
- data.tar.gz: 55ffa16dccd6b383f2cb0999d4b92eeb080b893616660d778dac2212a07b640aa754531ca50b6cf04bd0e92d0d9cea3f7729000e1b58b07c38bf6334f0c158d3
6
+ metadata.gz: 6727269c9ffe5664c7c6a342eeafb0f715ea177929e8e82c5d76ea86593c3124e07074d987ea4755fc47d041319ef81892df9a71bf16b1af505edd42357b9602
7
+ data.tar.gz: c9e7452a80261991c3d7684c41c3dc906a7b83943fa5f2189f0af9b48bd420465aa0ab7d4bbdd89fc5225605a67ec5342341796ee1b3c6b860d87e55a53b2d1d
data/Gemfile CHANGED
@@ -9,6 +9,10 @@ gem "rake", "~> 13.0"
9
9
 
10
10
  gem "rubocop", "~> 1.55"
11
11
 
12
+ group :test do
13
+ gem "activerecord"
14
+ end
15
+
12
16
  group :development do
13
17
  gem "rspec", require: false
14
18
  gem "rspec-daemon", require: false
@@ -18,6 +22,5 @@ end
18
22
 
19
23
  # dependencies only for signature
20
24
  group :signature do
21
- gem "activerecord"
22
25
  gem "railties"
23
26
  end
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- rbs_active_hash (1.1.1)
4
+ rbs_active_hash (1.2.0)
5
5
  active_hash
6
6
  rbs
7
7
  rbs_rails
@@ -113,7 +113,7 @@ GEM
113
113
  diff-lcs (>= 1.2.0, < 2.0)
114
114
  rspec-support (~> 3.12.0)
115
115
  rspec-support (3.12.0)
116
- rubocop (1.55.0)
116
+ rubocop (1.55.1)
117
117
  json (~> 2.3)
118
118
  language_server-protocol (>= 3.17.0)
119
119
  parallel (~> 1.10)
@@ -40,6 +40,7 @@ module RbsActiveHash
40
40
  <<~RBS
41
41
  #{header}
42
42
  #{enum_decls}
43
+ #{association_decls}
43
44
  #{method_decls}
44
45
  #{footer}
45
46
  RBS
@@ -97,6 +98,64 @@ module RbsActiveHash
97
98
  end
98
99
  end
99
100
 
101
+ def association_decls # rubocop:disable Metrics/AbcSize
102
+ return unless klass.ancestors.include? ::ActiveHash::Associations
103
+
104
+ path, = Object.const_source_location(klass_name)
105
+ return unless path
106
+
107
+ parser = Associations::Parser.new
108
+ parser.parse(IO.read(path.to_s), klass_name.split("::").map(&:to_sym))
109
+
110
+ <<~RBS
111
+ include ActiveHash::Associations
112
+ extend ActiveHash::Associations::Methods
113
+
114
+ #{has_many_decls(parser.has_many)}
115
+ #{has_one_decls(parser.has_one)}
116
+ #{belongs_to_decls(parser.belongs_to)}
117
+ RBS
118
+ end
119
+
120
+ def has_many_decls(definitions) # rubocop:disable Naming/PredicateName
121
+ definitions.map do |definition|
122
+ association_id, options = definition
123
+ klass = options.fetch(:class_name, association_id.to_s.classify).constantize
124
+
125
+ relation = if Object.const_defined?(:ActiveRecord) && klass.ancestors.include?(ActiveRecord::Base)
126
+ "#{klass.name}::ActiveRecord_Relation"
127
+ else
128
+ "Array[#{klass.name}]"
129
+ end
130
+
131
+ <<~RBS
132
+ def #{association_id}: () -> #{relation}
133
+ def #{association_id.to_s.underscore.singularize}_ids: () -> Array[Integer]
134
+ RBS
135
+ end.join("\n")
136
+ end
137
+
138
+ def has_one_decls(definitions) # rubocop:disable Naming/PredicateName
139
+ definitions.map do |definition|
140
+ association_id, options = definition
141
+ class_name = options.fetch(:class_name, association_id.to_s.classify).constantize
142
+
143
+ "def #{association_id}: () -> #{class_name}"
144
+ end.join("\n")
145
+ end
146
+
147
+ def belongs_to_decls(definitions)
148
+ definitions.map do |definition|
149
+ association_id, options = definition
150
+ class_name = options.fetch(:class_name, association_id.to_s.classify).constantize
151
+
152
+ <<~RBS
153
+ def #{association_id}: () -> #{class_name}
154
+ def #{association_id}=: (Integer) -> Integer
155
+ RBS
156
+ end.join("\n")
157
+ end
158
+
100
159
  def method_decls
101
160
  method_names.map do |method|
102
161
  method_type = stringify_type(method_types.fetch(method, "untyped"))
@@ -0,0 +1,91 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "rbs"
4
+
5
+ module RbsActiveHash
6
+ module Associations
7
+ class AssociationDefinition < RBS::AST::Members::Include
8
+ end
9
+
10
+ class RB < RBS::Prototype::RB
11
+ def process(node, decls:, comments:, context:)
12
+ case node.type
13
+ when :FCALL, :VCALL
14
+ case node.children.first
15
+ when :has_many, :has_one, :belongs_to
16
+ decls << AssociationDefinition.new(
17
+ name: RBS::TypeName.new(name: node.children.first, namespace: RBS::Namespace.root),
18
+ args: node.children[1],
19
+ annotations: [],
20
+ location: nil,
21
+ comment: nil
22
+ )
23
+ else
24
+ super
25
+ end
26
+ else
27
+ super
28
+ end
29
+ end
30
+ end
31
+
32
+ class Parser
33
+ attr_reader :has_many, :has_one, :belongs_to
34
+
35
+ def initialize
36
+ @has_many = []
37
+ @has_one = []
38
+ @belongs_to = []
39
+ end
40
+
41
+ def parse(string, target)
42
+ parser = RB.new
43
+ parser.parse(string)
44
+ parser.decls.each do |decl|
45
+ process(decl, target)
46
+ end
47
+ end
48
+
49
+ def process(node, target)
50
+ case node
51
+ when RBS::AST::Declarations::Module, RBS::AST::Declarations::Class
52
+ name = node.name.split
53
+ if target[...name.size] == name
54
+ node.members.each do |member|
55
+ process(member, target[name.size...].to_a)
56
+ end
57
+ end
58
+ when AssociationDefinition
59
+ process_association_definition(node) if target.empty?
60
+ end
61
+ end
62
+
63
+ def process_association_definition(node)
64
+ case node.name.name
65
+ when :has_many
66
+ association_id, args = node_to_literal(node.args)
67
+ @has_many << [association_id, args.to_h]
68
+ when :has_one
69
+ association_id, args = node_to_literal(node.args)
70
+ @has_one << [association_id, args.to_h]
71
+ when :belongs_to
72
+ association_id, args = node_to_literal(node.args)
73
+ @belongs_to << [association_id, args.to_h]
74
+ end
75
+ end
76
+
77
+ def node_to_literal(node)
78
+ case node.type
79
+ when :LIST
80
+ node.children[...-1].map { |child| node_to_literal(child) }
81
+ when :LIT, :STR
82
+ node.children.first
83
+ when :HASH
84
+ Hash[*node_to_literal(node.children.first)]
85
+ else
86
+ node
87
+ end
88
+ end
89
+ end
90
+ end
91
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module RbsActiveHash
4
- VERSION = "1.1.1"
4
+ VERSION = "1.2.0"
5
5
  end
@@ -1,6 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require_relative "rbs_active_hash/active_hash"
4
+ require_relative "rbs_active_hash/associations"
4
5
  require_relative "rbs_active_hash/version"
5
6
 
6
7
  module RbsActiveHash
@@ -2,7 +2,7 @@
2
2
  sources:
3
3
  - type: git
4
4
  name: ruby/gem_rbs_collection
5
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
5
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
6
6
  remote: https://github.com/ruby/gem_rbs_collection.git
7
7
  repo_dir: gems
8
8
  path: ".gem_rbs_collection"
@@ -16,7 +16,7 @@ gems:
16
16
  source:
17
17
  type: git
18
18
  name: ruby/gem_rbs_collection
19
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
19
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
20
20
  remote: https://github.com/ruby/gem_rbs_collection.git
21
21
  repo_dir: gems
22
22
  - name: actionview
@@ -24,7 +24,7 @@ gems:
24
24
  source:
25
25
  type: git
26
26
  name: ruby/gem_rbs_collection
27
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
27
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
28
28
  remote: https://github.com/ruby/gem_rbs_collection.git
29
29
  repo_dir: gems
30
30
  - name: active_hash
@@ -32,7 +32,7 @@ gems:
32
32
  source:
33
33
  type: git
34
34
  name: ruby/gem_rbs_collection
35
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
35
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
36
36
  remote: https://github.com/ruby/gem_rbs_collection.git
37
37
  repo_dir: gems
38
38
  - name: activemodel
@@ -40,7 +40,7 @@ gems:
40
40
  source:
41
41
  type: git
42
42
  name: ruby/gem_rbs_collection
43
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
43
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
44
44
  remote: https://github.com/ruby/gem_rbs_collection.git
45
45
  repo_dir: gems
46
46
  - name: activerecord
@@ -48,7 +48,7 @@ gems:
48
48
  source:
49
49
  type: git
50
50
  name: ruby/gem_rbs_collection
51
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
51
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
52
52
  remote: https://github.com/ruby/gem_rbs_collection.git
53
53
  repo_dir: gems
54
54
  - name: activesupport
@@ -56,7 +56,7 @@ gems:
56
56
  source:
57
57
  type: git
58
58
  name: ruby/gem_rbs_collection
59
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
59
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
60
60
  remote: https://github.com/ruby/gem_rbs_collection.git
61
61
  repo_dir: gems
62
62
  - name: ast
@@ -64,7 +64,7 @@ gems:
64
64
  source:
65
65
  type: git
66
66
  name: ruby/gem_rbs_collection
67
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
67
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
68
68
  remote: https://github.com/ruby/gem_rbs_collection.git
69
69
  repo_dir: gems
70
70
  - name: cgi
@@ -76,7 +76,7 @@ gems:
76
76
  source:
77
77
  type: git
78
78
  name: ruby/gem_rbs_collection
79
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
79
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
80
80
  remote: https://github.com/ruby/gem_rbs_collection.git
81
81
  repo_dir: gems
82
82
  - name: date
@@ -88,7 +88,7 @@ gems:
88
88
  source:
89
89
  type: git
90
90
  name: ruby/gem_rbs_collection
91
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
91
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
92
92
  remote: https://github.com/ruby/gem_rbs_collection.git
93
93
  repo_dir: gems
94
94
  - name: json
@@ -116,7 +116,7 @@ gems:
116
116
  source:
117
117
  type: git
118
118
  name: ruby/gem_rbs_collection
119
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
119
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
120
120
  remote: https://github.com/ruby/gem_rbs_collection.git
121
121
  repo_dir: gems
122
122
  - name: optparse
@@ -128,7 +128,7 @@ gems:
128
128
  source:
129
129
  type: git
130
130
  name: ruby/gem_rbs_collection
131
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
131
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
132
132
  remote: https://github.com/ruby/gem_rbs_collection.git
133
133
  repo_dir: gems
134
134
  - name: pathname
@@ -140,7 +140,7 @@ gems:
140
140
  source:
141
141
  type: git
142
142
  name: ruby/gem_rbs_collection
143
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
143
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
144
144
  remote: https://github.com/ruby/gem_rbs_collection.git
145
145
  repo_dir: gems
146
146
  - name: rails-dom-testing
@@ -148,7 +148,7 @@ gems:
148
148
  source:
149
149
  type: git
150
150
  name: ruby/gem_rbs_collection
151
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
151
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
152
152
  remote: https://github.com/ruby/gem_rbs_collection.git
153
153
  repo_dir: gems
154
154
  - name: railties
@@ -156,7 +156,7 @@ gems:
156
156
  source:
157
157
  type: git
158
158
  name: ruby/gem_rbs_collection
159
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
159
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
160
160
  remote: https://github.com/ruby/gem_rbs_collection.git
161
161
  repo_dir: gems
162
162
  - name: rainbow
@@ -164,7 +164,7 @@ gems:
164
164
  source:
165
165
  type: git
166
166
  name: ruby/gem_rbs_collection
167
- revision: 9330d49993d18362cce9190b9596f03d1f4915f8
167
+ revision: 965029a810c265f39b2b85f8c0edc160e5275e3d
168
168
  remote: https://github.com/ruby/gem_rbs_collection.git
169
169
  repo_dir: gems
170
170
  - name: rbs
@@ -16,6 +16,10 @@ module RbsActiveHash
16
16
  def header: () -> String
17
17
  def enum_decls: () -> String?
18
18
  def constants: () -> Array[String]
19
+ def association_decls: () -> String?
20
+ def has_many_decls: (Array[[Symbol, Hash[untyped, untyped]]]) -> String
21
+ def has_one_decls: (Array[[Symbol, Hash[untyped, untyped]]]) -> String
22
+ def belongs_to_decls: (Array[[Symbol, Hash[untyped, untyped]]]) -> String
19
23
  def method_decls: () -> String
20
24
  def method_names: () -> Array[Symbol]
21
25
  def method_types: () -> Hash[Symbol, untyped]
@@ -0,0 +1,21 @@
1
+ module RbsActiveHash
2
+ module Associations
3
+ class AssociationDefinition < RBS::AST::Members::Include
4
+ end
5
+
6
+ class RB < RBS::Prototype::RB
7
+ end
8
+
9
+ class Parser
10
+ attr_reader has_many: Array[[Symbol, Hash[untyped, untyped]]]
11
+ attr_reader has_one: Array[[Symbol, Hash[untyped, untyped]]]
12
+ attr_reader belongs_to: Array[[Symbol, Hash[untyped, untyped]]]
13
+
14
+ def initialize: () -> void
15
+ def parse: (String string, Array[Symbol] target) -> void
16
+ def process: (RBS::AST::Declarations::t | RBS::AST::Members::t node, Array[Symbol] target) -> void
17
+ def process_association_definition: (AssociationDefinition node) -> void
18
+ def node_to_literal: (untyped node) -> untyped
19
+ end
20
+ end
21
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rbs_active_hash
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.1
4
+ version: 1.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Takeshi KOMIYA
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2023-08-02 00:00:00.000000000 Z
11
+ date: 2023-08-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: active_hash
@@ -72,6 +72,7 @@ files:
72
72
  - lib/generators/rbs_active_hash/install_generator.rb
73
73
  - lib/rbs_active_hash.rb
74
74
  - lib/rbs_active_hash/active_hash.rb
75
+ - lib/rbs_active_hash/associations.rb
75
76
  - lib/rbs_active_hash/rake_task.rb
76
77
  - lib/rbs_active_hash/version.rb
77
78
  - rbs_active_hash.gemspec
@@ -80,6 +81,7 @@ files:
80
81
  - sig/generators/rbs_active_hash/install_generator.rbs
81
82
  - sig/rbs_active_hash.rbs
82
83
  - sig/rbs_active_hash/active_hash.rbs
84
+ - sig/rbs_active_hash/associations.rbs
83
85
  - sig/rbs_active_hash/rake_task.rbs
84
86
  - sig/shims/rake.rbs
85
87
  - sig/shims/thor.rbs