Cleanup the rubocop config
Go back to rubocop 0.80 for Ruby 2.3 support. Stop depending on the company style guide, as it needs a newer rubocop.
This commit is contained in:
parent
12ee08bf86
commit
b277e75e85
150
.rubocop.yml
150
.rubocop.yml
|
@ -1,13 +1,8 @@
|
||||||
inherit_from: .rubocop_todo.yml
|
|
||||||
|
|
||||||
inherit_gem:
|
|
||||||
rubocop-shopify: rubocop.yml
|
|
||||||
|
|
||||||
AllCops:
|
AllCops:
|
||||||
Exclude:
|
Exclude:
|
||||||
- 'vendor/**/*'
|
- 'vendor/**/*'
|
||||||
- 'tmp/**/*'
|
- 'tmp/**/*'
|
||||||
TargetRubyVersion: 2.5
|
TargetRubyVersion: 2.3
|
||||||
|
|
||||||
# This doesn't take into account retrying from an exception
|
# This doesn't take into account retrying from an exception
|
||||||
Lint/SuppressedException:
|
Lint/SuppressedException:
|
||||||
|
@ -17,6 +12,149 @@ Lint/SuppressedException:
|
||||||
Style/EmptyLiteral:
|
Style/EmptyLiteral:
|
||||||
Enabled: false
|
Enabled: false
|
||||||
|
|
||||||
|
Style/EmptyMethod:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
# allow the use of globals which makes sense in a CLI app like this
|
# allow the use of globals which makes sense in a CLI app like this
|
||||||
Style/GlobalVars:
|
Style/GlobalVars:
|
||||||
Enabled: false
|
Enabled: false
|
||||||
|
|
||||||
|
Style/PercentLiteralDelimiters:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/TrailingCommaInHashLiteral:
|
||||||
|
EnforcedStyleForMultiline: comma
|
||||||
|
|
||||||
|
Style/TrailingCommaInArguments:
|
||||||
|
EnforcedStyleForMultiline: comma
|
||||||
|
|
||||||
|
Layout/LineLength:
|
||||||
|
Max: 120
|
||||||
|
|
||||||
|
Style/TrailingCommaInArguments:
|
||||||
|
EnforcedStyleForMultiline: comma
|
||||||
|
|
||||||
|
Metrics/AbcSize:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Metrics/MethodLength:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Metrics/BlockLength:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Metrics/ClassLength:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Metrics/CyclomaticComplexity:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Metrics/ModuleLength:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Metrics/ParameterLists:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Metrics/PerceivedComplexity:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Naming/MethodName:
|
||||||
|
Exclude:
|
||||||
|
- 'test/**/*'
|
||||||
|
|
||||||
|
Layout/SpaceInsideHashLiteralBraces:
|
||||||
|
EnforcedStyle: no_space
|
||||||
|
|
||||||
|
Naming/RescuedExceptionsVariableName:
|
||||||
|
PreferredName: error
|
||||||
|
|
||||||
|
Bundler/OrderedGems:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Gemspec/OrderedDependencies:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Gemspec/DuplicatedAssignment:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Layout/MultilineMethodCallIndentation:
|
||||||
|
EnforcedStyle: indented
|
||||||
|
|
||||||
|
Style/SymbolArray:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/StderrPuts:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/ModuleFunction:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/IfUnlessModifier:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/GuardClause:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Layout/EndAlignment:
|
||||||
|
EnforcedStyleAlignWith: start_of_line
|
||||||
|
|
||||||
|
Layout/RescueEnsureAlignment:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Layout/FirstHashElementIndentation:
|
||||||
|
EnforcedStyle: consistent
|
||||||
|
|
||||||
|
Style/NumericPredicate:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Layout/SpaceInsideHashLiteralBraces:
|
||||||
|
EnforcedStyle: no_space
|
||||||
|
|
||||||
|
Lint/AssignmentInCondition:
|
||||||
|
AllowSafeAssignment: true
|
||||||
|
|
||||||
|
Lint/UnusedMethodArgument:
|
||||||
|
AllowUnusedKeywordArguments: true
|
||||||
|
|
||||||
|
Security/MarshalLoad:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Security/YAMLLoad:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/Alias:
|
||||||
|
EnforcedStyle: prefer_alias_method
|
||||||
|
|
||||||
|
Style/Documentation:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/DoubleNegation:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/CommentedKeyword:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Naming/VariableNumber:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/Next:
|
||||||
|
Enabled: false
|
||||||
|
|
||||||
|
Style/StringLiterals:
|
||||||
|
EnforcedStyle: double_quotes
|
||||||
|
|
||||||
|
|
||||||
|
Lint/RaiseException:
|
||||||
|
Enabled: true
|
||||||
|
|
||||||
|
Lint/StructNewOverride:
|
||||||
|
Enabled: true
|
||||||
|
|
||||||
|
Style/HashEachMethods:
|
||||||
|
Enabled: true
|
||||||
|
|
||||||
|
Style/HashTransformKeys:
|
||||||
|
Enabled: true
|
||||||
|
|
||||||
|
Style/HashTransformValues:
|
||||||
|
Enabled: true
|
||||||
|
|
|
@ -1,213 +0,0 @@
|
||||||
# This configuration was generated by
|
|
||||||
# `rubocop --auto-gen-config`
|
|
||||||
# on 2022-01-12 21:26:07 UTC using RuboCop version 1.24.1.
|
|
||||||
# The point is for the user to remove these configuration records
|
|
||||||
# one by one as the offenses are removed from the code base.
|
|
||||||
# Note that changes in the inspected code, or installation of new
|
|
||||||
# versions of RuboCop, may require this file to be generated again.
|
|
||||||
|
|
||||||
# Offense count: 1
|
|
||||||
# Configuration parameters: Include.
|
|
||||||
# Include: **/*.gemspec
|
|
||||||
Gemspec/DuplicatedAssignment:
|
|
||||||
Exclude:
|
|
||||||
- 'bootsnap.gemspec'
|
|
||||||
|
|
||||||
# Offense count: 1
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: TreatCommentsAsGroupSeparators, ConsiderPunctuation, Include.
|
|
||||||
# Include: **/*.gemspec
|
|
||||||
Gemspec/OrderedDependencies:
|
|
||||||
Exclude:
|
|
||||||
- 'bootsnap.gemspec'
|
|
||||||
|
|
||||||
# Offense count: 37
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
Layout/EmptyLineAfterMagicComment:
|
|
||||||
Enabled: false
|
|
||||||
|
|
||||||
# Offense count: 1
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
Layout/EmptyLines:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap.rb'
|
|
||||||
|
|
||||||
# Offense count: 2
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: AllowForAlignment, AllowBeforeTrailingComments, ForceEqualSignAlignment.
|
|
||||||
Layout/ExtraSpacing:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/cli.rb'
|
|
||||||
|
|
||||||
# Offense count: 2
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: EnforcedStyle, IndentationWidth.
|
|
||||||
# SupportedStyles: aligned, indented
|
|
||||||
Layout/LineEndStringConcatenationIndentation:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/compile_cache.rb'
|
|
||||||
- 'test/load_path_cache/realpath_cache_test.rb'
|
|
||||||
|
|
||||||
# Offense count: 3
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: EnforcedStyle, IndentationWidth.
|
|
||||||
# SupportedStyles: aligned, indented
|
|
||||||
Layout/MultilineOperationIndentation:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/compile_cache.rb'
|
|
||||||
- 'lib/bootsnap/load_path_cache.rb'
|
|
||||||
|
|
||||||
# Offense count: 1
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
Layout/RescueEnsureAlignment:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/load_path_cache/path.rb'
|
|
||||||
|
|
||||||
# Offense count: 12
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: EnforcedStyle, EnforcedStyleForEmptyBraces.
|
|
||||||
# SupportedStyles: space, no_space, compact
|
|
||||||
# SupportedStylesForEmptyBraces: space, no_space
|
|
||||||
Layout/SpaceInsideHashLiteralBraces:
|
|
||||||
Exclude:
|
|
||||||
- 'test/compile_cache/json_test.rb'
|
|
||||||
- 'test/compile_cache/yaml_test.rb'
|
|
||||||
|
|
||||||
# Offense count: 5
|
|
||||||
# Configuration parameters: AllowSafeAssignment.
|
|
||||||
Lint/AssignmentInCondition:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/cli.rb'
|
|
||||||
- 'lib/bootsnap/compile_cache/json.rb'
|
|
||||||
- 'lib/bootsnap/compile_cache/yaml.rb'
|
|
||||||
- 'lib/bootsnap/load_path_cache/loaded_features_index.rb'
|
|
||||||
|
|
||||||
# Offense count: 5
|
|
||||||
# Configuration parameters: IgnoredPatterns.
|
|
||||||
# SupportedStyles: snake_case, camelCase
|
|
||||||
Naming/MethodName:
|
|
||||||
EnforcedStyle: snake_case
|
|
||||||
|
|
||||||
# Offense count: 1
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: EnforcedStyle, SingleLineConditionsOnly, IncludeTernaryExpressions.
|
|
||||||
# SupportedStyles: assign_to_condition, assign_inside_condition
|
|
||||||
Style/ConditionalAssignment:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap.rb'
|
|
||||||
|
|
||||||
# Offense count: 36
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: IgnoreMacros, IgnoredMethods, IgnoredPatterns, IncludedMacros, AllowParenthesesInMultilineCall, AllowParenthesesInChaining, AllowParenthesesInCamelCaseMethod, AllowParenthesesInStringInterpolation, EnforcedStyle.
|
|
||||||
# SupportedStyles: require_parentheses, omit_parentheses
|
|
||||||
Style/MethodCallWithArgsParentheses:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap.rb'
|
|
||||||
- 'lib/bootsnap/cli.rb'
|
|
||||||
- 'test/cli_test.rb'
|
|
||||||
- 'test/compile_cache/json_test.rb'
|
|
||||||
- 'test/compile_cache/yaml_test.rb'
|
|
||||||
- 'test/compile_cache_test.rb'
|
|
||||||
- 'test/load_path_cache/cache_test.rb'
|
|
||||||
- 'test/load_path_cache/core_ext/kernel_require_test.rb'
|
|
||||||
- 'test/load_path_cache/store_test.rb'
|
|
||||||
- 'test/worker_pool_test.rb'
|
|
||||||
|
|
||||||
# Offense count: 2
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: AllowedMethods.
|
|
||||||
# AllowedMethods: be, be_a, be_an, be_between, be_falsey, be_kind_of, be_instance_of, be_truthy, be_within, eq, eql, end_with, include, match, raise_error, respond_to, start_with
|
|
||||||
Style/NestedParenthesizedCalls:
|
|
||||||
Exclude:
|
|
||||||
- 'test/load_path_cache/core_ext/kernel_require_test.rb'
|
|
||||||
|
|
||||||
# Offense count: 3
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: EnforcedStyle, MinBodyLength.
|
|
||||||
# SupportedStyles: skip_modifier_ifs, always
|
|
||||||
Style/Next:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/cli.rb'
|
|
||||||
|
|
||||||
# Offense count: 2
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
Style/RedundantBegin:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/load_path_cache/path.rb'
|
|
||||||
- 'lib/bootsnap/load_path_cache/store.rb'
|
|
||||||
|
|
||||||
# Offense count: 1
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
Style/RedundantFreeze:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/load_path_cache/store.rb'
|
|
||||||
|
|
||||||
# Offense count: 1
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
Style/RedundantParentheses:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/load_path_cache/cache.rb'
|
|
||||||
|
|
||||||
# Offense count: 7
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
Style/RedundantSelf:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/cli.rb'
|
|
||||||
- 'lib/bootsnap/compile_cache/json.rb'
|
|
||||||
- 'lib/bootsnap/compile_cache/yaml.rb'
|
|
||||||
|
|
||||||
# Offense count: 2
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: ConvertCodeThatCanStartToReturnNil, AllowedMethods.
|
|
||||||
# AllowedMethods: present?, blank?, presence, try, try!
|
|
||||||
Style/SafeNavigation:
|
|
||||||
Exclude:
|
|
||||||
- 'lib/bootsnap/compile_cache/json.rb'
|
|
||||||
- 'lib/bootsnap/compile_cache/yaml.rb'
|
|
||||||
|
|
||||||
# Offense count: 1
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: RequireEnglish, EnforcedStyle.
|
|
||||||
# SupportedStyles: use_perl_names, use_english_names
|
|
||||||
Style/SpecialGlobalVars:
|
|
||||||
Exclude:
|
|
||||||
- 'test/worker_pool_test.rb'
|
|
||||||
|
|
||||||
# Offense count: 593
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: EnforcedStyle, ConsistentQuotesInMultiline.
|
|
||||||
# SupportedStyles: single_quotes, double_quotes
|
|
||||||
Style/StringLiterals:
|
|
||||||
Enabled: false
|
|
||||||
|
|
||||||
# Offense count: 2
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: EnforcedStyle.
|
|
||||||
# SupportedStyles: single_quotes, double_quotes
|
|
||||||
Style/StringLiteralsInInterpolation:
|
|
||||||
Exclude:
|
|
||||||
- 'test/load_path_cache/path_test.rb'
|
|
||||||
- 'test/load_path_cache/realpath_cache_test.rb'
|
|
||||||
|
|
||||||
# Offense count: 2
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: .
|
|
||||||
# SupportedStyles: percent, brackets
|
|
||||||
Style/SymbolArray:
|
|
||||||
EnforcedStyle: percent
|
|
||||||
MinSize: 3
|
|
||||||
|
|
||||||
# Offense count: 1
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: EnforcedStyleForMultiline.
|
|
||||||
# SupportedStylesForMultiline: comma, consistent_comma, no_comma
|
|
||||||
Style/TrailingCommaInHashLiteral:
|
|
||||||
Exclude:
|
|
||||||
- 'bootsnap.gemspec'
|
|
||||||
|
|
||||||
# Offense count: 15
|
|
||||||
# Cop supports --auto-correct.
|
|
||||||
# Configuration parameters: MinSize, WordRegex.
|
|
||||||
# SupportedStyles: percent, brackets
|
|
||||||
Style/WordArray:
|
|
||||||
EnforcedStyle: percent
|
|
9
Gemfile
9
Gemfile
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
source 'https://rubygems.org'
|
|
||||||
|
source "https://rubygems.org"
|
||||||
|
|
||||||
# Specify your gem's dependencies in bootsnap.gemspec
|
# Specify your gem's dependencies in bootsnap.gemspec
|
||||||
gemspec
|
gemspec
|
||||||
|
@ -9,7 +10,7 @@ if ENV["PSYCH_4"]
|
||||||
end
|
end
|
||||||
|
|
||||||
group :development do
|
group :development do
|
||||||
gem 'rubocop'
|
gem "rubocop", "0.81.0" # Ruby 2.3 support
|
||||||
gem 'rubocop-shopify', require: false
|
gem "rubocop-shopify", require: false
|
||||||
gem 'byebug', platform: :ruby
|
gem "byebug", platform: :ruby
|
||||||
end
|
end
|
||||||
|
|
13
Rakefile
13
Rakefile
|
@ -1,12 +1,13 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('rake/extensiontask')
|
|
||||||
require('bundler/gem_tasks')
|
|
||||||
|
|
||||||
gemspec = Gem::Specification.load('bootsnap.gemspec')
|
require("rake/extensiontask")
|
||||||
|
require("bundler/gem_tasks")
|
||||||
|
|
||||||
|
gemspec = Gem::Specification.load("bootsnap.gemspec")
|
||||||
Rake::ExtensionTask.new do |ext|
|
Rake::ExtensionTask.new do |ext|
|
||||||
ext.name = 'bootsnap'
|
ext.name = "bootsnap"
|
||||||
ext.ext_dir = 'ext/bootsnap'
|
ext.ext_dir = "ext/bootsnap"
|
||||||
ext.lib_dir = 'lib/bootsnap'
|
ext.lib_dir = "lib/bootsnap"
|
||||||
ext.gem_spec = gemspec
|
ext.gem_spec = gemspec
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
# coding: utf-8
|
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
lib = File.expand_path('../lib', __FILE__)
|
|
||||||
|
lib = File.expand_path("lib", __dir__)
|
||||||
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
||||||
require('bootsnap/version')
|
require("bootsnap/version")
|
||||||
|
|
||||||
Gem::Specification.new do |spec|
|
Gem::Specification.new do |spec|
|
||||||
spec.name = "bootsnap"
|
spec.name = "bootsnap"
|
||||||
|
@ -17,30 +17,30 @@ Gem::Specification.new do |spec|
|
||||||
spec.homepage = "https://github.com/Shopify/bootsnap"
|
spec.homepage = "https://github.com/Shopify/bootsnap"
|
||||||
|
|
||||||
spec.metadata = {
|
spec.metadata = {
|
||||||
'bug_tracker_uri' => 'https://github.com/Shopify/bootsnap/issues',
|
"bug_tracker_uri" => "https://github.com/Shopify/bootsnap/issues",
|
||||||
'changelog_uri' => 'https://github.com/Shopify/bootsnap/blob/main/CHANGELOG.md',
|
"changelog_uri" => "https://github.com/Shopify/bootsnap/blob/main/CHANGELOG.md",
|
||||||
'source_code_uri' => 'https://github.com/Shopify/bootsnap',
|
"source_code_uri" => "https://github.com/Shopify/bootsnap",
|
||||||
'allowed_push_host' => 'https://rubygems.org'
|
"allowed_push_host" => "https://rubygems.org",
|
||||||
}
|
}
|
||||||
|
|
||||||
spec.files = %x(git ls-files -z ext lib).split("\x0") + %w(CHANGELOG.md LICENSE.txt README.md)
|
spec.files = `git ls-files -z ext lib`.split("\x0") + %w(CHANGELOG.md LICENSE.txt README.md)
|
||||||
spec.require_paths = %w(lib)
|
spec.require_paths = %w(lib)
|
||||||
|
|
||||||
spec.bindir = 'exe'
|
spec.bindir = "exe"
|
||||||
spec.executables = %w(bootsnap)
|
spec.executables = %w(bootsnap)
|
||||||
|
|
||||||
spec.required_ruby_version = '>= 2.3.0'
|
spec.required_ruby_version = ">= 2.3.0"
|
||||||
|
|
||||||
if RUBY_PLATFORM =~ /java/
|
if RUBY_PLATFORM =~ /java/
|
||||||
spec.platform = 'java'
|
spec.platform = "java"
|
||||||
else
|
else
|
||||||
spec.platform = Gem::Platform::RUBY
|
spec.platform = Gem::Platform::RUBY
|
||||||
spec.extensions = ['ext/bootsnap/extconf.rb']
|
spec.extensions = ["ext/bootsnap/extconf.rb"]
|
||||||
end
|
end
|
||||||
|
|
||||||
spec.add_development_dependency("bundler")
|
spec.add_development_dependency("bundler")
|
||||||
spec.add_development_dependency('rake')
|
spec.add_development_dependency("rake")
|
||||||
spec.add_development_dependency('rake-compiler')
|
spec.add_development_dependency("rake-compiler")
|
||||||
spec.add_development_dependency("minitest", "~> 5.0")
|
spec.add_development_dependency("minitest", "~> 5.0")
|
||||||
spec.add_development_dependency("mocha", "~> 1.2")
|
spec.add_development_dependency("mocha", "~> 1.2")
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
#!/usr/bin/env ruby
|
#!/usr/bin/env ruby
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
require 'bootsnap/cli'
|
require "bootsnap/cli"
|
||||||
exit Bootsnap::CLI.new(ARGV).run
|
exit Bootsnap::CLI.new(ARGV).run
|
||||||
|
|
|
@ -1,22 +1,23 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
require("mkmf")
|
require("mkmf")
|
||||||
|
|
||||||
if RUBY_ENGINE == 'ruby'
|
if RUBY_ENGINE == "ruby"
|
||||||
$CFLAGS << ' -O3 '
|
$CFLAGS << " -O3 "
|
||||||
$CFLAGS << ' -std=c99'
|
$CFLAGS << " -std=c99"
|
||||||
|
|
||||||
# ruby.h has some -Wpedantic fails in some cases
|
# ruby.h has some -Wpedantic fails in some cases
|
||||||
# (e.g. https://github.com/Shopify/bootsnap/issues/15)
|
# (e.g. https://github.com/Shopify/bootsnap/issues/15)
|
||||||
unless ['0', '', nil].include?(ENV['BOOTSNAP_PEDANTIC'])
|
unless ["0", "", nil].include?(ENV["BOOTSNAP_PEDANTIC"])
|
||||||
$CFLAGS << ' -Wall'
|
$CFLAGS << " -Wall"
|
||||||
$CFLAGS << ' -Werror'
|
$CFLAGS << " -Werror"
|
||||||
$CFLAGS << ' -Wextra'
|
$CFLAGS << " -Wextra"
|
||||||
$CFLAGS << ' -Wpedantic'
|
$CFLAGS << " -Wpedantic"
|
||||||
|
|
||||||
$CFLAGS << ' -Wno-unused-parameter' # VALUE self has to be there but we don't care what it is.
|
$CFLAGS << " -Wno-unused-parameter" # VALUE self has to be there but we don't care what it is.
|
||||||
$CFLAGS << ' -Wno-keyword-macro' # hiding return
|
$CFLAGS << " -Wno-keyword-macro" # hiding return
|
||||||
$CFLAGS << ' -Wno-gcc-compat' # ruby.h 2.6.0 on macos 10.14, dunno
|
$CFLAGS << " -Wno-gcc-compat" # ruby.h 2.6.0 on macos 10.14, dunno
|
||||||
$CFLAGS << ' -Wno-compound-token-split-by-macro'
|
$CFLAGS << " -Wno-compound-token-split-by-macro"
|
||||||
end
|
end
|
||||||
|
|
||||||
create_makefile("bootsnap/bootsnap")
|
create_makefile("bootsnap/bootsnap")
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
require_relative('bootsnap/version')
|
require_relative("bootsnap/version")
|
||||||
require_relative('bootsnap/bundler')
|
require_relative("bootsnap/bundler")
|
||||||
require_relative('bootsnap/load_path_cache')
|
require_relative("bootsnap/load_path_cache")
|
||||||
require_relative('bootsnap/compile_cache')
|
require_relative("bootsnap/compile_cache")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
InvalidConfiguration = Class.new(StandardError)
|
InvalidConfiguration = Class.new(StandardError)
|
||||||
|
@ -18,10 +18,10 @@ module Bootsnap
|
||||||
|
|
||||||
def self.logger=(logger)
|
def self.logger=(logger)
|
||||||
@logger = logger
|
@logger = logger
|
||||||
if logger.respond_to?(:debug)
|
self.instrumentation = if logger.respond_to?(:debug)
|
||||||
self.instrumentation = ->(event, path) { @logger.debug("[Bootsnap] #{event} #{path}") }
|
->(event, path) { @logger.debug("[Bootsnap] #{event} #{path}") }
|
||||||
else
|
else
|
||||||
self.instrumentation = ->(event, path) { @logger.call("[Bootsnap] #{event} #{path}") }
|
->(event, path) { @logger.call("[Bootsnap] #{event} #{path}") }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -62,13 +62,15 @@ module Bootsnap
|
||||||
"to turn `compile_cache_iseq` off on Ruby 2.5"
|
"to turn `compile_cache_iseq` off on Ruby 2.5"
|
||||||
end
|
end
|
||||||
|
|
||||||
Bootsnap::LoadPathCache.setup(
|
if load_path_cache
|
||||||
cache_path: cache_dir + '/bootsnap/load-path-cache',
|
Bootsnap::LoadPathCache.setup(
|
||||||
development_mode: development_mode,
|
cache_path: cache_dir + "/bootsnap/load-path-cache",
|
||||||
) if load_path_cache
|
development_mode: development_mode,
|
||||||
|
)
|
||||||
|
end
|
||||||
|
|
||||||
Bootsnap::CompileCache.setup(
|
Bootsnap::CompileCache.setup(
|
||||||
cache_dir: cache_dir + '/bootsnap/compile-cache',
|
cache_dir: cache_dir + "/bootsnap/compile-cache",
|
||||||
iseq: compile_cache_iseq,
|
iseq: compile_cache_iseq,
|
||||||
yaml: compile_cache_yaml,
|
yaml: compile_cache_yaml,
|
||||||
json: compile_cache_json,
|
json: compile_cache_json,
|
||||||
|
@ -79,18 +81,18 @@ module Bootsnap
|
||||||
return @iseq_cache_supported if defined? @iseq_cache_supported
|
return @iseq_cache_supported if defined? @iseq_cache_supported
|
||||||
|
|
||||||
ruby_version = Gem::Version.new(RUBY_VERSION)
|
ruby_version = Gem::Version.new(RUBY_VERSION)
|
||||||
@iseq_cache_supported = ruby_version < Gem::Version.new('2.5.0') || ruby_version >= Gem::Version.new('2.6.0')
|
@iseq_cache_supported = ruby_version < Gem::Version.new("2.5.0") || ruby_version >= Gem::Version.new("2.6.0")
|
||||||
end
|
end
|
||||||
|
|
||||||
def self.default_setup
|
def self.default_setup
|
||||||
env = ENV['RAILS_ENV'] || ENV['RACK_ENV'] || ENV['ENV']
|
env = ENV["RAILS_ENV"] || ENV["RACK_ENV"] || ENV["ENV"]
|
||||||
development_mode = ['', nil, 'development'].include?(env)
|
development_mode = ["", nil, "development"].include?(env)
|
||||||
|
|
||||||
unless ENV['DISABLE_BOOTSNAP']
|
unless ENV["DISABLE_BOOTSNAP"]
|
||||||
cache_dir = ENV['BOOTSNAP_CACHE_DIR']
|
cache_dir = ENV["BOOTSNAP_CACHE_DIR"]
|
||||||
unless cache_dir
|
unless cache_dir
|
||||||
config_dir_frame = caller.detect do |line|
|
config_dir_frame = caller.detect do |line|
|
||||||
line.include?('/config/')
|
line.include?("/config/")
|
||||||
end
|
end
|
||||||
|
|
||||||
unless config_dir_frame
|
unless config_dir_frame
|
||||||
|
@ -102,35 +104,34 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
path = config_dir_frame.split(/:\d+:/).first
|
path = config_dir_frame.split(/:\d+:/).first
|
||||||
path = File.dirname(path) until File.basename(path) == 'config'
|
path = File.dirname(path) until File.basename(path) == "config"
|
||||||
app_root = File.dirname(path)
|
app_root = File.dirname(path)
|
||||||
|
|
||||||
cache_dir = File.join(app_root, 'tmp', 'cache')
|
cache_dir = File.join(app_root, "tmp", "cache")
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
setup(
|
setup(
|
||||||
cache_dir: cache_dir,
|
cache_dir: cache_dir,
|
||||||
development_mode: development_mode,
|
development_mode: development_mode,
|
||||||
load_path_cache: !ENV['DISABLE_BOOTSNAP_LOAD_PATH_CACHE'],
|
load_path_cache: !ENV["DISABLE_BOOTSNAP_LOAD_PATH_CACHE"],
|
||||||
compile_cache_iseq: !ENV['DISABLE_BOOTSNAP_COMPILE_CACHE'] && iseq_cache_supported?,
|
compile_cache_iseq: !ENV["DISABLE_BOOTSNAP_COMPILE_CACHE"] && iseq_cache_supported?,
|
||||||
compile_cache_yaml: !ENV['DISABLE_BOOTSNAP_COMPILE_CACHE'],
|
compile_cache_yaml: !ENV["DISABLE_BOOTSNAP_COMPILE_CACHE"],
|
||||||
compile_cache_json: !ENV['DISABLE_BOOTSNAP_COMPILE_CACHE'],
|
compile_cache_json: !ENV["DISABLE_BOOTSNAP_COMPILE_CACHE"],
|
||||||
)
|
)
|
||||||
|
|
||||||
if ENV['BOOTSNAP_LOG']
|
if ENV["BOOTSNAP_LOG"]
|
||||||
log!
|
log!
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
if RbConfig::CONFIG['host_os'] =~ /mswin|mingw|cygwin/
|
if RbConfig::CONFIG["host_os"] =~ /mswin|mingw|cygwin/
|
||||||
def self.absolute_path?(path)
|
def self.absolute_path?(path)
|
||||||
path[1] == ':'
|
path[1] == ":"
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
def self.absolute_path?(path)
|
def self.absolute_path?(path)
|
||||||
path.start_with?('/')
|
path.start_with?("/")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
extend(self)
|
extend(self)
|
||||||
|
|
||||||
|
|
|
@ -1,10 +1,10 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
require 'bootsnap'
|
require "bootsnap"
|
||||||
require 'bootsnap/cli/worker_pool'
|
require "bootsnap/cli/worker_pool"
|
||||||
require 'optparse'
|
require "optparse"
|
||||||
require 'fileutils'
|
require "fileutils"
|
||||||
require 'etc'
|
require "etc"
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
class CLI
|
class CLI
|
||||||
|
@ -25,7 +25,7 @@ module Bootsnap
|
||||||
|
|
||||||
def initialize(argv)
|
def initialize(argv)
|
||||||
@argv = argv
|
@argv = argv
|
||||||
self.cache_dir = ENV.fetch('BOOTSNAP_CACHE_DIR', 'tmp/cache')
|
self.cache_dir = ENV.fetch("BOOTSNAP_CACHE_DIR", "tmp/cache")
|
||||||
self.compile_gemfile = false
|
self.compile_gemfile = false
|
||||||
self.exclude = nil
|
self.exclude = nil
|
||||||
self.verbose = false
|
self.verbose = false
|
||||||
|
@ -36,16 +36,16 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def precompile_command(*sources)
|
def precompile_command(*sources)
|
||||||
require 'bootsnap/compile_cache/iseq'
|
require "bootsnap/compile_cache/iseq"
|
||||||
require 'bootsnap/compile_cache/yaml'
|
require "bootsnap/compile_cache/yaml"
|
||||||
require 'bootsnap/compile_cache/json'
|
require "bootsnap/compile_cache/json"
|
||||||
|
|
||||||
fix_default_encoding do
|
fix_default_encoding do
|
||||||
Bootsnap::CompileCache::ISeq.cache_dir = self.cache_dir
|
Bootsnap::CompileCache::ISeq.cache_dir = cache_dir
|
||||||
Bootsnap::CompileCache::YAML.init!
|
Bootsnap::CompileCache::YAML.init!
|
||||||
Bootsnap::CompileCache::YAML.cache_dir = self.cache_dir
|
Bootsnap::CompileCache::YAML.cache_dir = cache_dir
|
||||||
Bootsnap::CompileCache::JSON.init!
|
Bootsnap::CompileCache::JSON.init!
|
||||||
Bootsnap::CompileCache::JSON.cache_dir = self.cache_dir
|
Bootsnap::CompileCache::JSON.cache_dir = cache_dir
|
||||||
|
|
||||||
@work_pool = WorkerPool.create(size: jobs, jobs: {
|
@work_pool = WorkerPool.create(size: jobs, jobs: {
|
||||||
ruby: method(:precompile_ruby),
|
ruby: method(:precompile_ruby),
|
||||||
|
@ -61,7 +61,7 @@ module Bootsnap
|
||||||
|
|
||||||
if compile_gemfile
|
if compile_gemfile
|
||||||
# Some gems embed their tests, they're very unlikely to be loaded, so not worth precompiling.
|
# Some gems embed their tests, they're very unlikely to be loaded, so not worth precompiling.
|
||||||
gem_exclude = Regexp.union([exclude, '/spec/', '/test/'].compact)
|
gem_exclude = Regexp.union([exclude, "/spec/", "/test/"].compact)
|
||||||
precompile_ruby_files($LOAD_PATH.map { |d| File.expand_path(d) }, exclude: gem_exclude)
|
precompile_ruby_files($LOAD_PATH.map { |d| File.expand_path(d) }, exclude: gem_exclude)
|
||||||
|
|
||||||
# Gems that include JSON or YAML files usually don't put them in `lib/`.
|
# Gems that include JSON or YAML files usually don't put them in `lib/`.
|
||||||
|
@ -72,7 +72,7 @@ module Bootsnap
|
||||||
precompile_json_files(gem_paths, exclude: gem_exclude)
|
precompile_json_files(gem_paths, exclude: gem_exclude)
|
||||||
end
|
end
|
||||||
|
|
||||||
if exitstatus = @work_pool.shutdown
|
if (exitstatus = @work_pool.shutdown)
|
||||||
exit(exitstatus)
|
exit(exitstatus)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -89,7 +89,7 @@ module Bootsnap
|
||||||
if dir_sort
|
if dir_sort
|
||||||
def list_files(path, pattern)
|
def list_files(path, pattern)
|
||||||
if File.directory?(path)
|
if File.directory?(path)
|
||||||
Dir[File.join(path, pattern), sort: false]
|
Dir[File.join(path, pattern), sort: false]
|
||||||
elsif File.exist?(path)
|
elsif File.exist?(path)
|
||||||
[path]
|
[path]
|
||||||
else
|
else
|
||||||
|
@ -99,7 +99,7 @@ module Bootsnap
|
||||||
else
|
else
|
||||||
def list_files(path, pattern)
|
def list_files(path, pattern)
|
||||||
if File.directory?(path)
|
if File.directory?(path)
|
||||||
Dir[File.join(path, pattern)]
|
Dir[File.join(path, pattern)]
|
||||||
elsif File.exist?(path)
|
elsif File.exist?(path)
|
||||||
[path]
|
[path]
|
||||||
else
|
else
|
||||||
|
@ -126,9 +126,9 @@ module Bootsnap
|
||||||
|
|
||||||
load_paths.each do |path|
|
load_paths.each do |path|
|
||||||
if !exclude || !exclude.match?(path)
|
if !exclude || !exclude.match?(path)
|
||||||
list_files(path, '**/*.{yml,yaml}').each do |yaml_file|
|
list_files(path, "**/*.{yml,yaml}").each do |yaml_file|
|
||||||
# We ignore hidden files to not match the various .ci.yml files
|
# We ignore hidden files to not match the various .ci.yml files
|
||||||
if !File.basename(yaml_file).start_with?('.') && (!exclude || !exclude.match?(yaml_file))
|
if !File.basename(yaml_file).start_with?(".") && (!exclude || !exclude.match?(yaml_file))
|
||||||
@work_pool.push(:yaml, yaml_file)
|
@work_pool.push(:yaml, yaml_file)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -149,9 +149,9 @@ module Bootsnap
|
||||||
|
|
||||||
load_paths.each do |path|
|
load_paths.each do |path|
|
||||||
if !exclude || !exclude.match?(path)
|
if !exclude || !exclude.match?(path)
|
||||||
list_files(path, '**/*.json').each do |json_file|
|
list_files(path, "**/*.json").each do |json_file|
|
||||||
# We ignore hidden files to not match the various .config.json files
|
# We ignore hidden files to not match the various .config.json files
|
||||||
if !File.basename(json_file).start_with?('.') && (!exclude || !exclude.match?(json_file))
|
if !File.basename(json_file).start_with?(".") && (!exclude || !exclude.match?(json_file))
|
||||||
@work_pool.push(:json, json_file)
|
@work_pool.push(:json, json_file)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -172,7 +172,7 @@ module Bootsnap
|
||||||
|
|
||||||
load_paths.each do |path|
|
load_paths.each do |path|
|
||||||
if !exclude || !exclude.match?(path)
|
if !exclude || !exclude.match?(path)
|
||||||
list_files(path, '**/*.rb').each do |ruby_file|
|
list_files(path, "**/*.rb").each do |ruby_file|
|
||||||
if !exclude || !exclude.match?(ruby_file)
|
if !exclude || !exclude.match?(ruby_file)
|
||||||
@work_pool.push(:ruby, ruby_file)
|
@work_pool.push(:ruby, ruby_file)
|
||||||
end
|
end
|
||||||
|
@ -210,7 +210,7 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def cache_dir=(dir)
|
def cache_dir=(dir)
|
||||||
@cache_dir = File.expand_path(File.join(dir, 'bootsnap/compile-cache'))
|
@cache_dir = File.expand_path(File.join(dir, "bootsnap/compile-cache"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def exclude_pattern(pattern)
|
def exclude_pattern(pattern)
|
||||||
|
@ -225,24 +225,24 @@ module Bootsnap
|
||||||
opts.separator "GLOBAL OPTIONS"
|
opts.separator "GLOBAL OPTIONS"
|
||||||
opts.separator ""
|
opts.separator ""
|
||||||
|
|
||||||
help = <<~EOS
|
help = <<~HELP
|
||||||
Path to the bootsnap cache directory. Defaults to tmp/cache
|
Path to the bootsnap cache directory. Defaults to tmp/cache
|
||||||
EOS
|
HELP
|
||||||
opts.on('--cache-dir DIR', help.strip) do |dir|
|
opts.on("--cache-dir DIR", help.strip) do |dir|
|
||||||
self.cache_dir = dir
|
self.cache_dir = dir
|
||||||
end
|
end
|
||||||
|
|
||||||
help = <<~EOS
|
help = <<~HELP
|
||||||
Print precompiled paths.
|
Print precompiled paths.
|
||||||
EOS
|
HELP
|
||||||
opts.on('--verbose', '-v', help.strip) do
|
opts.on("--verbose", "-v", help.strip) do
|
||||||
self.verbose = true
|
self.verbose = true
|
||||||
end
|
end
|
||||||
|
|
||||||
help = <<~EOS
|
help = <<~HELP
|
||||||
Number of workers to use. Default to number of processors, set to 0 to disable multi-processing.
|
Number of workers to use. Default to number of processors, set to 0 to disable multi-processing.
|
||||||
EOS
|
HELP
|
||||||
opts.on('--jobs JOBS', '-j', help.strip) do |jobs|
|
opts.on("--jobs JOBS", "-j", help.strip) do |jobs|
|
||||||
self.jobs = Integer(jobs)
|
self.jobs = Integer(jobs)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -251,30 +251,30 @@ module Bootsnap
|
||||||
opts.separator ""
|
opts.separator ""
|
||||||
opts.separator " precompile [DIRECTORIES...]: Precompile all .rb files in the passed directories"
|
opts.separator " precompile [DIRECTORIES...]: Precompile all .rb files in the passed directories"
|
||||||
|
|
||||||
help = <<~EOS
|
help = <<~HELP
|
||||||
Precompile the gems in Gemfile
|
Precompile the gems in Gemfile
|
||||||
EOS
|
HELP
|
||||||
opts.on('--gemfile', help) { self.compile_gemfile = true }
|
opts.on("--gemfile", help) { self.compile_gemfile = true }
|
||||||
|
|
||||||
help = <<~EOS
|
help = <<~HELP
|
||||||
Path pattern to not precompile. e.g. --exclude 'aws-sdk|google-api'
|
Path pattern to not precompile. e.g. --exclude 'aws-sdk|google-api'
|
||||||
EOS
|
HELP
|
||||||
opts.on('--exclude PATTERN', help) { |pattern| exclude_pattern(pattern) }
|
opts.on("--exclude PATTERN", help) { |pattern| exclude_pattern(pattern) }
|
||||||
|
|
||||||
help = <<~EOS
|
help = <<~HELP
|
||||||
Disable ISeq (.rb) precompilation.
|
Disable ISeq (.rb) precompilation.
|
||||||
EOS
|
HELP
|
||||||
opts.on('--no-iseq', help) { self.iseq = false }
|
opts.on("--no-iseq", help) { self.iseq = false }
|
||||||
|
|
||||||
help = <<~EOS
|
help = <<~HELP
|
||||||
Disable YAML precompilation.
|
Disable YAML precompilation.
|
||||||
EOS
|
HELP
|
||||||
opts.on('--no-yaml', help) { self.yaml = false }
|
opts.on("--no-yaml", help) { self.yaml = false }
|
||||||
|
|
||||||
help = <<~EOS
|
help = <<~HELP
|
||||||
Disable JSON precompilation.
|
Disable JSON precompilation.
|
||||||
EOS
|
HELP
|
||||||
opts.on('--no-json', help) { self.json = false }
|
opts.on("--no-json", help) { self.json = false }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -63,6 +63,7 @@ module Bootsnap
|
||||||
loop do
|
loop do
|
||||||
job, *args = Marshal.load(@pipe_out)
|
job, *args = Marshal.load(@pipe_out)
|
||||||
return if job == :exit
|
return if job == :exit
|
||||||
|
|
||||||
@jobs.fetch(job).call(*args)
|
@jobs.fetch(job).call(*args)
|
||||||
end
|
end
|
||||||
rescue IOError
|
rescue IOError
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module CompileCache
|
module CompileCache
|
||||||
Error = Class.new(StandardError)
|
Error = Class.new(StandardError)
|
||||||
|
@ -7,7 +8,7 @@ module Bootsnap
|
||||||
def self.setup(cache_dir:, iseq:, yaml:, json:)
|
def self.setup(cache_dir:, iseq:, yaml:, json:)
|
||||||
if iseq
|
if iseq
|
||||||
if supported?
|
if supported?
|
||||||
require_relative('compile_cache/iseq')
|
require_relative("compile_cache/iseq")
|
||||||
Bootsnap::CompileCache::ISeq.install!(cache_dir)
|
Bootsnap::CompileCache::ISeq.install!(cache_dir)
|
||||||
elsif $VERBOSE
|
elsif $VERBOSE
|
||||||
warn("[bootsnap/setup] bytecode caching is not supported on this implementation of Ruby")
|
warn("[bootsnap/setup] bytecode caching is not supported on this implementation of Ruby")
|
||||||
|
@ -16,7 +17,7 @@ module Bootsnap
|
||||||
|
|
||||||
if yaml
|
if yaml
|
||||||
if supported?
|
if supported?
|
||||||
require_relative('compile_cache/yaml')
|
require_relative("compile_cache/yaml")
|
||||||
Bootsnap::CompileCache::YAML.install!(cache_dir)
|
Bootsnap::CompileCache::YAML.install!(cache_dir)
|
||||||
elsif $VERBOSE
|
elsif $VERBOSE
|
||||||
warn("[bootsnap/setup] YAML parsing caching is not supported on this implementation of Ruby")
|
warn("[bootsnap/setup] YAML parsing caching is not supported on this implementation of Ruby")
|
||||||
|
@ -25,7 +26,7 @@ module Bootsnap
|
||||||
|
|
||||||
if json
|
if json
|
||||||
if supported?
|
if supported?
|
||||||
require_relative('compile_cache/json')
|
require_relative("compile_cache/json")
|
||||||
Bootsnap::CompileCache::JSON.install!(cache_dir)
|
Bootsnap::CompileCache::JSON.install!(cache_dir)
|
||||||
elsif $VERBOSE
|
elsif $VERBOSE
|
||||||
warn("[bootsnap/setup] JSON parsing caching is not supported on this implementation of Ruby")
|
warn("[bootsnap/setup] JSON parsing caching is not supported on this implementation of Ruby")
|
||||||
|
@ -44,9 +45,9 @@ module Bootsnap
|
||||||
|
|
||||||
def self.supported?
|
def self.supported?
|
||||||
# only enable on 'ruby' (MRI), POSIX (darwin, linux, *bsd), Windows (RubyInstaller2) and >= 2.3.0
|
# only enable on 'ruby' (MRI), POSIX (darwin, linux, *bsd), Windows (RubyInstaller2) and >= 2.3.0
|
||||||
RUBY_ENGINE == 'ruby' &&
|
RUBY_ENGINE == "ruby" &&
|
||||||
RUBY_PLATFORM =~ /darwin|linux|bsd|mswin|mingw|cygwin/ &&
|
RUBY_PLATFORM =~ /darwin|linux|bsd|mswin|mingw|cygwin/ &&
|
||||||
Gem::Version.new(RUBY_VERSION) >= Gem::Version.new("2.3.0")
|
Gem::Version.new(RUBY_VERSION) >= Gem::Version.new("2.3.0")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('bootsnap/bootsnap')
|
|
||||||
require('zlib')
|
require("bootsnap/bootsnap")
|
||||||
|
require("zlib")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module CompileCache
|
module CompileCache
|
||||||
|
@ -23,27 +24,27 @@ module Bootsnap
|
||||||
iseq = begin
|
iseq = begin
|
||||||
RubyVM::InstructionSequence.compile_file(path)
|
RubyVM::InstructionSequence.compile_file(path)
|
||||||
rescue SyntaxError
|
rescue SyntaxError
|
||||||
raise(Uncompilable, 'syntax error')
|
raise(Uncompilable, "syntax error")
|
||||||
end
|
end
|
||||||
|
|
||||||
begin
|
begin
|
||||||
iseq.to_binary
|
iseq.to_binary
|
||||||
rescue TypeError
|
rescue TypeError
|
||||||
raise(Uncompilable, 'ruby bug #18250')
|
raise(Uncompilable, "ruby bug #18250")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
def self.input_to_storage(_, path)
|
def self.input_to_storage(_, path)
|
||||||
RubyVM::InstructionSequence.compile_file(path).to_binary
|
RubyVM::InstructionSequence.compile_file(path).to_binary
|
||||||
rescue SyntaxError
|
rescue SyntaxError
|
||||||
raise(Uncompilable, 'syntax error')
|
raise(Uncompilable, "syntax error")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def self.storage_to_output(binary, _args)
|
def self.storage_to_output(binary, _args)
|
||||||
RubyVM::InstructionSequence.load_from_binary(binary)
|
RubyVM::InstructionSequence.load_from_binary(binary)
|
||||||
rescue RuntimeError => e
|
rescue RuntimeError => error
|
||||||
if e.message == 'broken binary format'
|
if error.message == "broken binary format"
|
||||||
STDERR.puts("[Bootsnap::CompileCache] warning: rejecting broken binary")
|
STDERR.puts("[Bootsnap::CompileCache] warning: rejecting broken binary")
|
||||||
nil
|
nil
|
||||||
else
|
else
|
||||||
|
@ -80,8 +81,8 @@ module Bootsnap
|
||||||
Bootsnap::CompileCache::ISeq.fetch(path.to_s)
|
Bootsnap::CompileCache::ISeq.fetch(path.to_s)
|
||||||
rescue Errno::EACCES
|
rescue Errno::EACCES
|
||||||
Bootsnap::CompileCache.permission_error(path)
|
Bootsnap::CompileCache.permission_error(path)
|
||||||
rescue RuntimeError => e
|
rescue RuntimeError => error
|
||||||
if e.message =~ /unmatched platform/
|
if error.message =~ /unmatched platform/
|
||||||
puts("unmatched platform for file #{path}")
|
puts("unmatched platform for file #{path}")
|
||||||
end
|
end
|
||||||
raise
|
raise
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('bootsnap/bootsnap')
|
|
||||||
|
require("bootsnap/bootsnap")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module CompileCache
|
module CompileCache
|
||||||
|
@ -13,7 +14,7 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def storage_to_output(data, kwargs)
|
def storage_to_output(data, kwargs)
|
||||||
if kwargs && kwargs.key?(:symbolize_names)
|
if kwargs&.key?(:symbolize_names)
|
||||||
kwargs[:symbolize_keys] = kwargs.delete(:symbolize_names)
|
kwargs[:symbolize_keys] = kwargs.delete(:symbolize_names)
|
||||||
end
|
end
|
||||||
msgpack_factory.load(data, kwargs)
|
msgpack_factory.load(data, kwargs)
|
||||||
|
@ -40,22 +41,23 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def init!
|
def init!
|
||||||
require('json')
|
require("json")
|
||||||
require('msgpack')
|
require("msgpack")
|
||||||
|
|
||||||
self.msgpack_factory = MessagePack::Factory.new
|
self.msgpack_factory = MessagePack::Factory.new
|
||||||
self.supported_options = [:symbolize_names]
|
self.supported_options = [:symbolize_names]
|
||||||
if ::JSON.parse('["foo"]', freeze: true).first.frozen?
|
if ::JSON.parse('["foo"]', freeze: true).first.frozen?
|
||||||
self.supported_options = [:freeze]
|
self.supported_options = [:freeze]
|
||||||
end
|
end
|
||||||
self.supported_options.freeze
|
supported_options.freeze
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
module Patch
|
module Patch
|
||||||
def load_file(path, *args)
|
def load_file(path, *args)
|
||||||
return super if args.size > 1
|
return super if args.size > 1
|
||||||
if kwargs = args.first
|
|
||||||
|
if (kwargs = args.first)
|
||||||
return super unless kwargs.is_a?(Hash)
|
return super unless kwargs.is_a?(Hash)
|
||||||
return super unless (kwargs.keys - ::Bootsnap::CompileCache::JSON.supported_options).empty?
|
return super unless (kwargs.keys - ::Bootsnap::CompileCache::JSON.supported_options).empty?
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('bootsnap/bootsnap')
|
|
||||||
|
require("bootsnap/bootsnap")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module CompileCache
|
module CompileCache
|
||||||
|
@ -16,7 +17,7 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def storage_to_output(data, kwargs)
|
def storage_to_output(data, kwargs)
|
||||||
if kwargs && kwargs.key?(:symbolize_names)
|
if kwargs&.key?(:symbolize_names)
|
||||||
kwargs[:symbolize_keys] = kwargs.delete(:symbolize_names)
|
kwargs[:symbolize_keys] = kwargs.delete(:symbolize_names)
|
||||||
end
|
end
|
||||||
msgpack_factory.load(data, kwargs)
|
msgpack_factory.load(data, kwargs)
|
||||||
|
@ -33,6 +34,7 @@ module Bootsnap
|
||||||
def strict_load(payload, *args)
|
def strict_load(payload, *args)
|
||||||
ast = ::YAML.parse(payload)
|
ast = ::YAML.parse(payload)
|
||||||
return ast unless ast
|
return ast unless ast
|
||||||
|
|
||||||
strict_visitor.create(*args).visit(ast)
|
strict_visitor.create(*args).visit(ast)
|
||||||
end
|
end
|
||||||
ruby2_keywords :strict_load if respond_to?(:ruby2_keywords, true)
|
ruby2_keywords :strict_load if respond_to?(:ruby2_keywords, true)
|
||||||
|
@ -52,14 +54,14 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def init!
|
def init!
|
||||||
require('yaml')
|
require("yaml")
|
||||||
require('msgpack')
|
require("msgpack")
|
||||||
require('date')
|
require("date")
|
||||||
|
|
||||||
if Patch.method_defined?(:unsafe_load_file) && !::YAML.respond_to?(:unsafe_load_file)
|
if Patch.method_defined?(:unsafe_load_file) && !::YAML.respond_to?(:unsafe_load_file)
|
||||||
Patch.send(:remove_method, :unsafe_load_file)
|
Patch.send(:remove_method, :unsafe_load_file)
|
||||||
end
|
end
|
||||||
if Patch.method_defined?(:load_file) && ::YAML::VERSION >= '4'
|
if Patch.method_defined?(:load_file) && ::YAML::VERSION >= "4"
|
||||||
Patch.send(:remove_method, :load_file)
|
Patch.send(:remove_method, :load_file)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -74,7 +76,7 @@ module Bootsnap
|
||||||
MessagePack::Timestamp::TYPE, # or just -1
|
MessagePack::Timestamp::TYPE, # or just -1
|
||||||
Time,
|
Time,
|
||||||
packer: MessagePack::Time::Packer,
|
packer: MessagePack::Time::Packer,
|
||||||
unpacker: MessagePack::Time::Unpacker
|
unpacker: MessagePack::Time::Unpacker,
|
||||||
)
|
)
|
||||||
|
|
||||||
marshal_fallback = {
|
marshal_fallback = {
|
||||||
|
@ -94,14 +96,14 @@ module Bootsnap
|
||||||
self.supported_options = []
|
self.supported_options = []
|
||||||
params = ::YAML.method(:load).parameters
|
params = ::YAML.method(:load).parameters
|
||||||
if params.include?([:key, :symbolize_names])
|
if params.include?([:key, :symbolize_names])
|
||||||
self.supported_options << :symbolize_names
|
supported_options << :symbolize_names
|
||||||
end
|
end
|
||||||
if params.include?([:key, :freeze])
|
if params.include?([:key, :freeze])
|
||||||
if factory.load(factory.dump('yaml'), freeze: true).frozen?
|
if factory.load(factory.dump("yaml"), freeze: true).frozen?
|
||||||
self.supported_options << :freeze
|
supported_options << :freeze
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
self.supported_options.freeze
|
supported_options.freeze
|
||||||
end
|
end
|
||||||
|
|
||||||
def strict_visitor
|
def strict_visitor
|
||||||
|
@ -110,6 +112,7 @@ module Bootsnap
|
||||||
if target.tag
|
if target.tag
|
||||||
raise Uncompilable, "YAML tags are not supported: #{target.tag}"
|
raise Uncompilable, "YAML tags are not supported: #{target.tag}"
|
||||||
end
|
end
|
||||||
|
|
||||||
super
|
super
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -119,7 +122,8 @@ module Bootsnap
|
||||||
module Patch
|
module Patch
|
||||||
def load_file(path, *args)
|
def load_file(path, *args)
|
||||||
return super if args.size > 1
|
return super if args.size > 1
|
||||||
if kwargs = args.first
|
|
||||||
|
if (kwargs = args.first)
|
||||||
return super unless kwargs.is_a?(Hash)
|
return super unless kwargs.is_a?(Hash)
|
||||||
return super unless (kwargs.keys - ::Bootsnap::CompileCache::YAML.supported_options).empty?
|
return super unless (kwargs.keys - ::Bootsnap::CompileCache::YAML.supported_options).empty?
|
||||||
end
|
end
|
||||||
|
@ -140,7 +144,8 @@ module Bootsnap
|
||||||
|
|
||||||
def unsafe_load_file(path, *args)
|
def unsafe_load_file(path, *args)
|
||||||
return super if args.size > 1
|
return super if args.size > 1
|
||||||
if kwargs = args.first
|
|
||||||
|
if (kwargs = args.first)
|
||||||
return super unless kwargs.is_a?(Hash)
|
return super unless kwargs.is_a?(Hash)
|
||||||
return super unless (kwargs.keys - ::Bootsnap::CompileCache::YAML.supported_options).empty?
|
return super unless (kwargs.keys - ::Bootsnap::CompileCache::YAML.supported_options).empty?
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,9 +1,10 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module ExplicitRequire
|
module ExplicitRequire
|
||||||
ARCHDIR = RbConfig::CONFIG['archdir']
|
ARCHDIR = RbConfig::CONFIG["archdir"]
|
||||||
RUBYLIBDIR = RbConfig::CONFIG['rubylibdir']
|
RUBYLIBDIR = RbConfig::CONFIG["rubylibdir"]
|
||||||
DLEXT = RbConfig::CONFIG['DLEXT']
|
DLEXT = RbConfig::CONFIG["DLEXT"]
|
||||||
|
|
||||||
def self.from_self(feature)
|
def self.from_self(feature)
|
||||||
require_relative("../#{feature}")
|
require_relative("../#{feature}")
|
||||||
|
|
|
@ -5,9 +5,9 @@ module Bootsnap
|
||||||
ReturnFalse = Class.new(StandardError)
|
ReturnFalse = Class.new(StandardError)
|
||||||
FallbackScan = Class.new(StandardError)
|
FallbackScan = Class.new(StandardError)
|
||||||
|
|
||||||
DOT_RB = '.rb'
|
DOT_RB = ".rb"
|
||||||
DOT_SO = '.so'
|
DOT_SO = ".so"
|
||||||
SLASH = '/'
|
SLASH = "/"
|
||||||
|
|
||||||
# If a NameError happens several levels deep, don't re-handle it
|
# If a NameError happens several levels deep, don't re-handle it
|
||||||
# all the way up the chain: mark it once and bubble it up without
|
# all the way up the chain: mark it once and bubble it up without
|
||||||
|
@ -15,7 +15,7 @@ module Bootsnap
|
||||||
ERROR_TAG_IVAR = :@__bootsnap_rescued
|
ERROR_TAG_IVAR = :@__bootsnap_rescued
|
||||||
|
|
||||||
DL_EXTENSIONS = ::RbConfig::CONFIG
|
DL_EXTENSIONS = ::RbConfig::CONFIG
|
||||||
.values_at('DLEXT', 'DLEXT2')
|
.values_at("DLEXT", "DLEXT2")
|
||||||
.reject { |ext| !ext || ext.empty? }
|
.reject { |ext| !ext || ext.empty? }
|
||||||
.map { |ext| ".#{ext}" }
|
.map { |ext| ".#{ext}" }
|
||||||
.freeze
|
.freeze
|
||||||
|
@ -42,24 +42,24 @@ module Bootsnap
|
||||||
@realpath_cache = RealpathCache.new
|
@realpath_cache = RealpathCache.new
|
||||||
|
|
||||||
@load_path_cache = Cache.new(store, $LOAD_PATH, development_mode: development_mode)
|
@load_path_cache = Cache.new(store, $LOAD_PATH, development_mode: development_mode)
|
||||||
require_relative('load_path_cache/core_ext/kernel_require')
|
require_relative("load_path_cache/core_ext/kernel_require")
|
||||||
require_relative('load_path_cache/core_ext/loaded_features')
|
require_relative("load_path_cache/core_ext/loaded_features")
|
||||||
end
|
end
|
||||||
|
|
||||||
def supported?
|
def supported?
|
||||||
RUBY_ENGINE == 'ruby' &&
|
RUBY_ENGINE == "ruby" &&
|
||||||
RUBY_PLATFORM =~ /darwin|linux|bsd|mswin|mingw|cygwin/
|
RUBY_PLATFORM =~ /darwin|linux|bsd|mswin|mingw|cygwin/
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
if Bootsnap::LoadPathCache.supported?
|
if Bootsnap::LoadPathCache.supported?
|
||||||
require_relative('load_path_cache/path_scanner')
|
require_relative("load_path_cache/path_scanner")
|
||||||
require_relative('load_path_cache/path')
|
require_relative("load_path_cache/path")
|
||||||
require_relative('load_path_cache/cache')
|
require_relative("load_path_cache/cache")
|
||||||
require_relative('load_path_cache/store')
|
require_relative("load_path_cache/store")
|
||||||
require_relative('load_path_cache/change_observer')
|
require_relative("load_path_cache/change_observer")
|
||||||
require_relative('load_path_cache/loaded_features_index')
|
require_relative("load_path_cache/loaded_features_index")
|
||||||
require_relative('load_path_cache/realpath_cache')
|
require_relative("load_path_cache/realpath_cache")
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
require_relative('../explicit_require')
|
require_relative("../explicit_require")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
|
@ -28,15 +28,16 @@ module Bootsnap
|
||||||
BUILTIN_FEATURES = $LOADED_FEATURES.each_with_object({}) do |feat, features|
|
BUILTIN_FEATURES = $LOADED_FEATURES.each_with_object({}) do |feat, features|
|
||||||
# Builtin features are of the form 'enumerator.so'.
|
# Builtin features are of the form 'enumerator.so'.
|
||||||
# All others include paths.
|
# All others include paths.
|
||||||
next unless feat.size < 20 && !feat.include?('/')
|
next unless feat.size < 20 && !feat.include?("/")
|
||||||
|
|
||||||
base = File.basename(feat, '.*') # enumerator.so -> enumerator
|
base = File.basename(feat, ".*") # enumerator.so -> enumerator
|
||||||
ext = File.extname(feat) # .so
|
ext = File.extname(feat) # .so
|
||||||
|
|
||||||
features[feat] = nil # enumerator.so
|
features[feat] = nil # enumerator.so
|
||||||
features[base] = nil # enumerator
|
features[base] = nil # enumerator
|
||||||
|
|
||||||
next unless [DOT_SO, *DL_EXTENSIONS].include?(ext)
|
next unless [DOT_SO, *DL_EXTENSIONS].include?(ext)
|
||||||
|
|
||||||
DL_EXTENSIONS.each do |dl_ext|
|
DL_EXTENSIONS.each do |dl_ext|
|
||||||
features["#{base}#{dl_ext}"] = nil # enumerator.bundle
|
features["#{base}#{dl_ext}"] = nil # enumerator.bundle
|
||||||
end
|
end
|
||||||
|
@ -50,7 +51,7 @@ module Bootsnap
|
||||||
|
|
||||||
return feature if Bootsnap.absolute_path?(feature)
|
return feature if Bootsnap.absolute_path?(feature)
|
||||||
|
|
||||||
if feature.start_with?('./', '../')
|
if feature.start_with?("./", "../")
|
||||||
return try_extensions ? expand_path(feature) : File.expand_path(feature).freeze
|
return try_extensions ? expand_path(feature) : File.expand_path(feature).freeze
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -64,7 +65,7 @@ module Bootsnap
|
||||||
# returns false as if it were already loaded; however, there is no
|
# returns false as if it were already loaded; however, there is no
|
||||||
# file to find on disk. We've pre-built a list of these, and we
|
# file to find on disk. We've pre-built a list of these, and we
|
||||||
# return false if any of them is loaded.
|
# return false if any of them is loaded.
|
||||||
raise(LoadPathCache::ReturnFalse, '', []) if BUILTIN_FEATURES.key?(feature)
|
raise(LoadPathCache::ReturnFalse, "", []) if BUILTIN_FEATURES.key?(feature)
|
||||||
|
|
||||||
# The feature wasn't found on our preliminary search through the index.
|
# The feature wasn't found on our preliminary search through the index.
|
||||||
# We resolve this differently depending on what the extension was.
|
# We resolve this differently depending on what the extension was.
|
||||||
|
@ -73,13 +74,14 @@ module Bootsnap
|
||||||
# native dynamic extension, e.g. .bundle or .so), we know it was a
|
# native dynamic extension, e.g. .bundle or .so), we know it was a
|
||||||
# failure and there's nothing more we can do to find the file.
|
# failure and there's nothing more we can do to find the file.
|
||||||
# no extension, .rb, (.bundle or .so)
|
# no extension, .rb, (.bundle or .so)
|
||||||
when '', *CACHED_EXTENSIONS
|
when "", *CACHED_EXTENSIONS
|
||||||
nil
|
nil
|
||||||
# Ruby allows specifying native extensions as '.so' even when DLEXT
|
# Ruby allows specifying native extensions as '.so' even when DLEXT
|
||||||
# is '.bundle'. This is where we handle that case.
|
# is '.bundle'. This is where we handle that case.
|
||||||
when DOT_SO
|
when DOT_SO
|
||||||
x = search_index(feature[0..-4] + DLEXT)
|
x = search_index(feature[0..-4] + DLEXT)
|
||||||
return x if x
|
return x if x
|
||||||
|
|
||||||
if DLEXT2
|
if DLEXT2
|
||||||
x = search_index(feature[0..-4] + DLEXT2)
|
x = search_index(feature[0..-4] + DLEXT2)
|
||||||
return x if x
|
return x if x
|
||||||
|
@ -87,7 +89,7 @@ module Bootsnap
|
||||||
else
|
else
|
||||||
# other, unknown extension. For example, `.rake`. Since we haven't
|
# other, unknown extension. For example, `.rake`. Since we haven't
|
||||||
# cached these, we legitimately need to run the load path search.
|
# cached these, we legitimately need to run the load path search.
|
||||||
raise(LoadPathCache::FallbackScan, '', [])
|
raise(LoadPathCache::FallbackScan, "", [])
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -95,16 +97,18 @@ module Bootsnap
|
||||||
# cases where the file doesn't appear to be on the load path. We should
|
# cases where the file doesn't appear to be on the load path. We should
|
||||||
# be able to detect newly-created files without rebooting the
|
# be able to detect newly-created files without rebooting the
|
||||||
# application.
|
# application.
|
||||||
raise(LoadPathCache::FallbackScan, '', []) if @development_mode
|
raise(LoadPathCache::FallbackScan, "", []) if @development_mode
|
||||||
end
|
end
|
||||||
|
|
||||||
def unshift_paths(sender, *paths)
|
def unshift_paths(sender, *paths)
|
||||||
return unless sender == @path_obj
|
return unless sender == @path_obj
|
||||||
|
|
||||||
@mutex.synchronize { unshift_paths_locked(*paths) }
|
@mutex.synchronize { unshift_paths_locked(*paths) }
|
||||||
end
|
end
|
||||||
|
|
||||||
def push_paths(sender, *paths)
|
def push_paths(sender, *paths)
|
||||||
return unless sender == @path_obj
|
return unless sender == @path_obj
|
||||||
|
|
||||||
@mutex.synchronize { push_paths_locked(*paths) }
|
@mutex.synchronize { push_paths_locked(*paths) }
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -137,6 +141,7 @@ module Bootsnap
|
||||||
p = Path.new(path)
|
p = Path.new(path)
|
||||||
@has_relative_paths = true if p.relative?
|
@has_relative_paths = true if p.relative?
|
||||||
next if p.non_directory?
|
next if p.non_directory?
|
||||||
|
|
||||||
expanded_path = p.expanded_path
|
expanded_path = p.expanded_path
|
||||||
entries, dirs = p.entries_and_dirs(@store)
|
entries, dirs = p.entries_and_dirs(@store)
|
||||||
# push -> low precedence -> set only if unset
|
# push -> low precedence -> set only if unset
|
||||||
|
@ -151,6 +156,7 @@ module Bootsnap
|
||||||
paths.map(&:to_s).reverse_each do |path|
|
paths.map(&:to_s).reverse_each do |path|
|
||||||
p = Path.new(path)
|
p = Path.new(path)
|
||||||
next if p.non_directory?
|
next if p.non_directory?
|
||||||
|
|
||||||
expanded_path = p.expanded_path
|
expanded_path = p.expanded_path
|
||||||
entries, dirs = p.entries_and_dirs(@store)
|
entries, dirs = p.entries_and_dirs(@store)
|
||||||
# unshift -> high precedence -> unconditional set
|
# unshift -> high precedence -> unconditional set
|
||||||
|
@ -173,56 +179,62 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
if DLEXT2
|
if DLEXT2
|
||||||
def search_index(f, try_extensions: true)
|
def search_index(feature, try_extensions: true)
|
||||||
if try_extensions
|
if try_extensions
|
||||||
try_index(f + DOT_RB) || try_index(f + DLEXT) || try_index(f + DLEXT2) || try_index(f)
|
try_index(feature + DOT_RB) ||
|
||||||
|
try_index(feature + DLEXT) ||
|
||||||
|
try_index(feature + DLEXT2) ||
|
||||||
|
try_index(feature)
|
||||||
else
|
else
|
||||||
try_index(f)
|
try_index(feature)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def maybe_append_extension(f)
|
def maybe_append_extension(feature)
|
||||||
try_ext(f + DOT_RB) || try_ext(f + DLEXT) || try_ext(f + DLEXT2) || f
|
try_ext(feature + DOT_RB) ||
|
||||||
|
try_ext(feature + DLEXT) ||
|
||||||
|
try_ext(feature + DLEXT2) ||
|
||||||
|
feature
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
def search_index(f, try_extensions: true)
|
def search_index(feature, try_extensions: true)
|
||||||
if try_extensions
|
if try_extensions
|
||||||
try_index(f + DOT_RB) || try_index(f + DLEXT) || try_index(f)
|
try_index(feature + DOT_RB) || try_index(feature + DLEXT) || try_index(feature)
|
||||||
else
|
else
|
||||||
try_index(f)
|
try_index(feature)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def maybe_append_extension(f)
|
def maybe_append_extension(feature)
|
||||||
try_ext(f + DOT_RB) || try_ext(f + DLEXT) || f
|
try_ext(feature + DOT_RB) || try_ext(feature + DLEXT) || feature
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
s = rand.to_s.force_encoding(Encoding::US_ASCII).freeze
|
s = rand.to_s.force_encoding(Encoding::US_ASCII).freeze
|
||||||
if s.respond_to?(:-@)
|
if s.respond_to?(:-@)
|
||||||
if (-s).equal?(s) && (-s.dup).equal?(s) || RUBY_VERSION >= '2.7'
|
if (-s).equal?(s) && (-s.dup).equal?(s) || RUBY_VERSION >= "2.7"
|
||||||
def try_index(f)
|
def try_index(feature)
|
||||||
if (p = @index[f])
|
if (path = @index[feature])
|
||||||
-(File.join(p, f).freeze)
|
-File.join(path, feature).freeze
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
def try_index(f)
|
def try_index(feature)
|
||||||
if (p = @index[f])
|
if (path = @index[feature])
|
||||||
-File.join(p, f).untaint
|
-File.join(path, feature).untaint
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
def try_index(f)
|
def try_index(feature)
|
||||||
if (p = @index[f])
|
if (path = @index[feature])
|
||||||
File.join(p, f)
|
File.join(path, feature)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def try_ext(f)
|
def try_ext(feature)
|
||||||
f if File.exist?(f)
|
feature if File.exist?(feature)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
module ChangeObserver
|
module ChangeObserver
|
||||||
|
@ -57,6 +58,7 @@ module Bootsnap
|
||||||
|
|
||||||
def self.register(observer, arr)
|
def self.register(observer, arr)
|
||||||
return if arr.frozen? # can't register observer, but no need to.
|
return if arr.frozen? # can't register observer, but no need to.
|
||||||
|
|
||||||
arr.instance_variable_set(:@lpc_observer, observer)
|
arr.instance_variable_set(:@lpc_observer, observer)
|
||||||
arr.extend(ArrayMixin)
|
arr.extend(ArrayMixin)
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
module CoreExt
|
module CoreExt
|
||||||
|
@ -13,7 +14,7 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
module Kernel
|
module Kernel
|
||||||
module_function # rubocop:disable Style/ModuleFunction
|
module_function
|
||||||
|
|
||||||
alias_method(:require_without_bootsnap, :require)
|
alias_method(:require_without_bootsnap, :require)
|
||||||
|
|
||||||
|
@ -32,9 +33,9 @@ module Kernel
|
||||||
end
|
end
|
||||||
|
|
||||||
raise(Bootsnap::LoadPathCache::CoreExt.make_load_error(path))
|
raise(Bootsnap::LoadPathCache::CoreExt.make_load_error(path))
|
||||||
rescue LoadError => e
|
rescue LoadError => error
|
||||||
e.instance_variable_set(Bootsnap::LoadPathCache::ERROR_TAG_IVAR, true)
|
error.instance_variable_set(Bootsnap::LoadPathCache::ERROR_TAG_IVAR, true)
|
||||||
raise(e)
|
raise(error)
|
||||||
rescue Bootsnap::LoadPathCache::ReturnFalse
|
rescue Bootsnap::LoadPathCache::ReturnFalse
|
||||||
false
|
false
|
||||||
rescue Bootsnap::LoadPathCache::FallbackScan
|
rescue Bootsnap::LoadPathCache::FallbackScan
|
||||||
|
@ -75,9 +76,9 @@ class Module
|
||||||
# added to $LOADED_FEATURES and won't be able to hook that modification
|
# added to $LOADED_FEATURES and won't be able to hook that modification
|
||||||
# since it's done in C-land.
|
# since it's done in C-land.
|
||||||
autoload_without_bootsnap(const, Bootsnap::LoadPathCache.load_path_cache.find(path) || path)
|
autoload_without_bootsnap(const, Bootsnap::LoadPathCache.load_path_cache.find(path) || path)
|
||||||
rescue LoadError => e
|
rescue LoadError => error
|
||||||
e.instance_variable_set(Bootsnap::LoadPathCache::ERROR_TAG_IVAR, true)
|
error.instance_variable_set(Bootsnap::LoadPathCache::ERROR_TAG_IVAR, true)
|
||||||
raise(e)
|
raise(error)
|
||||||
rescue Bootsnap::LoadPathCache::ReturnFalse
|
rescue Bootsnap::LoadPathCache::ReturnFalse
|
||||||
false
|
false
|
||||||
rescue Bootsnap::LoadPathCache::FallbackScan
|
rescue Bootsnap::LoadPathCache::FallbackScan
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
class << $LOADED_FEATURES
|
class << $LOADED_FEATURES
|
||||||
alias_method(:delete_without_bootsnap, :delete)
|
alias_method(:delete_without_bootsnap, :delete)
|
||||||
def delete(key)
|
def delete(key)
|
||||||
|
|
|
@ -29,14 +29,15 @@ module Bootsnap
|
||||||
@mutex = Mutex.new
|
@mutex = Mutex.new
|
||||||
|
|
||||||
# In theory the user could mutate $LOADED_FEATURES and invalidate our
|
# In theory the user could mutate $LOADED_FEATURES and invalidate our
|
||||||
# cache. If this ever comes up in practice — or if you, the
|
# cache. If this ever comes up in practice - or if you, the
|
||||||
# enterprising reader, feels inclined to solve this problem — we could
|
# enterprising reader, feels inclined to solve this problem - we could
|
||||||
# parallel the work done with ChangeObserver on $LOAD_PATH to mirror
|
# parallel the work done with ChangeObserver on $LOAD_PATH to mirror
|
||||||
# updates to our @lfi.
|
# updates to our @lfi.
|
||||||
$LOADED_FEATURES.each do |feat|
|
$LOADED_FEATURES.each do |feat|
|
||||||
hash = feat.hash
|
hash = feat.hash
|
||||||
$LOAD_PATH.each do |lpe|
|
$LOAD_PATH.each do |lpe|
|
||||||
next unless feat.start_with?(lpe)
|
next unless feat.start_with?(lpe)
|
||||||
|
|
||||||
# /a/b/lib/my/foo.rb
|
# /a/b/lib/my/foo.rb
|
||||||
# ^^^^^^^^^
|
# ^^^^^^^^^
|
||||||
short = feat[(lpe.length + 1)..-1]
|
short = feat[(lpe.length + 1)..-1]
|
||||||
|
@ -93,7 +94,7 @@ module Bootsnap
|
||||||
ret = yield
|
ret = yield
|
||||||
long = $LOADED_FEATURES[len..-1].detect do |feat|
|
long = $LOADED_FEATURES[len..-1].detect do |feat|
|
||||||
offset = 0
|
offset = 0
|
||||||
while offset = feat.index(short, offset)
|
while (offset = feat.index(short, offset))
|
||||||
if feat.index(".", offset + 1) && !feat.index("/", offset + 2)
|
if feat.index(".", offset + 1) && !feat.index("/", offset + 2)
|
||||||
break true
|
break true
|
||||||
else
|
else
|
||||||
|
@ -128,7 +129,7 @@ module Bootsnap
|
||||||
|
|
||||||
private
|
private
|
||||||
|
|
||||||
STRIP_EXTENSION = /\.[^.]*?$/
|
STRIP_EXTENSION = /\.[^.]*?$/.freeze
|
||||||
private_constant(:STRIP_EXTENSION)
|
private_constant(:STRIP_EXTENSION)
|
||||||
|
|
||||||
# Might Ruby automatically search for this extension if
|
# Might Ruby automatically search for this extension if
|
||||||
|
@ -145,15 +146,15 @@ module Bootsnap
|
||||||
# with calling a Ruby file 'x.dylib.rb' and then requiring it as 'x.dylib'.)
|
# with calling a Ruby file 'x.dylib.rb' and then requiring it as 'x.dylib'.)
|
||||||
#
|
#
|
||||||
# See <https://ruby-doc.org/core-2.6.4/Kernel.html#method-i-require>.
|
# See <https://ruby-doc.org/core-2.6.4/Kernel.html#method-i-require>.
|
||||||
def extension_elidable?(f)
|
def extension_elidable?(feature)
|
||||||
f.to_s.end_with?('.rb', '.so', '.o', '.dll', '.dylib')
|
feature.to_s.end_with?(".rb", ".so", ".o", ".dll", ".dylib")
|
||||||
end
|
end
|
||||||
|
|
||||||
def strip_extension_if_elidable(f)
|
def strip_extension_if_elidable(feature)
|
||||||
if extension_elidable?(f)
|
if extension_elidable?(feature)
|
||||||
f.sub(STRIP_EXTENSION, '')
|
feature.sub(STRIP_EXTENSION, "")
|
||||||
else
|
else
|
||||||
f
|
feature
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require_relative('path_scanner')
|
|
||||||
|
require_relative("path_scanner")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
|
@ -43,6 +44,7 @@ module Bootsnap
|
||||||
# set to zero anyway, just in case we change the stability heuristics.
|
# set to zero anyway, just in case we change the stability heuristics.
|
||||||
_, entries, dirs = store.get(expanded_path)
|
_, entries, dirs = store.get(expanded_path)
|
||||||
return [entries, dirs] if entries # cache hit
|
return [entries, dirs] if entries # cache hit
|
||||||
|
|
||||||
entries, dirs = scan!
|
entries, dirs = scan!
|
||||||
store.set(expanded_path, [0, entries, dirs])
|
store.set(expanded_path, [0, entries, dirs])
|
||||||
return [entries, dirs]
|
return [entries, dirs]
|
||||||
|
@ -93,8 +95,8 @@ module Bootsnap
|
||||||
|
|
||||||
# Built-in ruby lib stuff doesn't change, but things can occasionally be
|
# Built-in ruby lib stuff doesn't change, but things can occasionally be
|
||||||
# installed into sitedir, which generally lives under libdir.
|
# installed into sitedir, which generally lives under libdir.
|
||||||
RUBY_LIBDIR = RbConfig::CONFIG['libdir']
|
RUBY_LIBDIR = RbConfig::CONFIG["libdir"]
|
||||||
RUBY_SITEDIR = RbConfig::CONFIG['sitedir']
|
RUBY_SITEDIR = RbConfig::CONFIG["sitedir"]
|
||||||
|
|
||||||
def stability
|
def stability
|
||||||
@stability ||= begin
|
@stability ||= begin
|
||||||
|
|
|
@ -1,18 +1,18 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
require_relative('../explicit_require')
|
require_relative("../explicit_require")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
module PathScanner
|
module PathScanner
|
||||||
REQUIRABLE_EXTENSIONS = [DOT_RB] + DL_EXTENSIONS
|
REQUIRABLE_EXTENSIONS = [DOT_RB] + DL_EXTENSIONS
|
||||||
NORMALIZE_NATIVE_EXTENSIONS = !DL_EXTENSIONS.include?(LoadPathCache::DOT_SO)
|
NORMALIZE_NATIVE_EXTENSIONS = !DL_EXTENSIONS.include?(LoadPathCache::DOT_SO)
|
||||||
ALTERNATIVE_NATIVE_EXTENSIONS_PATTERN = /\.(o|bundle|dylib)\z/
|
ALTERNATIVE_NATIVE_EXTENSIONS_PATTERN = /\.(o|bundle|dylib)\z/.freeze
|
||||||
|
|
||||||
BUNDLE_PATH = if Bootsnap.bundler?
|
BUNDLE_PATH = if Bootsnap.bundler?
|
||||||
(Bundler.bundle_path.cleanpath.to_s << LoadPathCache::SLASH).freeze
|
(Bundler.bundle_path.cleanpath.to_s << LoadPathCache::SLASH).freeze
|
||||||
else
|
else
|
||||||
''
|
""
|
||||||
end
|
end
|
||||||
|
|
||||||
class << self
|
class << self
|
||||||
|
@ -44,7 +44,8 @@ module Bootsnap
|
||||||
|
|
||||||
def walk(absolute_dir_path, relative_dir_path, &block)
|
def walk(absolute_dir_path, relative_dir_path, &block)
|
||||||
Dir.foreach(absolute_dir_path) do |name|
|
Dir.foreach(absolute_dir_path) do |name|
|
||||||
next if name.start_with?('.')
|
next if name.start_with?(".")
|
||||||
|
|
||||||
relative_path = relative_dir_path ? File.join(relative_dir_path, name) : name
|
relative_path = relative_dir_path ? File.join(relative_dir_path, name) : name
|
||||||
|
|
||||||
absolute_path = "#{absolute_dir_path}/#{name}"
|
absolute_path = "#{absolute_dir_path}/#{name}"
|
||||||
|
@ -58,7 +59,7 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
if RUBY_VERSION >= '3.1'
|
if RUBY_VERSION >= "3.1"
|
||||||
def os_path(path)
|
def os_path(path)
|
||||||
path.freeze
|
path.freeze
|
||||||
end
|
end
|
||||||
|
|
|
@ -21,6 +21,7 @@ module Bootsnap
|
||||||
|
|
||||||
def find_file(name)
|
def find_file(name)
|
||||||
return File.realpath(name).freeze if File.exist?(name)
|
return File.realpath(name).freeze if File.exist?(name)
|
||||||
|
|
||||||
CACHED_EXTENSIONS.each do |ext|
|
CACHED_EXTENSIONS.each do |ext|
|
||||||
filename = "#{name}#{ext}"
|
filename = "#{name}#{ext}"
|
||||||
return File.realpath(filename).freeze if File.exist?(filename)
|
return File.realpath(filename).freeze if File.exist?(filename)
|
||||||
|
|
|
@ -1,14 +1,15 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require_relative('../explicit_require')
|
|
||||||
|
|
||||||
Bootsnap::ExplicitRequire.with_gems('msgpack') { require('msgpack') }
|
require_relative("../explicit_require")
|
||||||
Bootsnap::ExplicitRequire.from_rubylibdir('fileutils')
|
|
||||||
|
Bootsnap::ExplicitRequire.with_gems("msgpack") { require("msgpack") }
|
||||||
|
Bootsnap::ExplicitRequire.from_rubylibdir("fileutils")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
class Store
|
class Store
|
||||||
VERSION_KEY = '__bootsnap_ruby_version__'
|
VERSION_KEY = "__bootsnap_ruby_version__"
|
||||||
CURRENT_VERSION = "#{RUBY_REVISION}-#{RUBY_PLATFORM}".freeze
|
CURRENT_VERSION = "#{RUBY_REVISION}-#{RUBY_PLATFORM}".freeze # rubocop:disable Style/RedundantFreeze
|
||||||
|
|
||||||
NestedTransactionError = Class.new(StandardError)
|
NestedTransactionError = Class.new(StandardError)
|
||||||
SetOutsideTransactionNotAllowed = Class.new(StandardError)
|
SetOutsideTransactionNotAllowed = Class.new(StandardError)
|
||||||
|
@ -26,6 +27,7 @@ module Bootsnap
|
||||||
|
|
||||||
def fetch(key)
|
def fetch(key)
|
||||||
raise(SetOutsideTransactionNotAllowed) unless @txn_mutex.owned?
|
raise(SetOutsideTransactionNotAllowed) unless @txn_mutex.owned?
|
||||||
|
|
||||||
v = get(key)
|
v = get(key)
|
||||||
unless v
|
unless v
|
||||||
@dirty = true
|
@dirty = true
|
||||||
|
@ -37,6 +39,7 @@ module Bootsnap
|
||||||
|
|
||||||
def set(key, value)
|
def set(key, value)
|
||||||
raise(SetOutsideTransactionNotAllowed) unless @txn_mutex.owned?
|
raise(SetOutsideTransactionNotAllowed) unless @txn_mutex.owned?
|
||||||
|
|
||||||
if value != @data[key]
|
if value != @data[key]
|
||||||
@dirty = true
|
@dirty = true
|
||||||
@data[key] = value
|
@data[key] = value
|
||||||
|
@ -45,6 +48,7 @@ module Bootsnap
|
||||||
|
|
||||||
def transaction
|
def transaction
|
||||||
raise(NestedTransactionError) if @txn_mutex.owned?
|
raise(NestedTransactionError) if @txn_mutex.owned?
|
||||||
|
|
||||||
@txn_mutex.synchronize do
|
@txn_mutex.synchronize do
|
||||||
begin
|
begin
|
||||||
yield
|
yield
|
||||||
|
@ -88,7 +92,7 @@ module Bootsnap
|
||||||
def dump_data
|
def dump_data
|
||||||
# Change contents atomically so other processes can't get invalid
|
# Change contents atomically so other processes can't get invalid
|
||||||
# caches if they read at an inopportune time.
|
# caches if they read at an inopportune time.
|
||||||
tmp = "#{@store_path}.#{Process.pid}.#{(rand * 100000).to_i}.tmp"
|
tmp = "#{@store_path}.#{Process.pid}.#{(rand * 100_000).to_i}.tmp"
|
||||||
FileUtils.mkpath(File.dirname(tmp))
|
FileUtils.mkpath(File.dirname(tmp))
|
||||||
exclusive_write = File::Constants::CREAT | File::Constants::EXCL | File::Constants::WRONLY
|
exclusive_write = File::Constants::CREAT | File::Constants::EXCL | File::Constants::WRONLY
|
||||||
# `encoding:` looks redundant wrt `binwrite`, but necessary on windows
|
# `encoding:` looks redundant wrt `binwrite`, but necessary on windows
|
||||||
|
@ -103,7 +107,7 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def default_data
|
def default_data
|
||||||
{ VERSION_KEY => CURRENT_VERSION }
|
{VERSION_KEY => CURRENT_VERSION}
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require_relative('../bootsnap')
|
|
||||||
|
require_relative("../bootsnap")
|
||||||
|
|
||||||
Bootsnap.default_setup
|
Bootsnap.default_setup
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
VERSION = "1.9.4"
|
VERSION = "1.9.4"
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,17 +1,18 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
class BundlerTest < Minitest::Test
|
class BundlerTest < Minitest::Test
|
||||||
def test_bundler_with_bundle_bin_path_env
|
def test_bundler_with_bundle_bin_path_env
|
||||||
without_required_env_keys do
|
without_required_env_keys do
|
||||||
ENV['BUNDLE_BIN_PATH'] = 'foo'
|
ENV["BUNDLE_BIN_PATH"] = "foo"
|
||||||
assert_predicate(Bootsnap, :bundler?)
|
assert_predicate(Bootsnap, :bundler?)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_bundler_with_bundle_gemfile_env
|
def test_bundler_with_bundle_gemfile_env
|
||||||
without_required_env_keys do
|
without_required_env_keys do
|
||||||
ENV['BUNDLE_GEMFILE'] = 'foo'
|
ENV["BUNDLE_GEMFILE"] = "foo"
|
||||||
assert_predicate(Bootsnap, :bundler?)
|
assert_predicate(Bootsnap, :bundler?)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
require('bootsnap/cli')
|
require("test_helper")
|
||||||
|
require("bootsnap/cli")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
class CLITest < Minitest::Test
|
class CLITest < Minitest::Test
|
||||||
|
@ -8,52 +9,52 @@ module Bootsnap
|
||||||
|
|
||||||
def setup
|
def setup
|
||||||
super
|
super
|
||||||
@cache_dir = File.expand_path('tmp/cache/bootsnap/compile-cache')
|
@cache_dir = File.expand_path("tmp/cache/bootsnap/compile-cache")
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_precompile_single_file
|
def test_precompile_single_file
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
CompileCache::ISeq.expects(:precompile).with(File.expand_path(path), cache_dir: @cache_dir)
|
CompileCache::ISeq.expects(:precompile).with(File.expand_path(path), cache_dir: @cache_dir)
|
||||||
assert_equal 0, CLI.new(['precompile', '-j', '0', path]).run
|
assert_equal 0, CLI.new(["precompile", "-j", "0", path]).run
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_no_iseq
|
def test_no_iseq
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
CompileCache::ISeq.expects(:precompile).never
|
CompileCache::ISeq.expects(:precompile).never
|
||||||
assert_equal 0, CLI.new(['precompile', '-j', '0', '--no-iseq', path]).run
|
assert_equal 0, CLI.new(["precompile", "-j", "0", "--no-iseq", path]).run
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_precompile_directory
|
def test_precompile_directory
|
||||||
path_a = Help.set_file('foo/a.rb', 'a = a = 3', 100)
|
path_a = Help.set_file("foo/a.rb", "a = a = 3", 100)
|
||||||
path_b = Help.set_file('foo/b.rb', 'b = b = 3', 100)
|
path_b = Help.set_file("foo/b.rb", "b = b = 3", 100)
|
||||||
|
|
||||||
CompileCache::ISeq.expects(:precompile).with(File.expand_path(path_a), cache_dir: @cache_dir)
|
CompileCache::ISeq.expects(:precompile).with(File.expand_path(path_a), cache_dir: @cache_dir)
|
||||||
CompileCache::ISeq.expects(:precompile).with(File.expand_path(path_b), cache_dir: @cache_dir)
|
CompileCache::ISeq.expects(:precompile).with(File.expand_path(path_b), cache_dir: @cache_dir)
|
||||||
assert_equal 0, CLI.new(['precompile', '-j', '0', 'foo']).run
|
assert_equal 0, CLI.new(["precompile", "-j", "0", "foo"]).run
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_precompile_exclude
|
def test_precompile_exclude
|
||||||
path_a = Help.set_file('foo/a.rb', 'a = a = 3', 100)
|
path_a = Help.set_file("foo/a.rb", "a = a = 3", 100)
|
||||||
Help.set_file('foo/b.rb', 'b = b = 3', 100)
|
Help.set_file("foo/b.rb", "b = b = 3", 100)
|
||||||
|
|
||||||
CompileCache::ISeq.expects(:precompile).with(File.expand_path(path_a), cache_dir: @cache_dir)
|
CompileCache::ISeq.expects(:precompile).with(File.expand_path(path_a), cache_dir: @cache_dir)
|
||||||
assert_equal 0, CLI.new(['precompile', '-j', '0', '--exclude', 'b.rb', 'foo']).run
|
assert_equal 0, CLI.new(["precompile", "-j", "0", "--exclude", "b.rb", "foo"]).run
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_precompile_gemfile
|
def test_precompile_gemfile
|
||||||
assert_equal 0, CLI.new(['precompile', '--gemfile']).run
|
assert_equal 0, CLI.new(["precompile", "--gemfile"]).run
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_precompile_yaml
|
def test_precompile_yaml
|
||||||
path = Help.set_file('a.yaml', 'foo: bar', 100)
|
path = Help.set_file("a.yaml", "foo: bar", 100)
|
||||||
CompileCache::YAML.expects(:precompile).with(File.expand_path(path), cache_dir: @cache_dir)
|
CompileCache::YAML.expects(:precompile).with(File.expand_path(path), cache_dir: @cache_dir)
|
||||||
assert_equal 0, CLI.new(['precompile', '-j', '0', path]).run
|
assert_equal 0, CLI.new(["precompile", "-j", "0", path]).run
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_no_yaml
|
def test_no_yaml
|
||||||
path = Help.set_file('a.yaml', 'foo: bar', 100)
|
path = Help.set_file("a.yaml", "foo: bar", 100)
|
||||||
CompileCache::YAML.expects(:precompile).never
|
CompileCache::YAML.expects(:precompile).never
|
||||||
assert_equal 0, CLI.new(['precompile', '-j', '0', '--no-yaml', path]).run
|
assert_equal 0, CLI.new(["precompile", "-j", "0", "--no-yaml", path]).run
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,11 +1,12 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
class CompileCacheISeqTest < Minitest::Test
|
class CompileCacheISeqTest < Minitest::Test
|
||||||
include(TmpdirHelper)
|
include(TmpdirHelper)
|
||||||
|
|
||||||
def test_ruby_bug_18250
|
def test_ruby_bug_18250
|
||||||
Help.set_file('a.rb', 'def foo(*); ->{ super }; end; def foo(**); ->{ super }; end', 100)
|
Help.set_file("a.rb", "def foo(*); ->{ super }; end; def foo(**); ->{ super }; end", 100)
|
||||||
Bootsnap::CompileCache::ISeq.fetch('a.rb')
|
Bootsnap::CompileCache::ISeq.fetch("a.rb")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
class CompileCacheJSONTest < Minitest::Test
|
class CompileCacheJSONTest < Minitest::Test
|
||||||
include(TmpdirHelper)
|
include(TmpdirHelper)
|
||||||
|
@ -7,7 +8,7 @@ class CompileCacheJSONTest < Minitest::Test
|
||||||
module FakeJson
|
module FakeJson
|
||||||
Fallback = Class.new(StandardError)
|
Fallback = Class.new(StandardError)
|
||||||
class << self
|
class << self
|
||||||
def load_file(path, symbolize_names: false, freeze: false, fallback: nil)
|
def load_file(_path, symbolize_names: false, freeze: false, fallback: nil)
|
||||||
raise Fallback
|
raise Fallback
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -27,55 +28,55 @@ class CompileCacheJSONTest < Minitest::Test
|
||||||
}
|
}
|
||||||
JSON
|
JSON
|
||||||
expected = {
|
expected = {
|
||||||
'foo' => 42,
|
"foo" => 42,
|
||||||
'bar' => [1],
|
"bar" => [1],
|
||||||
}
|
}
|
||||||
assert_equal expected, document
|
assert_equal expected, document
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_load_file
|
def test_load_file
|
||||||
Help.set_file('a.json', '{"foo": "bar"}', 100)
|
Help.set_file("a.json", '{"foo": "bar"}', 100)
|
||||||
assert_equal({'foo' => 'bar'}, FakeJson.load_file('a.json'))
|
assert_equal({"foo" => "bar"}, FakeJson.load_file("a.json"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_load_file_symbolize_names
|
def test_load_file_symbolize_names
|
||||||
Help.set_file('a.json', '{"foo": "bar"}', 100)
|
Help.set_file("a.json", '{"foo": "bar"}', 100)
|
||||||
FakeJson.load_file('a.json')
|
FakeJson.load_file("a.json")
|
||||||
|
|
||||||
if ::Bootsnap::CompileCache::JSON.supported_options.include?(:symbolize_names)
|
if ::Bootsnap::CompileCache::JSON.supported_options.include?(:symbolize_names)
|
||||||
2.times do
|
2.times do
|
||||||
assert_equal({foo: 'bar'}, FakeJson.load_file('a.json', symbolize_names: true))
|
assert_equal({foo: "bar"}, FakeJson.load_file("a.json", symbolize_names: true))
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
assert_raises(FakeJson::Fallback) do # would call super
|
assert_raises(FakeJson::Fallback) do # would call super
|
||||||
FakeJson.load_file('a.json', symbolize_names: true)
|
FakeJson.load_file("a.json", symbolize_names: true)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_load_file_freeze
|
def test_load_file_freeze
|
||||||
Help.set_file('a.json', '["foo"]', 100)
|
Help.set_file("a.json", '["foo"]', 100)
|
||||||
FakeJson.load_file('a.json')
|
FakeJson.load_file("a.json")
|
||||||
|
|
||||||
if ::Bootsnap::CompileCache::JSON.supported_options.include?(:freeze)
|
if ::Bootsnap::CompileCache::JSON.supported_options.include?(:freeze)
|
||||||
2.times do
|
2.times do
|
||||||
string = FakeJson.load_file('a.json', freeze: true).first
|
string = FakeJson.load_file("a.json", freeze: true).first
|
||||||
assert_equal("foo", string)
|
assert_equal("foo", string)
|
||||||
assert_predicate(string, :frozen?)
|
assert_predicate(string, :frozen?)
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
assert_raises(FakeJson::Fallback) do # would call super
|
assert_raises(FakeJson::Fallback) do # would call super
|
||||||
FakeJson.load_file('a.json', freeze: true)
|
FakeJson.load_file("a.json", freeze: true)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_load_file_unknown_option
|
def test_load_file_unknown_option
|
||||||
Help.set_file('a.json', '["foo"]', 100)
|
Help.set_file("a.json", '["foo"]', 100)
|
||||||
FakeJson.load_file('a.json')
|
FakeJson.load_file("a.json")
|
||||||
|
|
||||||
assert_raises(FakeJson::Fallback) do # would call super
|
assert_raises(FakeJson::Fallback) do # would call super
|
||||||
FakeJson.load_file('a.json', fallback: true)
|
FakeJson.load_file("a.json", fallback: true)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
class CompileCacheYAMLTest < Minitest::Test
|
class CompileCacheYAMLTest < Minitest::Test
|
||||||
include(TmpdirHelper)
|
include(TmpdirHelper)
|
||||||
|
@ -7,11 +8,11 @@ class CompileCacheYAMLTest < Minitest::Test
|
||||||
module FakeYaml
|
module FakeYaml
|
||||||
Fallback = Class.new(StandardError)
|
Fallback = Class.new(StandardError)
|
||||||
class << self
|
class << self
|
||||||
def load_file(path, symbolize_names: false, freeze: false, fallback: nil)
|
def load_file(_path, symbolize_names: false, freeze: false, fallback: nil)
|
||||||
raise Fallback
|
raise Fallback
|
||||||
end
|
end
|
||||||
|
|
||||||
def unsafe_load_file(path, symbolize_names: false, freeze: false, fallback: nil)
|
def unsafe_load_file(_path, symbolize_names: false, freeze: false, fallback: nil)
|
||||||
raise Fallback
|
raise Fallback
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -31,7 +32,7 @@ class CompileCacheYAMLTest < Minitest::Test
|
||||||
YAML
|
YAML
|
||||||
expected = {
|
expected = {
|
||||||
foo: 42,
|
foo: 42,
|
||||||
'bar' => [1],
|
"bar" => [1],
|
||||||
}
|
}
|
||||||
assert_equal expected, document
|
assert_equal expected, document
|
||||||
end
|
end
|
||||||
|
@ -44,89 +45,89 @@ class CompileCacheYAMLTest < Minitest::Test
|
||||||
YAML
|
YAML
|
||||||
expected = {
|
expected = {
|
||||||
foo: 42,
|
foo: 42,
|
||||||
'bar' => [1],
|
"bar" => [1],
|
||||||
}
|
}
|
||||||
assert_equal expected, document
|
assert_equal expected, document
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_yaml_tags
|
def test_yaml_tags
|
||||||
error = assert_raises Bootsnap::CompileCache::Uncompilable do
|
error = assert_raises Bootsnap::CompileCache::Uncompilable do
|
||||||
::Bootsnap::CompileCache::YAML.strict_load('!many Boolean')
|
::Bootsnap::CompileCache::YAML.strict_load("!many Boolean")
|
||||||
end
|
end
|
||||||
assert_equal "YAML tags are not supported: !many", error.message
|
assert_equal "YAML tags are not supported: !many", error.message
|
||||||
|
|
||||||
error = assert_raises Bootsnap::CompileCache::Uncompilable do
|
error = assert_raises Bootsnap::CompileCache::Uncompilable do
|
||||||
::Bootsnap::CompileCache::YAML.strict_load('!ruby/object {}')
|
::Bootsnap::CompileCache::YAML.strict_load("!ruby/object {}")
|
||||||
end
|
end
|
||||||
assert_equal "YAML tags are not supported: !ruby/object", error.message
|
assert_equal "YAML tags are not supported: !ruby/object", error.message
|
||||||
end
|
end
|
||||||
|
|
||||||
if YAML::VERSION >= '4'
|
if YAML::VERSION >= "4"
|
||||||
def test_load_psych_4
|
def test_load_psych_4
|
||||||
# Until we figure out a proper strategy, only `YAML.unsafe_load_file`
|
# Until we figure out a proper strategy, only `YAML.unsafe_load_file`
|
||||||
# is cached with Psych >= 4
|
# is cached with Psych >= 4
|
||||||
Help.set_file('a.yml', "foo: &foo\n bar: 42\nplop:\n <<: *foo", 100)
|
Help.set_file("a.yml", "foo: &foo\n bar: 42\nplop:\n <<: *foo", 100)
|
||||||
assert_raises FakeYaml::Fallback do
|
assert_raises FakeYaml::Fallback do
|
||||||
FakeYaml.load_file('a.yml')
|
FakeYaml.load_file("a.yml")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
def test_load_file
|
def test_load_file
|
||||||
Help.set_file('a.yml', "---\nfoo: bar", 100)
|
Help.set_file("a.yml", "---\nfoo: bar", 100)
|
||||||
assert_equal({'foo' => 'bar'}, FakeYaml.load_file('a.yml'))
|
assert_equal({"foo" => "bar"}, FakeYaml.load_file("a.yml"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_load_file_aliases
|
def test_load_file_aliases
|
||||||
Help.set_file('a.yml', "foo: &foo\n bar: 42\nplop:\n <<: *foo", 100)
|
Help.set_file("a.yml", "foo: &foo\n bar: 42\nplop:\n <<: *foo", 100)
|
||||||
assert_equal({"foo" => { "bar" => 42 }, "plop" => { "bar" => 42} }, FakeYaml.load_file('a.yml'))
|
assert_equal({"foo" => {"bar" => 42}, "plop" => {"bar" => 42}}, FakeYaml.load_file("a.yml"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_load_file_symbolize_names
|
def test_load_file_symbolize_names
|
||||||
Help.set_file('a.yml', "---\nfoo: bar", 100)
|
Help.set_file("a.yml", "---\nfoo: bar", 100)
|
||||||
FakeYaml.load_file('a.yml')
|
FakeYaml.load_file("a.yml")
|
||||||
|
|
||||||
if ::Bootsnap::CompileCache::YAML.supported_options.include?(:symbolize_names)
|
if ::Bootsnap::CompileCache::YAML.supported_options.include?(:symbolize_names)
|
||||||
2.times do
|
2.times do
|
||||||
assert_equal({foo: 'bar'}, FakeYaml.load_file('a.yml', symbolize_names: true))
|
assert_equal({foo: "bar"}, FakeYaml.load_file("a.yml", symbolize_names: true))
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
assert_raises(FakeYaml::Fallback) do # would call super
|
assert_raises(FakeYaml::Fallback) do # would call super
|
||||||
FakeYaml.load_file('a.yml', symbolize_names: true)
|
FakeYaml.load_file("a.yml", symbolize_names: true)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_load_file_freeze
|
def test_load_file_freeze
|
||||||
Help.set_file('a.yml', "---\nfoo", 100)
|
Help.set_file("a.yml", "---\nfoo", 100)
|
||||||
FakeYaml.load_file('a.yml')
|
FakeYaml.load_file("a.yml")
|
||||||
|
|
||||||
if ::Bootsnap::CompileCache::YAML.supported_options.include?(:freeze)
|
if ::Bootsnap::CompileCache::YAML.supported_options.include?(:freeze)
|
||||||
2.times do
|
2.times do
|
||||||
string = FakeYaml.load_file('a.yml', freeze: true)
|
string = FakeYaml.load_file("a.yml", freeze: true)
|
||||||
assert_equal("foo", string)
|
assert_equal("foo", string)
|
||||||
assert_predicate(string, :frozen?)
|
assert_predicate(string, :frozen?)
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
assert_raises(FakeYaml::Fallback) do # would call super
|
assert_raises(FakeYaml::Fallback) do # would call super
|
||||||
FakeYaml.load_file('a.yml', freeze: true)
|
FakeYaml.load_file("a.yml", freeze: true)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_load_file_unknown_option
|
def test_load_file_unknown_option
|
||||||
Help.set_file('a.yml', "---\nfoo", 100)
|
Help.set_file("a.yml", "---\nfoo", 100)
|
||||||
FakeYaml.load_file('a.yml')
|
FakeYaml.load_file("a.yml")
|
||||||
|
|
||||||
assert_raises(FakeYaml::Fallback) do # would call super
|
assert_raises(FakeYaml::Fallback) do # would call super
|
||||||
FakeYaml.load_file('a.yml', fallback: true)
|
FakeYaml.load_file("a.yml", fallback: true)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
if YAML.respond_to?(:unsafe_load_file)
|
if YAML.respond_to?(:unsafe_load_file)
|
||||||
def test_unsafe_load_file
|
def test_unsafe_load_file
|
||||||
Help.set_file('a.yml', "foo: &foo\n bar: 42\nplop:\n <<: *foo", 100)
|
Help.set_file("a.yml", "foo: &foo\n bar: 42\nplop:\n <<: *foo", 100)
|
||||||
assert_equal({"foo" => { "bar" => 42 }, "plop" => { "bar" => 42} }, FakeYaml.unsafe_load_file('a.yml'))
|
assert_equal({"foo" => {"bar" => 42}, "plop" => {"bar" => 42}}, FakeYaml.unsafe_load_file("a.yml"))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
class CompileCacheHandlerErrorsTest < Minitest::Test
|
class CompileCacheHandlerErrorsTest < Minitest::Test
|
||||||
include(TmpdirHelper)
|
include(TmpdirHelper)
|
||||||
|
@ -10,16 +11,16 @@ class CompileCacheHandlerErrorsTest < Minitest::Test
|
||||||
# 3. exception
|
# 3. exception
|
||||||
|
|
||||||
def test_input_to_storage_unexpected_type
|
def test_input_to_storage_unexpected_type
|
||||||
path = Help.set_file('a.rb', 'a = 3', 100)
|
path = Help.set_file("a.rb", "a = 3", 100)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).returns(nil)
|
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).returns(nil)
|
||||||
# this could be made slightly more obvious though.
|
# this could be made slightly more obvious though.
|
||||||
assert_raises(TypeError) { load(path) }
|
assert_raises(TypeError) { load(path) }
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_input_to_storage_invalid_instance_of_expected_type
|
def test_input_to_storage_invalid_instance_of_expected_type
|
||||||
path = Help.set_file('a.rb', 'a = 3', 100)
|
path = Help.set_file("a.rb", "a = 3", 100)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).returns('broken')
|
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).returns("broken")
|
||||||
Bootsnap::CompileCache::ISeq.expects(:input_to_output).with('a = 3', nil).returns('whatever')
|
Bootsnap::CompileCache::ISeq.expects(:input_to_output).with("a = 3", nil).returns("whatever")
|
||||||
_, err = capture_subprocess_io do
|
_, err = capture_subprocess_io do
|
||||||
load(path)
|
load(path)
|
||||||
end
|
end
|
||||||
|
@ -27,14 +28,14 @@ class CompileCacheHandlerErrorsTest < Minitest::Test
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_input_to_storage_raises
|
def test_input_to_storage_raises
|
||||||
path = Help.set_file('a.rb', 'a = 3', 100)
|
path = Help.set_file("a.rb", "a = 3", 100)
|
||||||
klass = Class.new(StandardError)
|
klass = Class.new(StandardError)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).raises(klass, 'oops')
|
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).raises(klass, "oops")
|
||||||
assert_raises(klass) { load(path) }
|
assert_raises(klass) { load(path) }
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_storage_to_output_unexpected_type
|
def test_storage_to_output_unexpected_type
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).returns(Object.new)
|
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).returns(Object.new)
|
||||||
# It seems like ruby doesn't really care.
|
# It seems like ruby doesn't really care.
|
||||||
load(path)
|
load(path)
|
||||||
|
@ -45,16 +46,16 @@ class CompileCacheHandlerErrorsTest < Minitest::Test
|
||||||
# def test_storage_to_output_invalid_instance_of_expected_type
|
# def test_storage_to_output_invalid_instance_of_expected_type
|
||||||
|
|
||||||
def test_storage_to_output_raises
|
def test_storage_to_output_raises
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
klass = Class.new(StandardError)
|
klass = Class.new(StandardError)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).times(2).raises(klass, 'oops')
|
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).times(2).raises(klass, "oops")
|
||||||
assert_raises(klass) { load(path) }
|
assert_raises(klass) { load(path) }
|
||||||
# called from two paths; this tests the second.
|
# called from two paths; this tests the second.
|
||||||
assert_raises(klass) { load(path) }
|
assert_raises(klass) { load(path) }
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_input_to_output_unexpected_type
|
def test_input_to_output_unexpected_type
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).raises(Bootsnap::CompileCache::Uncompilable)
|
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).raises(Bootsnap::CompileCache::Uncompilable)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:input_to_output).returns(Object.new)
|
Bootsnap::CompileCache::ISeq.expects(:input_to_output).returns(Object.new)
|
||||||
# It seems like ruby doesn't really care.
|
# It seems like ruby doesn't really care.
|
||||||
|
@ -66,10 +67,10 @@ class CompileCacheHandlerErrorsTest < Minitest::Test
|
||||||
# def test_input_to_output_invalid_instance_of_expected_type
|
# def test_input_to_output_invalid_instance_of_expected_type
|
||||||
|
|
||||||
def test_input_to_output_raises
|
def test_input_to_output_raises
|
||||||
path = Help.set_file('a.rb', 'a = 3', 100)
|
path = Help.set_file("a.rb", "a = 3", 100)
|
||||||
klass = Class.new(StandardError)
|
klass = Class.new(StandardError)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).raises(Bootsnap::CompileCache::Uncompilable)
|
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).raises(Bootsnap::CompileCache::Uncompilable)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:input_to_output).raises(klass, 'oops')
|
Bootsnap::CompileCache::ISeq.expects(:input_to_output).raises(klass, "oops")
|
||||||
assert_raises(klass) { load(path) }
|
assert_raises(klass) { load(path) }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,8 +1,9 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
require('tempfile')
|
require("test_helper")
|
||||||
require('tmpdir')
|
require("tempfile")
|
||||||
require('fileutils')
|
require("tmpdir")
|
||||||
|
require("fileutils")
|
||||||
|
|
||||||
class CompileCacheKeyFormatTest < Minitest::Test
|
class CompileCacheKeyFormatTest < Minitest::Test
|
||||||
FILE = File.expand_path(__FILE__)
|
FILE = File.expand_path(__FILE__)
|
||||||
|
@ -16,7 +17,7 @@ class CompileCacheKeyFormatTest < Minitest::Test
|
||||||
size: 16...24,
|
size: 16...24,
|
||||||
mtime: 24...32,
|
mtime: 24...32,
|
||||||
data_size: 32...40,
|
data_size: 32...40,
|
||||||
}
|
}.freeze
|
||||||
|
|
||||||
def test_key_version
|
def test_key_version
|
||||||
key = cache_key_for_file(FILE)
|
key = cache_key_for_file(FILE)
|
||||||
|
@ -27,12 +28,12 @@ class CompileCacheKeyFormatTest < Minitest::Test
|
||||||
def test_key_compile_option_stable
|
def test_key_compile_option_stable
|
||||||
k1 = cache_key_for_file(FILE)
|
k1 = cache_key_for_file(FILE)
|
||||||
k2 = cache_key_for_file(FILE)
|
k2 = cache_key_for_file(FILE)
|
||||||
RubyVM::InstructionSequence.compile_option = { tailcall_optimization: true }
|
RubyVM::InstructionSequence.compile_option = {tailcall_optimization: true}
|
||||||
k3 = cache_key_for_file(FILE)
|
k3 = cache_key_for_file(FILE)
|
||||||
assert_equal(k1[R[:compile_option]], k2[R[:compile_option]])
|
assert_equal(k1[R[:compile_option]], k2[R[:compile_option]])
|
||||||
refute_equal(k1[R[:compile_option]], k3[R[:compile_option]])
|
refute_equal(k1[R[:compile_option]], k3[R[:compile_option]])
|
||||||
ensure
|
ensure
|
||||||
RubyVM::InstructionSequence.compile_option = { tailcall_optimization: false }
|
RubyVM::InstructionSequence.compile_option = {tailcall_optimization: false}
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_key_ruby_revision
|
def test_key_ruby_revision
|
||||||
|
@ -60,11 +61,11 @@ class CompileCacheKeyFormatTest < Minitest::Test
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_fetch
|
def test_fetch
|
||||||
if RbConfig::CONFIG['host_os'] =~ /mswin|mingw|cygwin/
|
if RbConfig::CONFIG["host_os"] =~ /mswin|mingw|cygwin/
|
||||||
target = 'NUL'
|
target = "NUL"
|
||||||
expected_file = "#{@tmp_dir}/36/9eba19c29ffe00"
|
expected_file = "#{@tmp_dir}/36/9eba19c29ffe00"
|
||||||
else
|
else
|
||||||
target = '/dev/null'
|
target = "/dev/null"
|
||||||
expected_file = "#{@tmp_dir}/8c/d2d180bbd995df"
|
expected_file = "#{@tmp_dir}/8c/d2d180bbd995df"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -80,7 +81,7 @@ class CompileCacheKeyFormatTest < Minitest::Test
|
||||||
|
|
||||||
def test_unexistent_fetch
|
def test_unexistent_fetch
|
||||||
assert_raises(Errno::ENOENT) do
|
assert_raises(Errno::ENOENT) do
|
||||||
Bootsnap::CompileCache::Native.fetch(@tmp_dir, '123', Bootsnap::CompileCache::ISeq, nil)
|
Bootsnap::CompileCache::Native.fetch(@tmp_dir, "123", Bootsnap::CompileCache::ISeq, nil)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
class CompileCacheTest < Minitest::Test
|
class CompileCacheTest < Minitest::Test
|
||||||
include(TmpdirHelper)
|
include(TmpdirHelper)
|
||||||
|
@ -14,7 +15,7 @@ class CompileCacheTest < Minitest::Test
|
||||||
|
|
||||||
def test_coverage_running?
|
def test_coverage_running?
|
||||||
refute(Bootsnap::CompileCache::Native.coverage_running?)
|
refute(Bootsnap::CompileCache::Native.coverage_running?)
|
||||||
require('coverage')
|
require("coverage")
|
||||||
begin
|
begin
|
||||||
Coverage.start
|
Coverage.start
|
||||||
assert(Bootsnap::CompileCache::Native.coverage_running?)
|
assert(Bootsnap::CompileCache::Native.coverage_running?)
|
||||||
|
@ -24,7 +25,7 @@ class CompileCacheTest < Minitest::Test
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_no_write_permission_to_cache
|
def test_no_write_permission_to_cache
|
||||||
if RbConfig::CONFIG['host_os'] =~ /mswin|mingw|cygwin/
|
if RbConfig::CONFIG["host_os"] =~ /mswin|mingw|cygwin/
|
||||||
# Always pass this test on Windows because directories aren't read, only
|
# Always pass this test on Windows because directories aren't read, only
|
||||||
# listed. You can restrict the ability to list directory contents on
|
# listed. You can restrict the ability to list directory contents on
|
||||||
# Windows or you can set ACLS on a folder such that it is not allowed to
|
# Windows or you can set ACLS on a folder such that it is not allowed to
|
||||||
|
@ -36,25 +37,25 @@ class CompileCacheTest < Minitest::Test
|
||||||
# read-only files.
|
# read-only files.
|
||||||
pass
|
pass
|
||||||
else
|
else
|
||||||
path = Help.set_file('a.rb', 'a = 3', 100)
|
path = Help.set_file("a.rb", "a = 3", 100)
|
||||||
folder = File.dirname(Help.cache_path(@tmp_dir, path))
|
folder = File.dirname(Help.cache_path(@tmp_dir, path))
|
||||||
FileUtils.mkdir_p(folder)
|
FileUtils.mkdir_p(folder)
|
||||||
FileUtils.chmod(0400, folder)
|
FileUtils.chmod(0o400, folder)
|
||||||
load(path)
|
load(path)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_can_open_read_only_cache
|
def test_can_open_read_only_cache
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
# Load once to create the cache file
|
# Load once to create the cache file
|
||||||
load(path)
|
load(path)
|
||||||
FileUtils.chmod(0400, path)
|
FileUtils.chmod(0o400, path)
|
||||||
# Loading again after the file is marked read-only should still succeed
|
# Loading again after the file is marked read-only should still succeed
|
||||||
load(path)
|
load(path)
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_file_is_only_read_once
|
def test_file_is_only_read_once
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
storage = RubyVM::InstructionSequence.compile_file(path).to_binary
|
storage = RubyVM::InstructionSequence.compile_file(path).to_binary
|
||||||
output = RubyVM::InstructionSequence.load_from_binary(storage)
|
output = RubyVM::InstructionSequence.load_from_binary(storage)
|
||||||
# This doesn't really *prove* the file is only read once, but
|
# This doesn't really *prove* the file is only read once, but
|
||||||
|
@ -66,7 +67,7 @@ class CompileCacheTest < Minitest::Test
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_raises_syntax_error
|
def test_raises_syntax_error
|
||||||
path = Help.set_file('a.rb', 'a = (3', 100)
|
path = Help.set_file("a.rb", "a = (3", 100)
|
||||||
assert_raises(SyntaxError) do
|
assert_raises(SyntaxError) do
|
||||||
# SyntaxError emits directly to stderr in addition to raising, it seems.
|
# SyntaxError emits directly to stderr in addition to raising, it seems.
|
||||||
capture_io { load(path) }
|
capture_io { load(path) }
|
||||||
|
@ -74,19 +75,19 @@ class CompileCacheTest < Minitest::Test
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_no_recache_when_mtime_and_size_same
|
def test_no_recache_when_mtime_and_size_same
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
storage = RubyVM::InstructionSequence.compile_file(path).to_binary
|
storage = RubyVM::InstructionSequence.compile_file(path).to_binary
|
||||||
output = RubyVM::InstructionSequence.load_from_binary(storage)
|
output = RubyVM::InstructionSequence.load_from_binary(storage)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).times(1).returns(storage)
|
Bootsnap::CompileCache::ISeq.expects(:input_to_storage).times(1).returns(storage)
|
||||||
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).times(2).returns(output)
|
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).times(2).returns(output)
|
||||||
|
|
||||||
load(path)
|
load(path)
|
||||||
Help.set_file(path, 'a = a = 4', 100)
|
Help.set_file(path, "a = a = 4", 100)
|
||||||
load(path)
|
load(path)
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_recache_when_mtime_different
|
def test_recache_when_mtime_different
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
storage = RubyVM::InstructionSequence.compile_file(path).to_binary
|
storage = RubyVM::InstructionSequence.compile_file(path).to_binary
|
||||||
output = RubyVM::InstructionSequence.load_from_binary(storage)
|
output = RubyVM::InstructionSequence.load_from_binary(storage)
|
||||||
# Totally lies the second time but that's not the point.
|
# Totally lies the second time but that's not the point.
|
||||||
|
@ -94,12 +95,12 @@ class CompileCacheTest < Minitest::Test
|
||||||
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).times(2).returns(output)
|
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).times(2).returns(output)
|
||||||
|
|
||||||
load(path)
|
load(path)
|
||||||
Help.set_file(path, 'a = a = 2', 101)
|
Help.set_file(path, "a = a = 2", 101)
|
||||||
load(path)
|
load(path)
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_recache_when_size_different
|
def test_recache_when_size_different
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
storage = RubyVM::InstructionSequence.compile_file(path).to_binary
|
storage = RubyVM::InstructionSequence.compile_file(path).to_binary
|
||||||
output = RubyVM::InstructionSequence.load_from_binary(storage)
|
output = RubyVM::InstructionSequence.load_from_binary(storage)
|
||||||
# Totally lies the second time but that's not the point.
|
# Totally lies the second time but that's not the point.
|
||||||
|
@ -107,27 +108,27 @@ class CompileCacheTest < Minitest::Test
|
||||||
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).times(2).returns(output)
|
Bootsnap::CompileCache::ISeq.expects(:storage_to_output).times(2).returns(output)
|
||||||
|
|
||||||
load(path)
|
load(path)
|
||||||
Help.set_file(path, 'a = 33', 100)
|
Help.set_file(path, "a = 33", 100)
|
||||||
load(path)
|
load(path)
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_invalid_cache_file
|
def test_invalid_cache_file
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
cp = Help.cache_path(@tmp_dir, path)
|
cp = Help.cache_path(@tmp_dir, path)
|
||||||
FileUtils.mkdir_p(File.dirname(cp))
|
FileUtils.mkdir_p(File.dirname(cp))
|
||||||
File.write(cp, 'nope')
|
File.write(cp, "nope")
|
||||||
load(path)
|
load(path)
|
||||||
assert(File.size(cp) > 32) # cache was overwritten
|
assert(File.size(cp) > 32) # cache was overwritten
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_instrumentation_hit
|
def test_instrumentation_hit
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
file_path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
load(path)
|
load(file_path)
|
||||||
|
|
||||||
calls = []
|
calls = []
|
||||||
Bootsnap.instrumentation = ->(event, path) { calls << [event, path] }
|
Bootsnap.instrumentation = ->(event, path) { calls << [event, path] }
|
||||||
|
|
||||||
load(path)
|
load(file_path)
|
||||||
|
|
||||||
assert_equal [], calls
|
assert_equal [], calls
|
||||||
ensure
|
ensure
|
||||||
|
@ -135,29 +136,29 @@ class CompileCacheTest < Minitest::Test
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_instrumentation_miss
|
def test_instrumentation_miss
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
file_path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
|
|
||||||
calls = []
|
calls = []
|
||||||
Bootsnap.instrumentation = ->(event, path) { calls << [event, path] }
|
Bootsnap.instrumentation = ->(event, path) { calls << [event, path] }
|
||||||
|
|
||||||
load(path)
|
load(file_path)
|
||||||
|
|
||||||
assert_equal [[:miss, 'a.rb']], calls
|
assert_equal [[:miss, "a.rb"]], calls
|
||||||
ensure
|
ensure
|
||||||
Bootsnap.instrumentation = nil
|
Bootsnap.instrumentation = nil
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_instrumentation_stale
|
def test_instrumentation_stale
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
file_path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
load(path)
|
load(file_path)
|
||||||
path = Help.set_file('a.rb', 'a = a = 4', 101)
|
file_path = Help.set_file("a.rb", "a = a = 4", 101)
|
||||||
|
|
||||||
calls = []
|
calls = []
|
||||||
Bootsnap.instrumentation = ->(event, path) { calls << [event, path] }
|
Bootsnap.instrumentation = ->(event, path) { calls << [event, path] }
|
||||||
|
|
||||||
load(path)
|
load(file_path)
|
||||||
|
|
||||||
assert_equal [[:stale, 'a.rb']], calls
|
assert_equal [[:stale, "a.rb"]], calls
|
||||||
ensure
|
ensure
|
||||||
Bootsnap.instrumentation = nil
|
Bootsnap.instrumentation = nil
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,11 +1,12 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
class HelperTest < MiniTest::Test
|
class HelperTest < MiniTest::Test
|
||||||
include(TmpdirHelper)
|
include(TmpdirHelper)
|
||||||
|
|
||||||
def test_validate_cache_path
|
def test_validate_cache_path
|
||||||
path = Help.set_file('a.rb', 'a = a = 3', 100)
|
path = Help.set_file("a.rb", "a = a = 3", 100)
|
||||||
cp = Help.cache_path(@tmp_dir, path)
|
cp = Help.cache_path(@tmp_dir, path)
|
||||||
load(path)
|
load(path)
|
||||||
assert_equal(true, File.file?(cp))
|
assert_equal(true, File.file?(cp))
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
|
@ -28,31 +29,31 @@ module Bootsnap
|
||||||
# versions aren't a big deal, but feel free to fix the test.
|
# versions aren't a big deal, but feel free to fix the test.
|
||||||
def test_builtin_features
|
def test_builtin_features
|
||||||
cache = Cache.new(NullCache, [])
|
cache = Cache.new(NullCache, [])
|
||||||
assert_raises(ReturnFalse) { cache.find('thread') }
|
assert_raises(ReturnFalse) { cache.find("thread") }
|
||||||
assert_raises(ReturnFalse) { cache.find('thread.rb') }
|
assert_raises(ReturnFalse) { cache.find("thread.rb") }
|
||||||
assert_raises(ReturnFalse) { cache.find('enumerator') }
|
assert_raises(ReturnFalse) { cache.find("enumerator") }
|
||||||
assert_raises(ReturnFalse) { cache.find('enumerator.so') }
|
assert_raises(ReturnFalse) { cache.find("enumerator.so") }
|
||||||
if RUBY_PLATFORM =~ /darwin/
|
if RUBY_PLATFORM =~ /darwin/
|
||||||
assert_raises(ReturnFalse) { cache.find('enumerator.bundle') }
|
assert_raises(ReturnFalse) { cache.find("enumerator.bundle") }
|
||||||
else
|
else
|
||||||
assert_raises(FallbackScan) { cache.find('enumerator.bundle') }
|
assert_raises(FallbackScan) { cache.find("enumerator.bundle") }
|
||||||
end
|
end
|
||||||
|
|
||||||
bundle = RUBY_PLATFORM =~ /darwin/ ? 'bundle' : 'so'
|
bundle = RUBY_PLATFORM =~ /darwin/ ? "bundle" : "so"
|
||||||
|
|
||||||
refute(cache.find('thread.' + bundle))
|
refute(cache.find("thread." + bundle))
|
||||||
refute(cache.find('enumerator.rb'))
|
refute(cache.find("enumerator.rb"))
|
||||||
refute(cache.find('encdb.' + bundle))
|
refute(cache.find("encdb." + bundle))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_simple
|
def test_simple
|
||||||
po = [@dir1]
|
po = [@dir1]
|
||||||
cache = Cache.new(NullCache, po)
|
cache = Cache.new(NullCache, po)
|
||||||
assert_equal("#{@dir1}/a.rb", cache.find('a'))
|
assert_equal("#{@dir1}/a.rb", cache.find("a"))
|
||||||
refute(cache.find('a', try_extensions: false))
|
refute(cache.find("a", try_extensions: false))
|
||||||
cache.push_paths(po, @dir2)
|
cache.push_paths(po, @dir2)
|
||||||
assert_equal("#{@dir2}/b.rb", cache.find('b'))
|
assert_equal("#{@dir2}/b.rb", cache.find("b"))
|
||||||
refute(cache.find('b', try_extensions: false))
|
refute(cache.find("b", try_extensions: false))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_extension_append_for_relative_paths
|
def test_extension_append_for_relative_paths
|
||||||
|
@ -60,35 +61,35 @@ module Bootsnap
|
||||||
cache = Cache.new(NullCache, po)
|
cache = Cache.new(NullCache, po)
|
||||||
dir1_basename = File.basename(@dir1)
|
dir1_basename = File.basename(@dir1)
|
||||||
Dir.chdir(@dir1) do
|
Dir.chdir(@dir1) do
|
||||||
assert_equal("#{@dir1}/a.rb", cache.find('./a'))
|
assert_equal("#{@dir1}/a.rb", cache.find("./a"))
|
||||||
assert_equal("#{@dir1}/a", cache.find('./a', try_extensions: false))
|
assert_equal("#{@dir1}/a", cache.find("./a", try_extensions: false))
|
||||||
assert_equal("#{@dir1}/a.rb", cache.find("../#{dir1_basename}/a"))
|
assert_equal("#{@dir1}/a.rb", cache.find("../#{dir1_basename}/a"))
|
||||||
assert_equal("#{@dir1}/a", cache.find("../#{dir1_basename}/a", try_extensions: false))
|
assert_equal("#{@dir1}/a", cache.find("../#{dir1_basename}/a", try_extensions: false))
|
||||||
assert_equal("#{@dir1}/dl#{DLEXT}", cache.find('./dl'))
|
assert_equal("#{@dir1}/dl#{DLEXT}", cache.find("./dl"))
|
||||||
assert_equal("#{@dir1}/dl", cache.find('./dl', try_extensions: false))
|
assert_equal("#{@dir1}/dl", cache.find("./dl", try_extensions: false))
|
||||||
assert_equal("#{@dir1}/enoent", cache.find('./enoent'))
|
assert_equal("#{@dir1}/enoent", cache.find("./enoent"))
|
||||||
assert_equal("#{@dir1}/enoent", cache.find('./enoent', try_extensions: false))
|
assert_equal("#{@dir1}/enoent", cache.find("./enoent", try_extensions: false))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_unshifted_paths_have_higher_precedence
|
def test_unshifted_paths_have_higher_precedence
|
||||||
po = [@dir1]
|
po = [@dir1]
|
||||||
cache = Cache.new(NullCache, po)
|
cache = Cache.new(NullCache, po)
|
||||||
assert_equal("#{@dir1}/conflict.rb", cache.find('conflict'))
|
assert_equal("#{@dir1}/conflict.rb", cache.find("conflict"))
|
||||||
assert_equal("#{@dir1}/conflict.rb", cache.find('conflict.rb', try_extensions: false))
|
assert_equal("#{@dir1}/conflict.rb", cache.find("conflict.rb", try_extensions: false))
|
||||||
cache.unshift_paths(po, @dir2)
|
cache.unshift_paths(po, @dir2)
|
||||||
assert_equal("#{@dir2}/conflict.rb", cache.find('conflict'))
|
assert_equal("#{@dir2}/conflict.rb", cache.find("conflict"))
|
||||||
assert_equal("#{@dir2}/conflict.rb", cache.find('conflict.rb', try_extensions: false))
|
assert_equal("#{@dir2}/conflict.rb", cache.find("conflict.rb", try_extensions: false))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_pushed_paths_have_lower_precedence
|
def test_pushed_paths_have_lower_precedence
|
||||||
po = [@dir1]
|
po = [@dir1]
|
||||||
cache = Cache.new(NullCache, po)
|
cache = Cache.new(NullCache, po)
|
||||||
assert_equal("#{@dir1}/conflict.rb", cache.find('conflict'))
|
assert_equal("#{@dir1}/conflict.rb", cache.find("conflict"))
|
||||||
assert_equal("#{@dir1}/conflict.rb", cache.find('conflict.rb', try_extensions: false))
|
assert_equal("#{@dir1}/conflict.rb", cache.find("conflict.rb", try_extensions: false))
|
||||||
cache.push_paths(po, @dir2)
|
cache.push_paths(po, @dir2)
|
||||||
assert_equal("#{@dir1}/conflict.rb", cache.find('conflict'))
|
assert_equal("#{@dir1}/conflict.rb", cache.find("conflict"))
|
||||||
assert_equal("#{@dir1}/conflict.rb", cache.find('conflict.rb', try_extensions: false))
|
assert_equal("#{@dir1}/conflict.rb", cache.find("conflict.rb", try_extensions: false))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_directory_caching
|
def test_directory_caching
|
||||||
|
@ -100,8 +101,8 @@ module Bootsnap
|
||||||
|
|
||||||
def test_extension_permutations
|
def test_extension_permutations
|
||||||
cache = Cache.new(NullCache, [@dir1])
|
cache = Cache.new(NullCache, [@dir1])
|
||||||
assert_equal("#{@dir1}/dl#{DLEXT}", cache.find('dl'))
|
assert_equal("#{@dir1}/dl#{DLEXT}", cache.find("dl"))
|
||||||
refute(cache.find('dl', try_extensions: false))
|
refute(cache.find("dl", try_extensions: false))
|
||||||
assert_equal("#{@dir1}/dl#{DLEXT}", cache.find("dl#{DLEXT}"))
|
assert_equal("#{@dir1}/dl#{DLEXT}", cache.find("dl#{DLEXT}"))
|
||||||
assert_equal("#{@dir1}/both.rb", cache.find("both"))
|
assert_equal("#{@dir1}/both.rb", cache.find("both"))
|
||||||
refute(cache.find("both", try_extensions: false))
|
refute(cache.find("both", try_extensions: false))
|
||||||
|
@ -114,14 +115,14 @@ module Bootsnap
|
||||||
def test_relative_paths_rescanned
|
def test_relative_paths_rescanned
|
||||||
Dir.chdir(@dir2) do
|
Dir.chdir(@dir2) do
|
||||||
cache = Cache.new(NullCache, %w(foo))
|
cache = Cache.new(NullCache, %w(foo))
|
||||||
refute(cache.find('bar/baz'))
|
refute(cache.find("bar/baz"))
|
||||||
Dir.chdir(@dir1) do
|
Dir.chdir(@dir1) do
|
||||||
# one caveat here is that you get the actual path back when
|
# one caveat here is that you get the actual path back when
|
||||||
# resolving relative paths. On darwin, this means that
|
# resolving relative paths. On darwin, this means that
|
||||||
# /var/folders/... comes back as /private/var/folders/... -- In
|
# /var/folders/... comes back as /private/var/folders/... -- In
|
||||||
# production, this should be fine, but for this test to pass, we
|
# production, this should be fine, but for this test to pass, we
|
||||||
# have to resolve it.
|
# have to resolve it.
|
||||||
assert_equal(File.realpath("#{@dir1}/foo/bar/baz.rb"), cache.find('bar/baz'))
|
assert_equal(File.realpath("#{@dir1}/foo/bar/baz.rb"), cache.find("bar/baz"))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -136,14 +137,14 @@ module Bootsnap
|
||||||
FileUtils.touch("#{@dir1}/new.rb")
|
FileUtils.touch("#{@dir1}/new.rb")
|
||||||
|
|
||||||
dev_no_cache.stubs(:now).returns(time + 31)
|
dev_no_cache.stubs(:now).returns(time + 31)
|
||||||
refute(dev_no_cache.find('new'))
|
refute(dev_no_cache.find("new"))
|
||||||
|
|
||||||
dev_yes_cache.stubs(:now).returns(time + 28)
|
dev_yes_cache.stubs(:now).returns(time + 28)
|
||||||
assert_raises(Bootsnap::LoadPathCache::FallbackScan) do
|
assert_raises(Bootsnap::LoadPathCache::FallbackScan) do
|
||||||
dev_yes_cache.find('new')
|
dev_yes_cache.find("new")
|
||||||
end
|
end
|
||||||
dev_yes_cache.stubs(:now).returns(time + 31)
|
dev_yes_cache.stubs(:now).returns(time + 31)
|
||||||
assert(dev_yes_cache.find('new'))
|
assert(dev_yes_cache.find("new"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_path_obj_equal?
|
def test_path_obj_equal?
|
||||||
|
@ -152,35 +153,35 @@ module Bootsnap
|
||||||
|
|
||||||
path_obj.unshift(@dir1)
|
path_obj.unshift(@dir1)
|
||||||
|
|
||||||
assert_equal("#{@dir1}/a.rb", cache.find('a'))
|
assert_equal("#{@dir1}/a.rb", cache.find("a"))
|
||||||
end
|
end
|
||||||
|
|
||||||
if RUBY_VERSION >= '2.5' && !(RbConfig::CONFIG['host_os'] =~ /mswin|mingw|cygwin/)
|
if RUBY_VERSION >= "2.5" && RbConfig::CONFIG["host_os"] !~ /mswin|mingw|cygwin/
|
||||||
# https://github.com/ruby/ruby/pull/4061
|
# https://github.com/ruby/ruby/pull/4061
|
||||||
# https://bugs.ruby-lang.org/issues/17517
|
# https://bugs.ruby-lang.org/issues/17517
|
||||||
OS_ASCII_PATH_ENCODING = RUBY_VERSION >= '3.1' ? Encoding::UTF_8 : Encoding::US_ASCII
|
OS_ASCII_PATH_ENCODING = RUBY_VERSION >= "3.1" ? Encoding::UTF_8 : Encoding::US_ASCII
|
||||||
|
|
||||||
def test_path_encoding
|
def test_path_encoding
|
||||||
po = [@dir1]
|
po = [@dir1]
|
||||||
cache = Cache.new(NullCache, po)
|
cache = Cache.new(NullCache, po)
|
||||||
|
|
||||||
path = cache.find('a')
|
path = cache.find("a")
|
||||||
|
|
||||||
assert_equal("#{@dir1}/a.rb", path)
|
assert_equal("#{@dir1}/a.rb", path)
|
||||||
require path
|
require path
|
||||||
internal_path = $LOADED_FEATURES.last
|
internal_path = $LOADED_FEATURES.last
|
||||||
assert_equal(OS_ASCII_PATH_ENCODING, internal_path.encoding)
|
assert_equal(OS_ASCII_PATH_ENCODING, internal_path.encoding)
|
||||||
assert_equal(OS_ASCII_PATH_ENCODING, path.encoding)
|
assert_equal(OS_ASCII_PATH_ENCODING, path.encoding)
|
||||||
File.write(path, '')
|
File.write(path, "")
|
||||||
assert_same path, internal_path
|
assert_same path, internal_path
|
||||||
|
|
||||||
utf8_path = cache.find('béé')
|
utf8_path = cache.find("béé")
|
||||||
require utf8_path
|
require utf8_path
|
||||||
internal_utf8_path = $LOADED_FEATURES.last
|
internal_utf8_path = $LOADED_FEATURES.last
|
||||||
assert_equal("#{@dir1}/béé.rb", utf8_path)
|
assert_equal("#{@dir1}/béé.rb", utf8_path)
|
||||||
assert_equal(Encoding::UTF_8, internal_utf8_path.encoding)
|
assert_equal(Encoding::UTF_8, internal_utf8_path.encoding)
|
||||||
assert_equal(Encoding::UTF_8, utf8_path.encoding)
|
assert_equal(Encoding::UTF_8, utf8_path.encoding)
|
||||||
File.write(utf8_path, '')
|
File.write(utf8_path, "")
|
||||||
assert_same utf8_path, internal_utf8_path
|
assert_same utf8_path, internal_utf8_path
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
|
@ -11,34 +12,34 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_observes_changes
|
def test_observes_changes
|
||||||
@observer.expects(:push_paths).with(@arr, 'a')
|
@observer.expects(:push_paths).with(@arr, "a")
|
||||||
@arr << 'a'
|
@arr << "a"
|
||||||
|
|
||||||
@observer.expects(:push_paths).with(@arr, 'b', 'c')
|
@observer.expects(:push_paths).with(@arr, "b", "c")
|
||||||
@arr.push('b', 'c')
|
@arr.push("b", "c")
|
||||||
|
|
||||||
@observer.expects(:push_paths).with(@arr, 'd', 'e')
|
@observer.expects(:push_paths).with(@arr, "d", "e")
|
||||||
@arr.append('d', 'e')
|
@arr.append("d", "e")
|
||||||
|
|
||||||
@observer.expects(:unshift_paths).with(@arr, 'f', 'g')
|
@observer.expects(:unshift_paths).with(@arr, "f", "g")
|
||||||
@arr.unshift('f', 'g')
|
@arr.unshift("f", "g")
|
||||||
|
|
||||||
@observer.expects(:push_paths).with(@arr, 'h', 'i')
|
@observer.expects(:push_paths).with(@arr, "h", "i")
|
||||||
@arr.concat(%w(h i))
|
@arr.concat(%w(h i))
|
||||||
|
|
||||||
@observer.expects(:unshift_paths).with(@arr, 'j', 'k')
|
@observer.expects(:unshift_paths).with(@arr, "j", "k")
|
||||||
@arr.prepend('j', 'k')
|
@arr.prepend("j", "k")
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_reinitializes_on_aggressive_modifications
|
def test_reinitializes_on_aggressive_modifications
|
||||||
@observer.expects(:push_paths).with(@arr, 'a', 'b', 'c')
|
@observer.expects(:push_paths).with(@arr, "a", "b", "c")
|
||||||
@arr.push('a', 'b', 'c')
|
@arr.push("a", "b", "c")
|
||||||
|
|
||||||
@observer.expects(:reinitialize).times(4)
|
@observer.expects(:reinitialize).times(4)
|
||||||
@arr.delete(3)
|
@arr.delete(3)
|
||||||
@arr.compact!
|
@arr.compact!
|
||||||
@arr.map!(&:upcase)
|
@arr.map!(&:upcase)
|
||||||
assert_equal('C', @arr.pop)
|
assert_equal("C", @arr.pop)
|
||||||
assert_equal(%w(A B), @arr)
|
assert_equal(%w(A B), @arr)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -50,8 +51,8 @@ module Bootsnap
|
||||||
def test_register_twice_observes_once
|
def test_register_twice_observes_once
|
||||||
ChangeObserver.register(@observer, @arr)
|
ChangeObserver.register(@observer, @arr)
|
||||||
|
|
||||||
@observer.expects(:push_paths).with(@arr, 'a').once
|
@observer.expects(:push_paths).with(@arr, "a").once
|
||||||
@arr << 'a'
|
@arr << "a"
|
||||||
assert_equal(%w(a), @arr)
|
assert_equal(%w(a), @arr)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module KernelRequireTest
|
module KernelRequireTest
|
||||||
|
@ -24,10 +25,10 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_no_exstensions_for_kernel_load
|
def test_no_exstensions_for_kernel_load
|
||||||
assert_raises(LoadError) { load 'a' }
|
assert_raises(LoadError) { load "a" }
|
||||||
assert(load 'no_ext')
|
assert(load("no_ext"))
|
||||||
Dir.chdir(@dir2)
|
Dir.chdir(@dir2)
|
||||||
assert(load 'loads.rb')
|
assert(load("loads.rb"))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
|
@ -11,35 +12,35 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_successful_addition
|
def test_successful_addition
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.register('bundler', '/a/b/bundler.rb') {}
|
@index.register("bundler", "/a/b/bundler.rb") {}
|
||||||
assert(@index.key?('bundler'))
|
assert(@index.key?("bundler"))
|
||||||
assert(@index.key?('bundler.rb'))
|
assert(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_no_add_on_raise
|
def test_no_add_on_raise
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
assert_raises(RuntimeError) do
|
assert_raises(RuntimeError) do
|
||||||
@index.register('bundler', '/a/b/bundler.rb') { raise }
|
@index.register("bundler", "/a/b/bundler.rb") { raise }
|
||||||
end
|
end
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_infer_base_from_ext
|
def test_infer_base_from_ext
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.register('bundler.rb') {}
|
@index.register("bundler.rb") {}
|
||||||
assert(@index.key?('bundler'))
|
assert(@index.key?("bundler"))
|
||||||
assert(@index.key?('bundler.rb'))
|
assert(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_only_strip_elidable_ext
|
def test_only_strip_elidable_ext
|
||||||
|
@ -48,95 +49,95 @@ module Bootsnap
|
||||||
#
|
#
|
||||||
# E.g. 'descriptor.pb.rb' if required via 'descriptor.pb'
|
# E.g. 'descriptor.pb.rb' if required via 'descriptor.pb'
|
||||||
# should never be shortened to merely 'descriptor'!
|
# should never be shortened to merely 'descriptor'!
|
||||||
refute(@index.key?('descriptor.pb'))
|
refute(@index.key?("descriptor.pb"))
|
||||||
refute(@index.key?('descriptor.pb.rb'))
|
refute(@index.key?("descriptor.pb.rb"))
|
||||||
refute(@index.key?('descriptor.rb'))
|
refute(@index.key?("descriptor.rb"))
|
||||||
refute(@index.key?('descriptor'))
|
refute(@index.key?("descriptor"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.register('descriptor.pb.rb') {}
|
@index.register("descriptor.pb.rb") {}
|
||||||
assert(@index.key?('descriptor.pb'))
|
assert(@index.key?("descriptor.pb"))
|
||||||
assert(@index.key?('descriptor.pb.rb'))
|
assert(@index.key?("descriptor.pb.rb"))
|
||||||
refute(@index.key?('descriptor.rb'))
|
refute(@index.key?("descriptor.rb"))
|
||||||
refute(@index.key?('descriptor'))
|
refute(@index.key?("descriptor"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shared_library_ext_considered_elidable
|
def test_shared_library_ext_considered_elidable
|
||||||
# Check that '.dylib' (token shared library extension) is treated as elidable,
|
# Check that '.dylib' (token shared library extension) is treated as elidable,
|
||||||
# and doesn't get mixed up with Ruby '.rb' files.
|
# and doesn't get mixed up with Ruby '.rb' files.
|
||||||
refute(@index.key?('libgit2.dylib'))
|
refute(@index.key?("libgit2.dylib"))
|
||||||
refute(@index.key?('libgit2.dylib.rb'))
|
refute(@index.key?("libgit2.dylib.rb"))
|
||||||
refute(@index.key?('descriptor.rb'))
|
refute(@index.key?("descriptor.rb"))
|
||||||
refute(@index.key?('descriptor'))
|
refute(@index.key?("descriptor"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.register('libgit2.dylib') {}
|
@index.register("libgit2.dylib") {}
|
||||||
assert(@index.key?('libgit2.dylib'))
|
assert(@index.key?("libgit2.dylib"))
|
||||||
refute(@index.key?('libgit2.dylib.rb'))
|
refute(@index.key?("libgit2.dylib.rb"))
|
||||||
refute(@index.key?('libgit2.rb'))
|
refute(@index.key?("libgit2.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_cannot_infer_ext_from_base # Current limitation
|
def test_cannot_infer_ext_from_base # Current limitation
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.register('bundler') {}
|
@index.register("bundler") {}
|
||||||
assert(@index.key?('bundler'))
|
assert(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_purge_loaded_feature
|
def test_purge_loaded_feature
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.register('bundler', '/a/b/bundler.rb') {}
|
@index.register("bundler", "/a/b/bundler.rb") {}
|
||||||
assert(@index.key?('bundler'))
|
assert(@index.key?("bundler"))
|
||||||
assert(@index.key?('bundler.rb'))
|
assert(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.purge('/a/b/bundler.rb')
|
@index.purge("/a/b/bundler.rb")
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_purge_multi_loaded_feature
|
def test_purge_multi_loaded_feature
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.register('bundler', '/a/b/bundler.rb') {}
|
@index.register("bundler", "/a/b/bundler.rb") {}
|
||||||
assert(@index.key?('bundler'))
|
assert(@index.key?("bundler"))
|
||||||
assert(@index.key?('bundler.rb'))
|
assert(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.purge_multi(['/a/b/bundler.rb', '/a/b/does-not-exist.rb'])
|
@index.purge_multi(["/a/b/bundler.rb", "/a/b/does-not-exist.rb"])
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_register_finds_correct_feature
|
def test_register_finds_correct_feature
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.register('bundler', nil) { $LOADED_FEATURES << '/a/b/bundler.rb' }
|
@index.register("bundler", nil) { $LOADED_FEATURES << "/a/b/bundler.rb" }
|
||||||
assert(@index.key?('bundler'))
|
assert(@index.key?("bundler"))
|
||||||
assert(@index.key?('bundler.rb'))
|
assert(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
@index.purge('/a/b/bundler.rb')
|
@index.purge("/a/b/bundler.rb")
|
||||||
refute(@index.key?('bundler'))
|
refute(@index.key?("bundler"))
|
||||||
refute(@index.key?('bundler.rb'))
|
refute(@index.key?("bundler.rb"))
|
||||||
refute(@index.key?('foo'))
|
refute(@index.key?("foo"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_derives_initial_state_from_loaded_features
|
def test_derives_initial_state_from_loaded_features
|
||||||
index = LoadedFeaturesIndex.new
|
index = LoadedFeaturesIndex.new
|
||||||
assert(index.key?('minitest/autorun'))
|
assert(index.key?("minitest/autorun"))
|
||||||
assert(index.key?('minitest/autorun.rb'))
|
assert(index.key?("minitest/autorun.rb"))
|
||||||
refute(index.key?('minitest/autorun.so'))
|
refute(index.key?("minitest/autorun.so"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_works_with_pathname
|
def test_works_with_pathname
|
||||||
path = 'bundler.rb'
|
path = "bundler.rb"
|
||||||
pathname = Pathname.new(path)
|
pathname = Pathname.new(path)
|
||||||
@index.register(pathname, path) { true }
|
@index.register(pathname, path) { true }
|
||||||
assert(@index.key?(pathname))
|
assert(@index.key?(pathname))
|
||||||
|
|
|
@ -1,11 +1,12 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
class PathScannerTest < MiniTest::Test
|
class PathScannerTest < MiniTest::Test
|
||||||
DLEXT = RbConfig::CONFIG['DLEXT']
|
DLEXT = RbConfig::CONFIG["DLEXT"]
|
||||||
OTHER_DLEXT = DLEXT == 'bundle' ? 'so' : 'bundle'
|
OTHER_DLEXT = DLEXT == "bundle" ? "so" : "bundle"
|
||||||
|
|
||||||
def test_scans_requirables_and_dirs
|
def test_scans_requirables_and_dirs
|
||||||
Dir.mktmpdir do |dir|
|
Dir.mktmpdir do |dir|
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
require('bootsnap/load_path_cache')
|
require("test_helper")
|
||||||
|
require("bootsnap/load_path_cache")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
|
@ -10,17 +11,17 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_stability
|
def test_stability
|
||||||
require('time')
|
require("time")
|
||||||
time_file = Time.method(:rfc2822).source_location[0]
|
time_file = Time.method(:rfc2822).source_location[0]
|
||||||
volatile = Path.new(__FILE__)
|
volatile = Path.new(__FILE__)
|
||||||
stable = Path.new(time_file)
|
stable = Path.new(time_file)
|
||||||
unknown = Path.new('/who/knows')
|
unknown = Path.new("/who/knows")
|
||||||
lib = Path.new(RbConfig::CONFIG['libdir'] + '/a')
|
lib = Path.new(RbConfig::CONFIG["libdir"] + "/a")
|
||||||
site = Path.new(RbConfig::CONFIG['sitedir'] + '/b')
|
site = Path.new(RbConfig::CONFIG["sitedir"] + "/b")
|
||||||
absolute_prefix = RbConfig::CONFIG['host_os'] =~ /mswin|mingw|cygwin/ ? ENV['SystemDrive'] : ''
|
absolute_prefix = RbConfig::CONFIG["host_os"] =~ /mswin|mingw|cygwin/ ? ENV["SystemDrive"] : ""
|
||||||
bundler = Path.new(absolute_prefix + '/bp/3')
|
bundler = Path.new(absolute_prefix + "/bp/3")
|
||||||
|
|
||||||
Bundler.stubs(:bundle_path).returns(absolute_prefix + '/bp')
|
Bundler.stubs(:bundle_path).returns(absolute_prefix + "/bp")
|
||||||
|
|
||||||
assert(stable.stable?, "The stable path #{stable.path.inspect} was unexpectedly not stable.")
|
assert(stable.stable?, "The stable path #{stable.path.inspect} was unexpectedly not stable.")
|
||||||
refute(stable.volatile?, "The stable path #{stable.path.inspect} was unexpectedly volatile.")
|
refute(stable.volatile?, "The stable path #{stable.path.inspect} was unexpectedly volatile.")
|
||||||
|
@ -35,17 +36,17 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_non_directory?
|
def test_non_directory?
|
||||||
if RbConfig::CONFIG['host_os'] =~ /mswin|mingw|cygwin/
|
if RbConfig::CONFIG["host_os"] =~ /mswin|mingw|cygwin/
|
||||||
refute(Path.new('c:/dev').non_directory?)
|
refute(Path.new("c:/dev").non_directory?)
|
||||||
refute(Path.new('c:/nope').non_directory?)
|
refute(Path.new("c:/nope").non_directory?)
|
||||||
# there isn't a direct analog i could think of
|
# there isn't a direct analog i could think of
|
||||||
# assert(Path.new('/dev/null').non_directory?)
|
# assert(Path.new('/dev/null').non_directory?)
|
||||||
assert(Path.new("#{ENV['WinDir']}/System32/Drivers/Etc/hosts").non_directory?)
|
assert(Path.new("#{ENV['WinDir']}/System32/Drivers/Etc/hosts").non_directory?)
|
||||||
else
|
else
|
||||||
refute(Path.new('/dev').non_directory?)
|
refute(Path.new("/dev").non_directory?)
|
||||||
refute(Path.new('/nope').non_directory?)
|
refute(Path.new("/nope").non_directory?)
|
||||||
assert(Path.new('/dev/null').non_directory?)
|
assert(Path.new("/dev/null").non_directory?)
|
||||||
assert(Path.new('/etc/hosts').non_directory?)
|
assert(Path.new("/etc/hosts").non_directory?)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
|
|
||||||
require('test_helper')
|
require("test_helper")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
class RealpathCacheTest < MiniTest::Test
|
class RealpathCacheTest < MiniTest::Test
|
||||||
EXTENSIONS = ['', *CACHED_EXTENSIONS]
|
EXTENSIONS = ["", *CACHED_EXTENSIONS].freeze
|
||||||
|
|
||||||
def setup
|
def setup
|
||||||
@cache = RealpathCache.new
|
@cache = RealpathCache.new
|
||||||
|
@ -16,13 +16,13 @@ module Bootsnap
|
||||||
@symlinked_dir = "#{@base_dir}/symlink"
|
@symlinked_dir = "#{@base_dir}/symlink"
|
||||||
FileUtils.ln_s(@absolute_dir, @symlinked_dir)
|
FileUtils.ln_s(@absolute_dir, @symlinked_dir)
|
||||||
|
|
||||||
real_caller = File.new("#{@absolute_dir}/real_caller.rb", 'w').tap(&:close).path
|
real_caller = File.new("#{@absolute_dir}/real_caller.rb", "w").tap(&:close).path
|
||||||
symlinked_caller = "#{@absolute_dir}/symlinked_caller.rb"
|
symlinked_caller = "#{@absolute_dir}/symlinked_caller.rb"
|
||||||
|
|
||||||
FileUtils.ln_s(real_caller, symlinked_caller)
|
FileUtils.ln_s(real_caller, symlinked_caller)
|
||||||
|
|
||||||
EXTENSIONS.each do |ext|
|
EXTENSIONS.each do |ext|
|
||||||
real_required = File.new("#{@absolute_dir}/real_required#{ext}", 'w').tap(&:close).path
|
real_required = File.new("#{@absolute_dir}/real_required#{ext}", "w").tap(&:close).path
|
||||||
|
|
||||||
symlinked_required = "#{@absolute_dir}/symlinked_required#{ext}"
|
symlinked_required = "#{@absolute_dir}/symlinked_required#{ext}"
|
||||||
FileUtils.ln_s(real_required, symlinked_required)
|
FileUtils.ln_s(real_required, symlinked_required)
|
||||||
|
@ -40,9 +40,11 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
variants = %w(absolute symlink).product(%w(absolute symlink),
|
variants = %w(absolute symlink).product(
|
||||||
|
%w(absolute symlink),
|
||||||
%w(real_caller symlinked_caller),
|
%w(real_caller symlinked_caller),
|
||||||
%w(real_required symlinked_required))
|
%w(real_required symlinked_required),
|
||||||
|
)
|
||||||
|
|
||||||
variants.each do |caller_dir, required_dir, caller_file, required_file|
|
variants.each do |caller_dir, required_dir, caller_file, required_file|
|
||||||
method_name = "test_with_#{caller_dir}_caller_dir_" \
|
method_name = "test_with_#{caller_dir}_caller_dir_" \
|
||||||
|
|
|
@ -1,7 +1,8 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
require('tmpdir')
|
require("test_helper")
|
||||||
require('fileutils')
|
require("tmpdir")
|
||||||
|
require("fileutils")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
module LoadPathCache
|
module LoadPathCache
|
||||||
|
@ -19,36 +20,36 @@ module Bootsnap
|
||||||
attr_reader(:store)
|
attr_reader(:store)
|
||||||
|
|
||||||
def test_persistence
|
def test_persistence
|
||||||
store.transaction { store.set('a', 'b') }
|
store.transaction { store.set("a", "b") }
|
||||||
|
|
||||||
store2 = Store.new(@path)
|
store2 = Store.new(@path)
|
||||||
assert_equal('b', store2.get('a'))
|
assert_equal("b", store2.get("a"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_modification
|
def test_modification
|
||||||
store.transaction { store.set('a', 'b') }
|
store.transaction { store.set("a", "b") }
|
||||||
|
|
||||||
store2 = Store.new(@path)
|
store2 = Store.new(@path)
|
||||||
assert_equal('b', store2.get('a'))
|
assert_equal("b", store2.get("a"))
|
||||||
store.transaction { store.set('a', 'c') }
|
store.transaction { store.set("a", "c") }
|
||||||
|
|
||||||
store3 = Store.new(@path)
|
store3 = Store.new(@path)
|
||||||
assert_equal('c', store3.get('a'))
|
assert_equal("c", store3.get("a"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_stores_arrays
|
def test_stores_arrays
|
||||||
store.transaction { store.set('a', [1234, %w(a b)]) }
|
store.transaction { store.set("a", [1234, %w(a b)]) }
|
||||||
|
|
||||||
store2 = Store.new(@path)
|
store2 = Store.new(@path)
|
||||||
assert_equal([1234, %w(a b)], store2.get('a'))
|
assert_equal([1234, %w(a b)], store2.get("a"))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_transaction_required_to_set
|
def test_transaction_required_to_set
|
||||||
assert_raises(Store::SetOutsideTransactionNotAllowed) do
|
assert_raises(Store::SetOutsideTransactionNotAllowed) do
|
||||||
store.set('a', 'b')
|
store.set("a", "b")
|
||||||
end
|
end
|
||||||
assert_raises(Store::SetOutsideTransactionNotAllowed) do
|
assert_raises(Store::SetOutsideTransactionNotAllowed) do
|
||||||
store.fetch('a') { 'b' }
|
store.fetch("a") { "b" }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -59,35 +60,35 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_no_commit_unless_dirty
|
def test_no_commit_unless_dirty
|
||||||
store.transaction { store.set('a', nil) }
|
store.transaction { store.set("a", nil) }
|
||||||
refute(File.exist?(@path))
|
refute(File.exist?(@path))
|
||||||
store.transaction { store.set('a', 1) }
|
store.transaction { store.set("a", 1) }
|
||||||
assert(File.exist?(@path))
|
assert(File.exist?(@path))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_retry_on_collision
|
def test_retry_on_collision
|
||||||
retries = sequence('retries')
|
retries = sequence("retries")
|
||||||
|
|
||||||
MessagePack.expects(:dump).in_sequence(retries).raises(Errno::EEXIST.new("File exists @ rb_sysopen"))
|
MessagePack.expects(:dump).in_sequence(retries).raises(Errno::EEXIST.new("File exists @ rb_sysopen"))
|
||||||
MessagePack.expects(:dump).in_sequence(retries).returns(1)
|
MessagePack.expects(:dump).in_sequence(retries).returns(1)
|
||||||
FileUtils.expects(:mv).in_sequence(retries)
|
FileUtils.expects(:mv).in_sequence(retries)
|
||||||
|
|
||||||
store.transaction { store.set('a', 1) }
|
store.transaction { store.set("a", 1) }
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_ignore_read_only_filesystem
|
def test_ignore_read_only_filesystem
|
||||||
MessagePack.expects(:dump).raises(Errno::EROFS.new("Read-only file system @ rb_sysopen"))
|
MessagePack.expects(:dump).raises(Errno::EROFS.new("Read-only file system @ rb_sysopen"))
|
||||||
store.transaction { store.set('a', 1) }
|
store.transaction { store.set("a", 1) }
|
||||||
refute(File.exist?(@path))
|
refute(File.exist?(@path))
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_bust_cache_on_ruby_change
|
def test_bust_cache_on_ruby_change
|
||||||
store.transaction { store.set('a', 'b') }
|
store.transaction { store.set("a", "b") }
|
||||||
|
|
||||||
assert_equal 'b', Store.new(@path).get('a')
|
assert_equal "b", Store.new(@path).get("a")
|
||||||
|
|
||||||
stub_const(Store, :CURRENT_VERSION, "foobar") do
|
stub_const(Store, :CURRENT_VERSION, "foobar") do
|
||||||
assert_nil Store.new(@path).get('a')
|
assert_nil Store.new(@path).get("a")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -1,3 +1,4 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('bundler/setup')
|
|
||||||
require('bootsnap/setup')
|
require("bundler/setup")
|
||||||
|
require("bootsnap/setup")
|
||||||
|
|
|
@ -1,12 +1,13 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
|
require("test_helper")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
class SetupTest < Minitest::Test
|
class SetupTest < Minitest::Test
|
||||||
def setup
|
def setup
|
||||||
@_old_env = ENV.to_h
|
@_old_env = ENV.to_h
|
||||||
@tmp_dir = Dir.mktmpdir('bootsnap-test')
|
@tmp_dir = Dir.mktmpdir("bootsnap-test")
|
||||||
ENV['BOOTSNAP_CACHE_DIR'] = @tmp_dir
|
ENV["BOOTSNAP_CACHE_DIR"] = @tmp_dir
|
||||||
end
|
end
|
||||||
|
|
||||||
def teardown
|
def teardown
|
||||||
|
@ -27,7 +28,7 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_default_setup_with_ENV_not_dev
|
def test_default_setup_with_ENV_not_dev
|
||||||
ENV['ENV'] = 'something'
|
ENV["ENV"] = "something"
|
||||||
|
|
||||||
Bootsnap.expects(:setup).with(
|
Bootsnap.expects(:setup).with(
|
||||||
cache_dir: @tmp_dir,
|
cache_dir: @tmp_dir,
|
||||||
|
@ -42,7 +43,7 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_default_setup_with_DISABLE_BOOTSNAP_LOAD_PATH_CACHE
|
def test_default_setup_with_DISABLE_BOOTSNAP_LOAD_PATH_CACHE
|
||||||
ENV['DISABLE_BOOTSNAP_LOAD_PATH_CACHE'] = 'something'
|
ENV["DISABLE_BOOTSNAP_LOAD_PATH_CACHE"] = "something"
|
||||||
|
|
||||||
Bootsnap.expects(:setup).with(
|
Bootsnap.expects(:setup).with(
|
||||||
cache_dir: @tmp_dir,
|
cache_dir: @tmp_dir,
|
||||||
|
@ -57,7 +58,7 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_default_setup_with_DISABLE_BOOTSNAP_COMPILE_CACHE
|
def test_default_setup_with_DISABLE_BOOTSNAP_COMPILE_CACHE
|
||||||
ENV['DISABLE_BOOTSNAP_COMPILE_CACHE'] = 'something'
|
ENV["DISABLE_BOOTSNAP_COMPILE_CACHE"] = "something"
|
||||||
|
|
||||||
Bootsnap.expects(:setup).with(
|
Bootsnap.expects(:setup).with(
|
||||||
cache_dir: @tmp_dir,
|
cache_dir: @tmp_dir,
|
||||||
|
@ -72,14 +73,14 @@ module Bootsnap
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_default_setup_with_DISABLE_BOOTSNAP
|
def test_default_setup_with_DISABLE_BOOTSNAP
|
||||||
ENV['DISABLE_BOOTSNAP'] = 'something'
|
ENV["DISABLE_BOOTSNAP"] = "something"
|
||||||
|
|
||||||
Bootsnap.expects(:setup).never
|
Bootsnap.expects(:setup).never
|
||||||
Bootsnap.default_setup
|
Bootsnap.default_setup
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_default_setup_with_BOOTSNAP_LOG
|
def test_default_setup_with_BOOTSNAP_LOG
|
||||||
ENV['BOOTSNAP_LOG'] = 'something'
|
ENV["BOOTSNAP_LOG"] = "something"
|
||||||
|
|
||||||
Bootsnap.expects(:setup).with(
|
Bootsnap.expects(:setup).with(
|
||||||
cache_dir: @tmp_dir,
|
cache_dir: @tmp_dir,
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
$LOAD_PATH.unshift(File.expand_path('../../lib', __FILE__))
|
|
||||||
|
$LOAD_PATH.unshift(File.expand_path("../lib", __dir__))
|
||||||
|
|
||||||
if defined? Warning
|
if defined? Warning
|
||||||
if Warning.respond_to?(:[]=)
|
if Warning.respond_to?(:[]=)
|
||||||
|
@ -7,18 +8,18 @@ if defined? Warning
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
require('bundler/setup')
|
require("bundler/setup")
|
||||||
require('bootsnap')
|
require("bootsnap")
|
||||||
require('bootsnap/compile_cache/yaml')
|
require("bootsnap/compile_cache/yaml")
|
||||||
require('bootsnap/compile_cache/json')
|
require("bootsnap/compile_cache/json")
|
||||||
|
|
||||||
require('tmpdir')
|
require("tmpdir")
|
||||||
require('fileutils')
|
require("fileutils")
|
||||||
|
|
||||||
require('minitest/autorun')
|
require("minitest/autorun")
|
||||||
require('mocha/minitest')
|
require("mocha/minitest")
|
||||||
|
|
||||||
cache_dir = File.expand_path('../../tmp/bootsnap/compile-cache', __FILE__)
|
cache_dir = File.expand_path("../tmp/bootsnap/compile-cache", __dir__)
|
||||||
Bootsnap::CompileCache.setup(cache_dir: cache_dir, iseq: true, yaml: false, json: false)
|
Bootsnap::CompileCache.setup(cache_dir: cache_dir, iseq: true, yaml: false, json: false)
|
||||||
|
|
||||||
if GC.respond_to?(:verify_compaction_references)
|
if GC.respond_to?(:verify_compaction_references)
|
||||||
|
@ -28,16 +29,16 @@ if GC.respond_to?(:verify_compaction_references)
|
||||||
end
|
end
|
||||||
|
|
||||||
module TestHandler
|
module TestHandler
|
||||||
def self.input_to_storage(_i, p)
|
def self.input_to_storage(_input, path)
|
||||||
'neato ' + p
|
"neato " + path
|
||||||
end
|
end
|
||||||
|
|
||||||
def self.storage_to_output(d, _a)
|
def self.storage_to_output(data, _kwargs)
|
||||||
d.upcase
|
data.upcase
|
||||||
end
|
end
|
||||||
|
|
||||||
def self.input_to_output(_d, _a)
|
def self.input_to_output(_data, _kwargs)
|
||||||
raise('but why tho')
|
raise("but why tho")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -67,7 +68,7 @@ module MiniTest
|
||||||
hash ^= fnv1a_64(args_key)
|
hash ^= fnv1a_64(args_key)
|
||||||
end
|
end
|
||||||
|
|
||||||
hex = hash.to_s(16).rjust(16, '0')
|
hex = hash.to_s(16).rjust(16, "0")
|
||||||
"#{dir}/#{hex[0..1]}/#{hex[2..-1]}"
|
"#{dir}/#{hex[0..1]}/#{hex[2..-1]}"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -95,7 +96,7 @@ module TmpdirHelper
|
||||||
def setup
|
def setup
|
||||||
super
|
super
|
||||||
@prev_dir = Dir.pwd
|
@prev_dir = Dir.pwd
|
||||||
@tmp_dir = Dir.mktmpdir('bootsnap-test')
|
@tmp_dir = Dir.mktmpdir("bootsnap-test")
|
||||||
Dir.chdir(@tmp_dir)
|
Dir.chdir(@tmp_dir)
|
||||||
@prev = Bootsnap::CompileCache::ISeq.cache_dir
|
@prev = Bootsnap::CompileCache::ISeq.cache_dir
|
||||||
Bootsnap::CompileCache::ISeq.cache_dir = @tmp_dir
|
Bootsnap::CompileCache::ISeq.cache_dir = @tmp_dir
|
||||||
|
|
|
@ -1,20 +1,21 @@
|
||||||
# frozen_string_literal: true
|
# frozen_string_literal: true
|
||||||
require('test_helper')
|
|
||||||
require('bootsnap/cli')
|
require("test_helper")
|
||||||
|
require("bootsnap/cli")
|
||||||
|
|
||||||
module Bootsnap
|
module Bootsnap
|
||||||
class WorkerPoolTestTest < Minitest::Test
|
class WorkerPoolTestTest < Minitest::Test
|
||||||
def test_dispatch
|
def test_dispatch
|
||||||
@pool = CLI::WorkerPool.create(size: 2, jobs: { touch: ->(path) { File.write(path, $$.to_s) } })
|
@pool = CLI::WorkerPool.create(size: 2, jobs: {touch: ->(path) { File.write(path, Process.pid.to_s) }})
|
||||||
@pool.spawn
|
@pool.spawn
|
||||||
|
|
||||||
Dir.mktmpdir('bootsnap-test') do |tmpdir|
|
Dir.mktmpdir("bootsnap-test") do |tmpdir|
|
||||||
10.times do |i|
|
10.times do |i|
|
||||||
@pool.push(:touch, File.join(tmpdir, i.to_s))
|
@pool.push(:touch, File.join(tmpdir, i.to_s))
|
||||||
end
|
end
|
||||||
|
|
||||||
@pool.shutdown
|
@pool.shutdown
|
||||||
files = Dir.chdir(tmpdir) { Dir['*'] }.sort
|
files = Dir.chdir(tmpdir) { Dir["*"] }.sort
|
||||||
assert_equal 10.times.map(&:to_s), files
|
assert_equal 10.times.map(&:to_s), files
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
Loading…
Reference in New Issue