ryac 0.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 +7 -0
- data/LICENSE +21 -0
- data/README.md +145 -0
- data/Rakefile +45 -0
- data/Steepfile +9 -0
- data/bin/console +11 -0
- data/bin/ryac +134 -0
- data/bin/setup +8 -0
- data/lib/ryac/analysis/constant/collection.rb +332 -0
- data/lib/ryac/analysis/constant/rename_mapping.rb +346 -0
- data/lib/ryac/analysis/cvar/collection.rb +37 -0
- data/lib/ryac/analysis/gvar/collection.rb +36 -0
- data/lib/ryac/analysis/gvar/rename_mapping.rb +82 -0
- data/lib/ryac/analysis/ivar/collection.rb +281 -0
- data/lib/ryac/analysis/keyword/collection.rb +213 -0
- data/lib/ryac/analysis/keyword/rename_mapping.rb +167 -0
- data/lib/ryac/analysis/local_scopes.rb +582 -0
- data/lib/ryac/analysis/method/collection.rb +298 -0
- data/lib/ryac/analysis/method/rename_mapping.rb +337 -0
- data/lib/ryac/analysis/method_aliases.rb +83 -0
- data/lib/ryac/analysis/method_aliasing.rb +65 -0
- data/lib/ryac/analysis/nesting.rb +123 -0
- data/lib/ryac/analysis/scope_management.rb +25 -0
- data/lib/ryac/analysis/site_bucket_mapping.rb +127 -0
- data/lib/ryac/analysis/type_oracle.rb +386 -0
- data/lib/ryac/ast_utils.rb +321 -0
- data/lib/ryac/errors.rb +32 -0
- data/lib/ryac/gem_resolver.rb +55 -0
- data/lib/ryac/minifier.rb +169 -0
- data/lib/ryac/name_generator.rb +68 -0
- data/lib/ryac/pipeline/analyzer.rb +264 -0
- data/lib/ryac/pipeline/attr_decl_shorten.rb +61 -0
- data/lib/ryac/pipeline/boolean_shorten.rb +26 -0
- data/lib/ryac/pipeline/char_shorten.rb +20 -0
- data/lib/ryac/pipeline/compactor.rb +1202 -0
- data/lib/ryac/pipeline/concatenator.rb +248 -0
- data/lib/ryac/pipeline/constant_aliaser.rb +240 -0
- data/lib/ryac/pipeline/constant_fold.rb +93 -0
- data/lib/ryac/pipeline/control_flow_simplify.rb +352 -0
- data/lib/ryac/pipeline/data_types.rb +179 -0
- data/lib/ryac/pipeline/endless_method.rb +60 -0
- data/lib/ryac/pipeline/errors.rb +94 -0
- data/lib/ryac/pipeline/file_collector.rb +360 -0
- data/lib/ryac/pipeline/method_renamer.rb +151 -0
- data/lib/ryac/pipeline/paren_optimizer.rb +161 -0
- data/lib/ryac/pipeline/rename_patcher.rb +274 -0
- data/lib/ryac/pipeline/source_patcher.rb +54 -0
- data/lib/ryac/pipeline/spelling_shorten.rb +60 -0
- data/lib/ryac/pipeline/stage.rb +72 -0
- data/lib/ryac/pipeline/stage_runner.rb +84 -0
- data/lib/ryac/pipeline/variable_renamer.rb +125 -0
- data/lib/ryac/union_find.rb +42 -0
- data/lib/ryac/version.rb +5 -0
- data/lib/ryac.rb +29 -0
- data/rbs_collection.lock.yaml +224 -0
- data/rbs_collection.yaml +25 -0
- data/sig/ryac/analysis/constant/collection.rbs +30 -0
- data/sig/ryac/analysis/constant/rename_mapping.rbs +60 -0
- data/sig/ryac/analysis/cvar/collection.rbs +11 -0
- data/sig/ryac/analysis/gvar/collection.rbs +9 -0
- data/sig/ryac/analysis/gvar/rename_mapping.rbs +23 -0
- data/sig/ryac/analysis/ivar/collection.rbs +26 -0
- data/sig/ryac/analysis/keyword/collection.rbs +27 -0
- data/sig/ryac/analysis/keyword/rename_mapping.rbs +31 -0
- data/sig/ryac/analysis/local_scopes.rbs +77 -0
- data/sig/ryac/analysis/method/collection.rbs +25 -0
- data/sig/ryac/analysis/method/rename_mapping.rbs +82 -0
- data/sig/ryac/analysis/method_aliases.rbs +10 -0
- data/sig/ryac/analysis/method_aliasing.rbs +9 -0
- data/sig/ryac/analysis/nesting.rbs +9 -0
- data/sig/ryac/analysis/scope_management.rbs +5 -0
- data/sig/ryac/analysis/site_bucket_mapping.rbs +26 -0
- data/sig/ryac/analysis/type_oracle.rbs +61 -0
- data/sig/ryac/ast_utils.rbs +34 -0
- data/sig/ryac/errors.rbs +21 -0
- data/sig/ryac/gem_resolver.rbs +28 -0
- data/sig/ryac/minifier.rbs +33 -0
- data/sig/ryac/name_generator.rbs +14 -0
- data/sig/ryac/pipeline/analyzer.rbs +34 -0
- data/sig/ryac/pipeline/attr_decl_shorten.rbs +17 -0
- data/sig/ryac/pipeline/boolean_shorten.rbs +11 -0
- data/sig/ryac/pipeline/char_shorten.rbs +11 -0
- data/sig/ryac/pipeline/compactor.rbs +125 -0
- data/sig/ryac/pipeline/concatenator.rbs +28 -0
- data/sig/ryac/pipeline/constant_aliaser.rbs +35 -0
- data/sig/ryac/pipeline/constant_fold.rbs +20 -0
- data/sig/ryac/pipeline/control_flow_simplify.rbs +34 -0
- data/sig/ryac/pipeline/data_types.rbs +151 -0
- data/sig/ryac/pipeline/endless_method.rbs +14 -0
- data/sig/ryac/pipeline/errors.rbs +46 -0
- data/sig/ryac/pipeline/file_collector.rbs +34 -0
- data/sig/ryac/pipeline/method_renamer.rbs +25 -0
- data/sig/ryac/pipeline/paren_optimizer.rbs +16 -0
- data/sig/ryac/pipeline/rename_patcher.rbs +38 -0
- data/sig/ryac/pipeline/source_patcher.rbs +12 -0
- data/sig/ryac/pipeline/spelling_shorten.rbs +14 -0
- data/sig/ryac/pipeline/stage.rbs +28 -0
- data/sig/ryac/pipeline/stage_runner.rbs +18 -0
- data/sig/ryac/pipeline/variable_renamer.rbs +21 -0
- data/sig/ryac/union_find.rbs +17 -0
- data/sig/ryac.rbs +13 -0
- data/sig/shims/env.rbs +19 -0
- data/sig/shims/typeprof/core/ast.rbs +299 -0
- data/sig/shims/typeprof/core/type.rbs +22 -0
- data/sig/shims/typeprof/core.rbs +73 -0
- data/tools/regen_pins.rb +45 -0
- metadata +201 -0
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
EXCLUDED_METHODS: Set[Symbol]
|
|
3
|
+
|
|
4
|
+
type method_key = [Array[Symbol], bool, Symbol]
|
|
5
|
+
|
|
6
|
+
class MethodRenameMapping
|
|
7
|
+
MIN_GROUP_SAVINGS: Integer
|
|
8
|
+
include UnionFind[method_key]
|
|
9
|
+
|
|
10
|
+
type class_key = [Array[Symbol], bool]
|
|
11
|
+
type method_data = { def_nodes: Array[Prism::Node], call_sites: Array[Prism::Node] }
|
|
12
|
+
# Both halves optional: assign_short_names substitutes {} when no oracle
|
|
13
|
+
# is given.
|
|
14
|
+
type hierarchy = { ?includers: Hash[class_key, Set[class_key]], ?ancestors: Hash[class_key, Array[class_key]] }
|
|
15
|
+
|
|
16
|
+
class MethodGroupEntry
|
|
17
|
+
attr_accessor keys: Array[method_key]
|
|
18
|
+
attr_accessor original_name: String
|
|
19
|
+
attr_accessor total_occurrences: Integer
|
|
20
|
+
|
|
21
|
+
def initialize: (?Array[method_key]?, ?String?, ?Integer?) -> void
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
@methods: Hash[method_key, method_data]
|
|
25
|
+
@node_to_key: Hash[Integer, method_key]
|
|
26
|
+
@node_short_names: Hash[[Integer, Integer], String]
|
|
27
|
+
@key_short_names: Hash[method_key, String]
|
|
28
|
+
@implicit_receiver_sites: Hash[Integer, scope_id]
|
|
29
|
+
@frozen: bool
|
|
30
|
+
|
|
31
|
+
def initialize: () -> void
|
|
32
|
+
|
|
33
|
+
def add_method: (method_key method_key, Prism::Node? def_node) -> void
|
|
34
|
+
|
|
35
|
+
def has_method?: (method_key method_key) -> bool
|
|
36
|
+
|
|
37
|
+
def add_call_site: (Prism::Node call_node, method_key method_key, has_receiver: bool, ?scope_id: scope_id?) -> void
|
|
38
|
+
|
|
39
|
+
def exclude_methods_by_mid: (Set[Symbol] mids) -> void
|
|
40
|
+
|
|
41
|
+
def merge_all_by_mid: (Symbol mid) -> void
|
|
42
|
+
|
|
43
|
+
def merge_blind_def_groups: () -> void
|
|
44
|
+
|
|
45
|
+
def add_unresolved_sites_for_mid: (Symbol mid, Array[Prism::Node] call_nodes) -> void
|
|
46
|
+
|
|
47
|
+
def group_keys: (method_key method_key) -> Array[method_key]
|
|
48
|
+
|
|
49
|
+
def each_group_call_site: (method_key method_key) { (Prism::Node, scope_id?) -> void } -> void
|
|
50
|
+
|
|
51
|
+
def assign_short_names: (scope_mapping_table scope_mappings, ?TypeOracle? oracle) -> void
|
|
52
|
+
def verify_no_shadowing!: (?hierarchy hierarchy) -> void
|
|
53
|
+
|
|
54
|
+
def short_name_for: ([Integer, Integer] node_location_key) -> String?
|
|
55
|
+
|
|
56
|
+
def short_name_for_key: (method_key method_key) -> String?
|
|
57
|
+
|
|
58
|
+
def node_mapping: () -> Hash[[Integer, Integer], String]
|
|
59
|
+
|
|
60
|
+
def each_method_key: () { (method_key) -> void } -> void
|
|
61
|
+
|
|
62
|
+
def method_mids: () -> Set[Symbol]
|
|
63
|
+
|
|
64
|
+
def each_cpath_for_mid: (Symbol mid) { (Array[Symbol], bool) -> void } -> void
|
|
65
|
+
|
|
66
|
+
private
|
|
67
|
+
|
|
68
|
+
def build_group_entries: (Hash[method_key, Array[method_key]] groups) -> Array[MethodGroupEntry]
|
|
69
|
+
|
|
70
|
+
def self.build_scope_vars: (scope_mapping_table scope_mappings) -> Hash[scope_id, Set[String]]
|
|
71
|
+
|
|
72
|
+
def groups_by_root: () -> Hash[method_key, Array[method_key]]
|
|
73
|
+
|
|
74
|
+
def build_existing_method_names: (TypeOracle oracle) -> [Hash[class_key, Set[String]], hierarchy]
|
|
75
|
+
|
|
76
|
+
def find_shortest_name: (Array[method_key] keys, Hash[scope_id, Set[String]] scope_vars, Hash[class_key, Set[String]] existing_methods, hierarchy hierarchy) -> String
|
|
77
|
+
|
|
78
|
+
def propagate_short_name: (Array[method_key] keys, String short_name, Hash[class_key, Set[String]] existing_methods, hierarchy hierarchy) -> void
|
|
79
|
+
|
|
80
|
+
def assign_short_name: (Array[method_key] keys, String short_name) -> void
|
|
81
|
+
end
|
|
82
|
+
end
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
KERNEL_ALIASES: Hash[Symbol, Symbol]
|
|
3
|
+
RECEIVER_ALIASES: Hash[Symbol, Symbol]
|
|
4
|
+
METHOD_ALIASES: Hash[Symbol, Symbol]
|
|
5
|
+
METHOD_TRANSFORMS: Hash[[Symbol, Symbol], String]
|
|
6
|
+
EMPTY_LITERALS: Hash[Symbol, String]
|
|
7
|
+
SIZE_COMPARISON_OPS: Hash[Symbol, String]
|
|
8
|
+
SIZE_COMPARISON_TRANSFORMS: Hash[[Symbol, Symbol], String]
|
|
9
|
+
SIZE_QUERY_MIDS: Hash[Symbol, Array[Symbol]]
|
|
10
|
+
end
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module AnalysisPhases
|
|
3
|
+
def resolve_method_aliases_and_transforms: (Prism::Node prism_root) -> [Hash[location_key, Symbol], Hash[location_key, String]]
|
|
4
|
+
|
|
5
|
+
private
|
|
6
|
+
|
|
7
|
+
def register_size_comparison: (Prism::CallNode node, Hash[location_key, String] transform_map, Array[location_key] suppressed_alias_keys) -> void
|
|
8
|
+
end
|
|
9
|
+
end
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module Nesting
|
|
3
|
+
def self?.each: (Prism::Node root) { (Prism::Node, Array[Symbol], bool, bool) -> void } -> void
|
|
4
|
+
def self?.each_meta_call: (Prism::Node root, Array[Symbol] names, ?loose: bool) { (Prism::CallNode, Array[Symbol], bool) -> void } -> void
|
|
5
|
+
def self?.each_method_definition: (Prism::Node root) { (Prism::DefNode, [Array[Symbol], bool, Symbol]) -> void } -> void
|
|
6
|
+
def self?.path_segments: (Prism::Node constant_path) -> [Array[Symbol], bool]?
|
|
7
|
+
def self?.walk: (Prism::Node? node, Array[Symbol] cpath, bool singleton, bool in_def) { (Prism::Node, Array[Symbol], bool, bool) -> void } -> void
|
|
8
|
+
end
|
|
9
|
+
end
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
class SiteBucketMapping
|
|
3
|
+
@prefix: String
|
|
4
|
+
@kept_name_max: Integer
|
|
5
|
+
@buckets: Hash[Array[Symbol], Hash[Symbol, Array[untyped]]]
|
|
6
|
+
@cpath_to_canonical: Hash[Array[Symbol], Array[Symbol]]
|
|
7
|
+
@excluded_cpaths: Set[Array[Symbol]]
|
|
8
|
+
@reserved_names: Hash[Array[Symbol], Set[String]]
|
|
9
|
+
@node_short_names: Hash[[Integer, Integer], String]
|
|
10
|
+
@frozen: bool
|
|
11
|
+
|
|
12
|
+
def initialize: (prefix: String) -> void
|
|
13
|
+
def add_site: (Array[Symbol] cpath, Symbol name, untyped node) -> void
|
|
14
|
+
def exclude_cpath: (Array[Symbol] cpath) -> void
|
|
15
|
+
def reserve_name: (Array[Symbol] cpath, String short_name) -> void
|
|
16
|
+
def each_canonical_cpath: () { (Array[Symbol]) -> void } -> void
|
|
17
|
+
def merge_with_ancestor: (Array[Symbol] child_cpath, Array[Symbol] ancestor_cpath) -> void
|
|
18
|
+
def assign_short_names: () -> void
|
|
19
|
+
def node_mapping: () -> Hash[[Integer, Integer], String]
|
|
20
|
+
|
|
21
|
+
private
|
|
22
|
+
|
|
23
|
+
def check_open!: (String action) -> void
|
|
24
|
+
def resolve_canonical: (Array[Symbol] cpath) -> Array[Symbol]
|
|
25
|
+
end
|
|
26
|
+
end
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
# The TypeProf aliases live with the one class allowed to touch them.
|
|
3
|
+
type tp_node = TypeProf::Core::AST::Node
|
|
4
|
+
type tp_genv = TypeProf::Core::GlobalEnv
|
|
5
|
+
|
|
6
|
+
class TypeOracle
|
|
7
|
+
def self.boot: (String content, Hash[String, String] rbs_files) -> TypeOracle
|
|
8
|
+
def self.raw_prism_node: (tp_node node) -> Prism::Node?
|
|
9
|
+
|
|
10
|
+
class CallerInfo
|
|
11
|
+
attr_accessor prism_node: Prism::Node?
|
|
12
|
+
attr_accessor super: bool
|
|
13
|
+
attr_accessor caller_cpath: Array[Symbol]?
|
|
14
|
+
attr_accessor receiver: bool
|
|
15
|
+
attr_accessor keyword_entries: Array[[Prism::Node, Prism::Node]]?
|
|
16
|
+
attr_accessor keyword_splat: bool
|
|
17
|
+
|
|
18
|
+
def initialize: (?prism_node: Prism::Node?, ?super: bool, ?caller_cpath: Array[Symbol]?, ?receiver: bool, ?keyword_entries: Array[[Prism::Node, Prism::Node]]?, ?keyword_splat: bool) -> void
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
TP_CALL_NODES: Array[Class]
|
|
22
|
+
|
|
23
|
+
@genv: tp_genv
|
|
24
|
+
@tp_root: tp_node
|
|
25
|
+
@ancestor_cpaths: Hash[MethodRenameMapping::class_key, Array[Array[Symbol]]]
|
|
26
|
+
@const_resolution_cache: Hash[location_key, Array[Symbol]?]
|
|
27
|
+
@method_cache: Hash[method_key, TypeProf::Core::MethodEntity?]
|
|
28
|
+
# Both built by build_tp_indexes before first read.
|
|
29
|
+
@tp_calls_by_loc: Hash[location_key, Hash[Symbol, TypeProf::Core::AST::CallBaseNode]]
|
|
30
|
+
@tp_consts_by_loc: Hash[location_key, TypeProf::Core::AST::ConstantReadNode]
|
|
31
|
+
|
|
32
|
+
def initialize: (tp_genv genv, tp_node tp_root) -> void
|
|
33
|
+
|
|
34
|
+
def each_ancestor_cpath: (Array[Symbol] cpath, bool singleton) { (Array[Symbol]) -> void } -> void
|
|
35
|
+
def each_ancestor_methods: (Array[Symbol] cpath, bool singleton) { (Array[Symbol], bool, Array[String]) -> void } -> void
|
|
36
|
+
def method_known?: (Array[Symbol] cpath, bool singleton, Symbol mid) -> bool
|
|
37
|
+
def method_defined?: (Array[Symbol] cpath, bool singleton, Symbol mid) -> bool
|
|
38
|
+
def method_call_count: (Array[Symbol] cpath, bool singleton, Symbol mid) -> Integer
|
|
39
|
+
def each_call_site_key: (Array[Symbol] cpath, bool singleton, Symbol mid) { (location_key) -> void } -> void
|
|
40
|
+
def method_definition_keys: (Array[Symbol] cpath, bool singleton, Symbol mid) -> Array[location_key]
|
|
41
|
+
def each_caller: (Array[Symbol] cpath, bool singleton, Symbol mid) { (CallerInfo) -> void } -> void
|
|
42
|
+
def resolved_targets: (Prism::Node prism_call_node, Symbol mid) -> Array[method_key]?
|
|
43
|
+
def first_argument_symbols: (Prism::CallNode prism_call_node) -> Array[Symbol]
|
|
44
|
+
def receiver_responds_to?: (Prism::CallNode prism_call_node, Symbol mid) -> bool
|
|
45
|
+
def receiver_within_type?: (Prism::CallNode prism_call_node, Symbol type_name) -> bool
|
|
46
|
+
def resolve_constant_read: (Prism::Node prism_node) -> Array[Symbol]?
|
|
47
|
+
def constant_read_count: (Array[Symbol] cpath) -> Integer
|
|
48
|
+
|
|
49
|
+
private
|
|
50
|
+
|
|
51
|
+
def tp_key: (tp_node node) -> location_key
|
|
52
|
+
def resolve_method: (Array[Symbol] cpath, bool singleton, Symbol mid) -> untyped
|
|
53
|
+
def every_receiver_base_type: (Prism::CallNode prism_call_node) { (untyped) -> boolish } -> bool
|
|
54
|
+
def type_responds_to?: (untyped mod, bool singleton, Symbol mid) -> bool
|
|
55
|
+
def mod_is_or_inherits?: (untyped mod, untyped target) -> bool
|
|
56
|
+
def tp_call_for: (Prism::Node prism_node, Symbol mid) -> TypeProf::Core::AST::CallBaseNode?
|
|
57
|
+
def tp_const_for: (Prism::Node prism_node) -> TypeProf::Core::AST::ConstantReadNode?
|
|
58
|
+
def build_tp_indexes: () -> void
|
|
59
|
+
def resolve_tp_const: (tp_node node) -> Array[Symbol]?
|
|
60
|
+
end
|
|
61
|
+
end
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module AstUtils
|
|
3
|
+
def self?.symbol_arguments: (Prism::CallNode call_node) -> Array[Symbol]
|
|
4
|
+
MIDDLE_METHODS: Array[Symbol]
|
|
5
|
+
TERNARY_SAFE_PREV: Array[Integer]
|
|
6
|
+
COMPARISON_PREV: Array[Integer]
|
|
7
|
+
PIPE_BREAK_BYTES: Array[Integer]
|
|
8
|
+
|
|
9
|
+
def self?.unwrap_statements: (Prism::Node? node) -> Prism::Node?
|
|
10
|
+
def self?.middle_method?: (Symbol method) -> bool
|
|
11
|
+
def self?.logical_op?: (Prism::Node? node) -> bool
|
|
12
|
+
def self?.has_block?: (Prism::CallNode node) -> bool
|
|
13
|
+
def self?.single_statement_body?: (Prism::Node? body) -> bool
|
|
14
|
+
def self?.setter_def_name?: (Symbol name) -> bool
|
|
15
|
+
def self?.simple_negatable?: (Prism::Node node) -> bool
|
|
16
|
+
def self?.first_arg_starts_with_brace?: (Prism::Node arg) -> bool
|
|
17
|
+
def self?.ends_with_name_char?: (Prism::Node? node) -> bool
|
|
18
|
+
def self?.ends_with_method_suffix?: (Prism::Node node) -> bool
|
|
19
|
+
def self?.needs_ternary_q_space?: (Prism::Node node) -> bool
|
|
20
|
+
def self?.modifier_control_flow?: (Prism::Node node) -> bool
|
|
21
|
+
def self?.modifier_conditional?: (Prism::Node node) -> bool?
|
|
22
|
+
def self?.modifier_loop?: (Prism::Node node) -> bool
|
|
23
|
+
def self?.ternary_needs_parens?: (Prism::Node node, String source) -> bool
|
|
24
|
+
def self?.can_omit_parens?: (Prism::CallNode node, ?String? method_name) -> bool
|
|
25
|
+
def self?.first_arg_is_regex?: (Prism::Node arg) -> bool
|
|
26
|
+
def self?.contains_bare_block?: (Prism::Node? node) -> bool
|
|
27
|
+
MATCH_REBIND_NODES: Array[untyped]
|
|
28
|
+
def self?.match_rebind?: (Prism::Node node) -> bool
|
|
29
|
+
def self?.shorthand_pun_values: (Prism::Node node) -> Array[Prism::Node]
|
|
30
|
+
def self?.each_node: (Prism::Node? node) { (Prism::Node) -> void } -> void
|
|
31
|
+
def self?.location_key: (Prism::Node node) -> location_key
|
|
32
|
+
def self?.line_col_key: (Prism::Node node) -> line_col_key
|
|
33
|
+
end
|
|
34
|
+
end
|
data/sig/ryac/errors.rbs
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
class Error < StandardError
|
|
3
|
+
end
|
|
4
|
+
|
|
5
|
+
class InputError < Error
|
|
6
|
+
end
|
|
7
|
+
|
|
8
|
+
class InternalError < Error
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
class MinifyError < InputError
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
class SyntaxError < InputError
|
|
15
|
+
attr_reader path: String?
|
|
16
|
+
attr_reader line: Integer?
|
|
17
|
+
attr_reader column: Integer?
|
|
18
|
+
|
|
19
|
+
def initialize: (String message, ?path: String?, ?line: Integer?, ?column: Integer?) -> void
|
|
20
|
+
end
|
|
21
|
+
end
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
class GemResolver
|
|
3
|
+
class GemResolution
|
|
4
|
+
attr_reader entry_path: String
|
|
5
|
+
attr_reader project_root: String
|
|
6
|
+
attr_reader require_paths: Array[String]
|
|
7
|
+
|
|
8
|
+
def self.new: (entry_path: String, project_root: String, require_paths: Array[String]) -> GemResolution
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def self.minifier_args: (Array[String] gem_names) -> { entry: String | Array[String], project_root: Array[String], gem_require_paths: Array[String] }
|
|
12
|
+
def call: (String gem_name) -> GemResolution
|
|
13
|
+
|
|
14
|
+
private
|
|
15
|
+
|
|
16
|
+
def find_entry_file: (Gem::Specification spec, String gem_name) -> String?
|
|
17
|
+
end
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
# The rbs gem's rubygems shim (rbs/sig/shims/rubygems.rbs) declares only the
|
|
21
|
+
# few Gem::Specification methods rbs itself calls; full_require_paths is real
|
|
22
|
+
# rubygems API (Gem::BasicSpecification#full_require_paths) that GemResolver
|
|
23
|
+
# uses, so it is declared here.
|
|
24
|
+
module Gem
|
|
25
|
+
class Specification
|
|
26
|
+
def full_require_paths: () -> Array[String]
|
|
27
|
+
end
|
|
28
|
+
end
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
class Minifier
|
|
3
|
+
DEFAULT_LEVEL: Symbol
|
|
4
|
+
|
|
5
|
+
type stage_class = singleton(Pipeline::Stage)
|
|
6
|
+
type stage_entry = [stage_class] | [stage_class, Hash[Symbol, untyped]]
|
|
7
|
+
|
|
8
|
+
def self.resolve_level: (String | Symbol value) -> Symbol
|
|
9
|
+
|
|
10
|
+
OPTIMIZE_PRE: Array[stage_entry]
|
|
11
|
+
OPTIMIZE_POST: Array[stage_entry]
|
|
12
|
+
ALL_VAR_FEATURES: Hash[Symbol, Hash[Symbol, bool]]
|
|
13
|
+
ALL_VAR_WITH_ATTR: Hash[Symbol, Hash[Symbol, bool]]
|
|
14
|
+
STABLE_STAGES: Array[stage_entry]
|
|
15
|
+
STAGES: Hash[Symbol, Array[stage_entry]]
|
|
16
|
+
|
|
17
|
+
def self.derive_unstable: (Array[stage_entry] stable) -> Array[stage_entry]
|
|
18
|
+
def self.run_stages: (String code, Array[stage_entry] stages, ?stdlib_requires: Array[String], ?rbs_files: Hash[String, String]) -> Pipeline::RenameResult
|
|
19
|
+
|
|
20
|
+
include Pipeline::SourcePatcher
|
|
21
|
+
|
|
22
|
+
attr_reader result: Pipeline::MinifiedResult?
|
|
23
|
+
|
|
24
|
+
def initialize: () -> void
|
|
25
|
+
def call: (String | Array[String] entry_path, ?level: Symbol | Array[stage_entry], ?project_root: String | Array[String] | nil, ?gem_names: Array[String], ?gem_require_paths: Array[String]) -> Pipeline::MinifiedResult
|
|
26
|
+
|
|
27
|
+
private
|
|
28
|
+
|
|
29
|
+
def run_pipeline: (Pipeline::ConcatenatedSource source, Symbol | Array[stage_entry] target_level) -> Pipeline::RenameResult
|
|
30
|
+
def build_result: (Pipeline::RenameResult rename_result, Pipeline::ConcatenatedSource source, Integer file_count) -> Pipeline::MinifiedResult
|
|
31
|
+
def build_output: (String code, Array[String] stdlib_requires, ?String preamble) -> String
|
|
32
|
+
end
|
|
33
|
+
end
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
class NameGenerator
|
|
3
|
+
LETTERS: Array[String]
|
|
4
|
+
DIGITS: Array[String]
|
|
5
|
+
KEPT_NAME_MAX: Integer
|
|
6
|
+
|
|
7
|
+
def initialize: (?(Array[String] | Set[String]) additional_excluded, ?prefix: String, ?upcase: bool) -> void
|
|
8
|
+
def next_name: () -> String
|
|
9
|
+
|
|
10
|
+
private
|
|
11
|
+
|
|
12
|
+
def index_to_name: (Integer index) -> String
|
|
13
|
+
end
|
|
14
|
+
end
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module Pipeline
|
|
3
|
+
class Analyzer
|
|
4
|
+
include AnalysisPhases
|
|
5
|
+
|
|
6
|
+
@syntax_data: syntax_data_map
|
|
7
|
+
# Values are { type: Symbol } or { type: Symbol, args: Array[Symbol] };
|
|
8
|
+
# kept untyped-valued because syntax_value has no Array member.
|
|
9
|
+
@meta_node_map: Hash[location_key, meta_node_entry]
|
|
10
|
+
|
|
11
|
+
def self.prism_only: (ConcatenatedSource source) -> AnalysisResult
|
|
12
|
+
def self.prism_only_from_string: (String content, ?source: ConcatenatedSource?) -> AnalysisResult
|
|
13
|
+
def call: (ConcatenatedSource source) -> AnalysisResult
|
|
14
|
+
def syntax_data_for: (Prism::ProgramNode prism_ast) -> syntax_data_map
|
|
15
|
+
|
|
16
|
+
private
|
|
17
|
+
|
|
18
|
+
def without_stdout_pollution: [T] () { () -> T } -> T
|
|
19
|
+
def setup_typeprof: (ConcatenatedSource source) -> [Prism::ParseResult, TypeOracle]
|
|
20
|
+
def analyze_keywords_and_scopes: () -> void
|
|
21
|
+
def analyze_methods_phase: () -> void
|
|
22
|
+
def analyze_variables_phase: () -> void
|
|
23
|
+
def analyze_constants_phase: () -> void
|
|
24
|
+
def precompute_rename_entries: () -> Hash[location_key, String]
|
|
25
|
+
def build_analysis_result: (Prism::ParseResult prism_result, ConcatenatedSource source, Hash[location_key, String] rename_map, Hash[location_key, Symbol] method_alias_map, Hash[location_key, String] method_transform_map, Hash[location_key, Hash[Symbol, String]] attr_rename_map, Hash[location_key, String] attr_ivar_entries, Hash[location_key, String] local_rename_entries) -> AnalysisResult
|
|
26
|
+
|
|
27
|
+
META_CALL_METHODS: Array[Symbol]
|
|
28
|
+
|
|
29
|
+
def precompute_meta_nodes: () -> void
|
|
30
|
+
def collect_syntax_data: (Prism::ProgramNode prism_ast) -> syntax_data_map
|
|
31
|
+
def traverse_prism: (Prism::Node node, syntax_data_map data) -> void
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
end
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module Pipeline
|
|
3
|
+
class AttrDeclShorten < Stage
|
|
4
|
+
include RenamePatcher
|
|
5
|
+
|
|
6
|
+
@rename_attrs: bool
|
|
7
|
+
|
|
8
|
+
def needs_analysis?: () -> bool
|
|
9
|
+
def initialize: (?rename_attrs: bool) -> void
|
|
10
|
+
def collect: (StageContext ctx, Array[patch_entry] patches) -> void
|
|
11
|
+
|
|
12
|
+
private
|
|
13
|
+
|
|
14
|
+
def render_attr_declaration: (Symbol type, Array[String] names) -> String?
|
|
15
|
+
end
|
|
16
|
+
end
|
|
17
|
+
end
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module Pipeline
|
|
3
|
+
class BooleanShorten < Stage
|
|
4
|
+
def collect: (StageContext ctx, Array[patch_entry] patches) -> void
|
|
5
|
+
|
|
6
|
+
private
|
|
7
|
+
|
|
8
|
+
def walk: (Prism::Node node, Array[patch_entry] patches, ?inside_block_params: bool) -> void
|
|
9
|
+
end
|
|
10
|
+
end
|
|
11
|
+
end
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module Pipeline
|
|
3
|
+
class Compactor
|
|
4
|
+
BINARY_OPERATORS: Array[Symbol]
|
|
5
|
+
NON_ASSOCIATIVE_OPS: Set[Symbol]
|
|
6
|
+
OPERATOR_PRECEDENCE: Hash[Symbol, Integer]
|
|
7
|
+
COMPOUND_WRITE_NODES: Array[singleton(Prism::Node)]
|
|
8
|
+
MODIFIER_KEYWORD_NODES: Array[singleton(Prism::Node)]
|
|
9
|
+
ASSIGNMENT_NODES: Array[singleton(Prism::Node)]
|
|
10
|
+
PARENS_KEPT_NODES: Array[singleton(Prism::Node)]
|
|
11
|
+
PARENS_KEPT_CLASSES: Set[singleton(Prism::Node)]
|
|
12
|
+
JUMP_NODES: Array[singleton(Prism::Node)]
|
|
13
|
+
LOGIC_LOOSE_OPERANDS: Array[singleton(Prism::Node)]
|
|
14
|
+
LOGIC_LOOSE_OPERAND_CLASSES: Set[singleton(Prism::Node)]
|
|
15
|
+
PERCENT_SAFE_WORD: Regexp
|
|
16
|
+
|
|
17
|
+
def self.jump_with_value?: (Prism::Node? node) -> bool
|
|
18
|
+
def self.loose_logic_operand?: (Prism::Node? node, tight: bool) -> bool
|
|
19
|
+
|
|
20
|
+
# The 24 compound-assignment node classes dispatched by r_compound_write
|
|
21
|
+
# (`+=`-style Operator variants plus `||=`/`&&=` Or/And variants).
|
|
22
|
+
type compound_write_node = Prism::LocalVariableOperatorWriteNode | Prism::LocalVariableOrWriteNode | Prism::LocalVariableAndWriteNode
|
|
23
|
+
| Prism::InstanceVariableOperatorWriteNode | Prism::InstanceVariableOrWriteNode | Prism::InstanceVariableAndWriteNode
|
|
24
|
+
| Prism::GlobalVariableOperatorWriteNode | Prism::GlobalVariableOrWriteNode | Prism::GlobalVariableAndWriteNode
|
|
25
|
+
| Prism::ClassVariableOperatorWriteNode | Prism::ClassVariableOrWriteNode | Prism::ClassVariableAndWriteNode
|
|
26
|
+
| Prism::ConstantOperatorWriteNode | Prism::ConstantOrWriteNode | Prism::ConstantAndWriteNode
|
|
27
|
+
| Prism::ConstantPathOperatorWriteNode | Prism::ConstantPathOrWriteNode | Prism::ConstantPathAndWriteNode
|
|
28
|
+
| Prism::CallOperatorWriteNode | Prism::CallOrWriteNode | Prism::CallAndWriteNode
|
|
29
|
+
| Prism::IndexOperatorWriteNode | Prism::IndexOrWriteNode | Prism::IndexAndWriteNode
|
|
30
|
+
|
|
31
|
+
@prism_ast: Prism::ProgramNode
|
|
32
|
+
GROUP_MIN: Integer
|
|
33
|
+
@standard_error_redefined: bool?
|
|
34
|
+
|
|
35
|
+
def call: (String input_string) -> String
|
|
36
|
+
|
|
37
|
+
private
|
|
38
|
+
|
|
39
|
+
def rebuild: () -> Array[String]
|
|
40
|
+
def r: (Prism::Node? node) -> String
|
|
41
|
+
def r_stmt: (Prism::Node? nodes) -> String
|
|
42
|
+
def singleton_self_def?: (Prism::Node node) -> bool
|
|
43
|
+
def render_statement_list: (Array[Prism::Node] stmts) -> Array[String]
|
|
44
|
+
def flush_singleton_run: (Array[Prism::DefNode] run) -> Array[String]
|
|
45
|
+
def r_call: (Prism::CallNode node) -> String
|
|
46
|
+
def r_binary_op: (Prism::CallNode node) -> String
|
|
47
|
+
def r_block_call: (Prism::CallNode node) -> String?
|
|
48
|
+
def r_index_access: (Prism::CallNode node) -> String
|
|
49
|
+
def r_index_assign: (Prism::CallNode node) -> String
|
|
50
|
+
def r_unary: (Prism::CallNode node, String op) -> String
|
|
51
|
+
def r_def: (Prism::DefNode node, ?drop_self_receiver: bool) -> String
|
|
52
|
+
def r_lambda: (Prism::LambdaNode node) -> String
|
|
53
|
+
def r_yield: (Prism::YieldNode node) -> String
|
|
54
|
+
def r_if: (Prism::IfNode node) -> String
|
|
55
|
+
def r_unless: (Prism::UnlessNode node) -> String
|
|
56
|
+
def r_while: (Prism::WhileNode node) -> String
|
|
57
|
+
def r_until: (Prism::UntilNode node) -> String
|
|
58
|
+
def r_case: (Prism::CaseNode node) -> String
|
|
59
|
+
def r_case_match: (Prism::CaseMatchNode node) -> String
|
|
60
|
+
def r_in_pattern: (Prism::Node pattern) -> String
|
|
61
|
+
def r_pattern: (Prism::Node node) -> String
|
|
62
|
+
def r_for: (Prism::ForNode node) -> String
|
|
63
|
+
def r_return: (Prism::ReturnNode node) -> String
|
|
64
|
+
def r_break: (Prism::BreakNode node) -> String
|
|
65
|
+
def r_alias_name: (Prism::Node node) -> String
|
|
66
|
+
def r_next: (Prism::NextNode node) -> String
|
|
67
|
+
def r_jump: (String keyword, Prism::ArgumentsNode? arguments) -> String
|
|
68
|
+
def r_compound_write: (compound_write_node node) -> String
|
|
69
|
+
def compound: (String | Symbol target, Symbol | String op, compound_write_node node) -> String
|
|
70
|
+
def call_target: (Prism::CallOperatorWriteNode | Prism::CallOrWriteNode | Prism::CallAndWriteNode node) -> String
|
|
71
|
+
def idx_target: (Prism::IndexOperatorWriteNode | Prism::IndexOrWriteNode | Prism::IndexAndWriteNode node) -> String
|
|
72
|
+
def r_symbol: (Prism::SymbolNode node) -> String
|
|
73
|
+
def r_regexp: (Prism::RegularExpressionNode node) -> String
|
|
74
|
+
def escape_regexp_slash: (String content) -> String
|
|
75
|
+
def r_array: (Prism::ArrayNode node) -> String
|
|
76
|
+
def percent_array_form: (Prism::ArrayNode node) -> String?
|
|
77
|
+
def r_float: (Prism::FloatNode node) -> String
|
|
78
|
+
def r_range: (Prism::RangeNode node, ?bare: bool) -> String
|
|
79
|
+
def r_delimited: (Prism::Node node) -> String
|
|
80
|
+
def r_flipflop: (Prism::FlipFlopNode node) -> String
|
|
81
|
+
def r_hash: (Prism::HashNode node) -> String
|
|
82
|
+
def r_keyword_hash: (Prism::KeywordHashNode node) -> String
|
|
83
|
+
def r_assoc: (Prism::AssocNode element) -> String
|
|
84
|
+
def r_string: (Prism::StringNode node) -> String
|
|
85
|
+
def r_interp_string: (Prism::InterpolatedStringNode node) -> String
|
|
86
|
+
def r_interp_symbol: (Prism::InterpolatedSymbolNode node) -> String
|
|
87
|
+
def r_interp_regexp: (Prism::InterpolatedRegularExpressionNode node) -> String
|
|
88
|
+
def interp_part: (Prism::Node part, ?escape_quotes: bool) -> String
|
|
89
|
+
def escape_for_dquote: (String str) -> String
|
|
90
|
+
def r_class: (Prism::ClassNode node) -> String
|
|
91
|
+
def r_module: (Prism::ModuleNode node) -> String
|
|
92
|
+
def r_singleton_class: (Prism::SingletonClassNode node) -> String
|
|
93
|
+
def r_and: (Prism::AndNode node) -> String
|
|
94
|
+
def r_or: (Prism::OrNode node) -> String
|
|
95
|
+
def logic_operand: (Prism::Node operand, tight: bool) -> String
|
|
96
|
+
def r_begin: (Prism::BeginNode node) -> String
|
|
97
|
+
def bare_standard_error?: (Array[Prism::node] exceptions) -> bool
|
|
98
|
+
def standard_error_redefined?: () -> bool
|
|
99
|
+
def r_super: (Prism::SuperNode node) -> String
|
|
100
|
+
def r_defined: (Prism::DefinedNode node) -> String
|
|
101
|
+
def r_multi_write: (Prism::MultiWriteNode node) -> String
|
|
102
|
+
def r_multi_target: (Prism::Node target) -> String
|
|
103
|
+
def r_array_pattern: (Prism::ArrayPatternNode node) -> String
|
|
104
|
+
def r_hash_pattern: (Prism::HashPatternNode node) -> String
|
|
105
|
+
def r_find_pattern: (Prism::FindPatternNode node) -> String
|
|
106
|
+
def build_call_args: (Prism::CallNode node, ?String? block_pass) -> String
|
|
107
|
+
def build_def_params: (Prism::ParametersNode? params) -> Array[String]
|
|
108
|
+
def r_multi_target_param: (Prism::MultiTargetNode target) -> String
|
|
109
|
+
def build_lambda_params: (Prism::Node? block_params) -> String
|
|
110
|
+
def extract_block_params: (Prism::BlockNode block) -> Array[String]
|
|
111
|
+
def recv_with_op: (Prism::Node? recv_node, String call_op) -> String
|
|
112
|
+
def wrap_operand: (Prism::Node? node, Symbol parent_op, Symbol side) -> [String, bool]
|
|
113
|
+
def binary_op_separator: (Prism::Node? recv_node, bool recv_wrapped, Symbol op) -> String
|
|
114
|
+
def build_if_chain: (Prism::IfNode node) -> String
|
|
115
|
+
def r_parens: (Prism::ParenthesesNode node) -> String
|
|
116
|
+
def fmt_body: (String? body) -> String
|
|
117
|
+
def binary_operator_call?: (Prism::Node? node) -> bool?
|
|
118
|
+
def setter_call?: (Prism::CallNode node) -> bool?
|
|
119
|
+
def node_returns_bot?: (Prism::Node node) -> bool
|
|
120
|
+
def rescue_var_used?: (Prism::RescueNode rescue_node) -> bool
|
|
121
|
+
def block_uses_it?: (Prism::Node? body) -> bool
|
|
122
|
+
def prism_traverse: (Prism::Node? node) { (Prism::Node) -> void } -> void
|
|
123
|
+
end
|
|
124
|
+
end
|
|
125
|
+
end
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module Pipeline
|
|
3
|
+
class Concatenator
|
|
4
|
+
class GraphSorter
|
|
5
|
+
include TSort[String]
|
|
6
|
+
|
|
7
|
+
def initialize: (DependencyGraph graph) -> void
|
|
8
|
+
def tsort_each_node: () { (String) -> void } -> void
|
|
9
|
+
def tsort_each_child: (String node) { (String) -> void } -> void
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def call: (DependencyGraph graph) -> ConcatenatedSource
|
|
13
|
+
|
|
14
|
+
private
|
|
15
|
+
|
|
16
|
+
def topological_sort: (DependencyGraph graph) -> Array[String]
|
|
17
|
+
def extract_cycle_from_graph: (DependencyGraph graph) -> Array[String]
|
|
18
|
+
def find_cycle_dfs: (DependencyGraph graph, String node, Set[String] visited, Set[String] rec_stack, Array[String] path) -> bool
|
|
19
|
+
def concatenate_files: (DependencyGraph graph, Array[String] sorted_paths) -> ConcatenatedSource
|
|
20
|
+
def collect_stdlib_requires: (FileEntry entry, Array[String] stdlib_requires) -> void
|
|
21
|
+
def process_require_statements: (FileEntry entry, DependencyGraph graph, Set[String] inlined, Hash[String, String] cleaned_cache) -> String
|
|
22
|
+
def offset_based_processing: (String content, Array[require_node_info] nodes, DependencyGraph graph, Set[String] in_class_deps, Set[String] inlined, Hash[String, String] cleaned_cache) -> String
|
|
23
|
+
def line_based_processing: (String content, Array[require_node_info] require_nodes) -> String
|
|
24
|
+
def resolve_node_path: (require_node_info node, DependencyGraph graph) -> String?
|
|
25
|
+
def strip_outer_nesting: (String content) -> String
|
|
26
|
+
end
|
|
27
|
+
end
|
|
28
|
+
end
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module Pipeline
|
|
3
|
+
class ConstantAliaser < Stage
|
|
4
|
+
include RenamePatcher
|
|
5
|
+
|
|
6
|
+
@class_module_cpath_offsets: Set[Integer]
|
|
7
|
+
@constant_mapping: ConstantRenameMapping
|
|
8
|
+
@rename_classes: bool
|
|
9
|
+
|
|
10
|
+
def needs_analysis?: () -> bool
|
|
11
|
+
def initialize: (?rename_classes: bool) -> void
|
|
12
|
+
def collect: (StageContext ctx, Array[patch_entry] patches) -> void
|
|
13
|
+
def finish: (StageContext ctx) -> void
|
|
14
|
+
|
|
15
|
+
private
|
|
16
|
+
|
|
17
|
+
def collect_patches: (Prism::Node node, Array[patch_entry] patches, AnalysisResult analysis) -> void
|
|
18
|
+
|
|
19
|
+
# The patch_* helpers are called for their side effects from the
|
|
20
|
+
# walk_prism block, whose declared result is Symbol? (:skip_children or
|
|
21
|
+
# nil) — untyped rather than void keeps the block body compatible.
|
|
22
|
+
def patch_constant_ref: (Prism::ConstantReadNode | Prism::ConstantPathNode node, Array[patch_entry] patches, AnalysisResult analysis) -> untyped
|
|
23
|
+
def patch_constant_write: (Prism::ConstantWriteNode | Prism::ConstantTargetNode node, Array[patch_entry] patches, AnalysisResult analysis) -> untyped
|
|
24
|
+
def patch_constant_path_write: (Prism::ConstantPathWriteNode node, Array[patch_entry] patches, AnalysisResult analysis) -> untyped
|
|
25
|
+
def patch_class_node: (Prism::ClassNode node, Array[patch_entry] patches, AnalysisResult analysis) -> untyped
|
|
26
|
+
def patch_module_node: (Prism::ModuleNode node, Array[patch_entry] patches, AnalysisResult analysis) -> untyped
|
|
27
|
+
def patch_definition_path: (Prism::ClassNode | Prism::ModuleNode node, Array[patch_entry] patches, Array[Symbol]? class_cpath, AnalysisResult analysis) -> void
|
|
28
|
+
def render_short_cpath: (Array[Symbol] cpath, ?from: Integer) -> String
|
|
29
|
+
def mark_constant_children: (Prism::Node node) -> void
|
|
30
|
+
def build_renamed_via_user_prefix: (Prism::ConstantPathNode node, AnalysisResult analysis) -> String?
|
|
31
|
+
def get_short_cpath: (Array[Symbol] cpath) -> String
|
|
32
|
+
def patch_def_receiver: (Prism::Node receiver, Array[patch_entry] patches, AnalysisResult analysis) -> untyped
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
end
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
module Ryac
|
|
2
|
+
module Pipeline
|
|
3
|
+
class ConstantFold < Stage
|
|
4
|
+
FOLDABLE_OPS: Array[Symbol]
|
|
5
|
+
INTEGER_ONLY_OPS: Array[Symbol]
|
|
6
|
+
|
|
7
|
+
def collect: (StageContext ctx, Array[patch_entry] patches) -> void
|
|
8
|
+
|
|
9
|
+
private
|
|
10
|
+
|
|
11
|
+
def walk: (Prism::Node node, Array[patch_entry] patches) -> void
|
|
12
|
+
def try_constant_fold: (Prism::Node node) -> Numeric?
|
|
13
|
+
def try_fold_binary_op: (Prism::CallNode node) -> Numeric?
|
|
14
|
+
# The operands are Integer | Float at runtime, but RBS's Numeric does
|
|
15
|
+
# not carry the arithmetic operators and the op is dispatched on a
|
|
16
|
+
# Symbol tag, so the operands stay untyped.
|
|
17
|
+
def apply_op: (untyped lhs, Symbol op, untyped rhs) -> Numeric?
|
|
18
|
+
end
|
|
19
|
+
end
|
|
20
|
+
end
|