Introduce UnpackStrategyImpl

This commit is contained in:
Douglas Eichelberger 2024-07-05 22:29:41 -07:00 committed by Issy Long
parent 0a18f77de4
commit 4ebf1116d7
31 changed files with 63 additions and 72 deletions

View File

@ -6,47 +6,27 @@ require "system_command"
# Module containing all available strategies for unpacking archives.
module UnpackStrategy
extend T::Helpers
include SystemCommand::Mixin
abstract!
# FIXME: Enable cop again when https://github.com/sorbet/sorbet/issues/3532 is fixed.
AnyStrategy = T.type_alias do # rubocop:disable Style/MutableConstant
T.any(
T.class_of(UnpackStrategy::Tar),
T.class_of(UnpackStrategy::Pax),
T.class_of(UnpackStrategy::Gzip),
T.class_of(UnpackStrategy::Dmg),
T.class_of(UnpackStrategy::Lzma),
T.class_of(UnpackStrategy::Xz),
T.class_of(UnpackStrategy::Zstd),
T.class_of(UnpackStrategy::Lzip),
T.class_of(UnpackStrategy::Air),
T.class_of(UnpackStrategy::Jar),
T.class_of(UnpackStrategy::LuaRock),
T.class_of(UnpackStrategy::MicrosoftOfficeXml),
T.class_of(UnpackStrategy::Zip),
T.class_of(UnpackStrategy::Pkg),
T.class_of(UnpackStrategy::Xar),
T.class_of(UnpackStrategy::Ttf),
T.class_of(UnpackStrategy::Otf),
T.class_of(UnpackStrategy::Git),
T.class_of(UnpackStrategy::Mercurial),
T.class_of(UnpackStrategy::Subversion),
T.class_of(UnpackStrategy::Cvs),
T.class_of(UnpackStrategy::SelfExtractingExecutable),
T.class_of(UnpackStrategy::Cab),
T.class_of(UnpackStrategy::Executable),
T.class_of(UnpackStrategy::Bzip2),
T.class_of(UnpackStrategy::Fossil),
T.class_of(UnpackStrategy::Bazaar),
T.class_of(UnpackStrategy::P7Zip),
T.class_of(UnpackStrategy::Sit),
T.class_of(UnpackStrategy::Rar),
T.class_of(UnpackStrategy::Lha),
)
# rubocop:disable Style/MutableConstant
UnpackStrategyImpl = T.type_alias { T.all(T::Class[UnpackStrategy], UnpackStrategy::ClassMethods) }
# rubocop:enable Style/MutableConstant
module ClassMethods
extend T::Helpers
abstract!
sig { abstract.returns(T::Array[String]) }
def extensions; end
sig { abstract.params(path: Pathname).returns(T::Boolean) }
def can_extract?(path); end
end
include SystemCommand::Mixin
mixes_in_class_methods(ClassMethods)
sig { returns(T.nilable(T::Array[AnyStrategy])) }
sig { returns(T.nilable(T::Array[UnpackStrategyImpl])) }
def self.strategies
@strategies ||= T.let([
Tar, # Needs to be before Bzip2/Gzip/Xz/Lzma/Zstd.
@ -81,11 +61,11 @@ module UnpackStrategy
Sit,
Rar,
Lha,
].freeze, T.nilable(T::Array[AnyStrategy]))
].freeze, T.nilable(T::Array[UnpackStrategyImpl]))
end
private_class_method :strategies
sig { params(type: Symbol).returns(T.nilable(T.any(T.class_of(UnpackStrategy::Uncompressed), AnyStrategy))) }
sig { params(type: Symbol).returns(T.nilable(UnpackStrategyImpl)) }
def self.from_type(type)
type = {
naked: :uncompressed,
@ -100,7 +80,7 @@ module UnpackStrategy
end
end
sig { params(extension: String).returns(T.nilable(AnyStrategy)) }
sig { params(extension: String).returns(T.nilable(UnpackStrategyImpl)) }
def self.from_extension(extension)
return unless strategies
@ -109,7 +89,7 @@ module UnpackStrategy
&.find { |s| s.extensions.any? { |ext| extension.end_with?(ext) } }
end
sig { params(path: Pathname).returns(T.nilable(AnyStrategy)) }
sig { params(path: Pathname).returns(T.nilable(UnpackStrategyImpl)) }
def self.from_magic(path)
strategies&.find { |s| s.can_extract?(path) }
end
@ -152,7 +132,6 @@ module UnpackStrategy
@merge_xattrs = merge_xattrs
end
abstract!
sig { abstract.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).void }
def extract_to_dir(unpack_dir, basename:, verbose:); end
private :extract_to_dir

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Air
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".air"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Bzip2
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".bz2"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Cab
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".cab"]
end

View File

@ -6,7 +6,7 @@ require_relative "tar"
module UnpackStrategy
# Strategy for unpacking compress archives.
class Compress < Tar
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".Z"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Directory
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[]
end

View File

@ -121,6 +121,12 @@ module UnpackStrategy
end
end
sig { override.returns(T::Array[String]) }
def self.extensions = []
sig { override.params(_path: Pathname).returns(T::Boolean) }
def self.can_extract?(_path) = false
private
sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
@ -165,7 +171,7 @@ module UnpackStrategy
end
private_constant :Mount
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".dmg"]
end

View File

@ -6,7 +6,7 @@ require_relative "uncompressed"
module UnpackStrategy
# Strategy for unpacking executables.
class Executable < Uncompressed
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".sh", ".bash"]
end

View File

@ -9,7 +9,7 @@ module UnpackStrategy
include UnpackStrategy
extend SystemCommand::Mixin
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class GenericUnar
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Gzip
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".gz"]
end

View File

@ -6,7 +6,7 @@ require_relative "uncompressed"
module UnpackStrategy
# Strategy for unpacking Java archives.
class Jar < Uncompressed
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".apk", ".jar"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Lha
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".lha", ".lzh"]
end

View File

@ -6,7 +6,7 @@ require_relative "uncompressed"
module UnpackStrategy
# Strategy for unpacking LuaRock archives.
class LuaRock < Uncompressed
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".rock"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Lzip
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".lz"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Lzma
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".lzma"]
end

View File

@ -6,7 +6,7 @@ require_relative "uncompressed"
module UnpackStrategy
# Strategy for unpacking Microsoft Office documents.
class MicrosoftOfficeXml < Uncompressed
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[
".doc", ".docx",

View File

@ -6,7 +6,7 @@ require_relative "uncompressed"
module UnpackStrategy
# Strategy for unpacking OpenType fonts.
class Otf < Uncompressed
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".otf"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class P7Zip
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".7z"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Pax
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".pax"]
end

View File

@ -6,7 +6,7 @@ require_relative "uncompressed"
module UnpackStrategy
# Strategy for unpacking macOS package installers.
class Pkg < Uncompressed
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".pkg", ".mkpg"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Rar
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".rar"]
end

View File

@ -6,7 +6,7 @@ require_relative "generic_unar"
module UnpackStrategy
# Strategy for unpacking self-extracting executables.
class SelfExtractingExecutable < GenericUnar
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[]
end

View File

@ -6,7 +6,7 @@ require_relative "generic_unar"
module UnpackStrategy
# Strategy for unpacking Stuffit archives.
class Sit < GenericUnar
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".sit"]
end

View File

@ -9,7 +9,7 @@ module UnpackStrategy
include UnpackStrategy
extend SystemCommand::Mixin
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[
".tar",

View File

@ -6,7 +6,7 @@ require_relative "uncompressed"
module UnpackStrategy
# Strategy for unpacking TrueType fonts.
class Ttf < Uncompressed
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".ttc", ".ttf"]
end

View File

@ -6,6 +6,12 @@ module UnpackStrategy
class Uncompressed
include UnpackStrategy
sig { override.returns(T::Array[String]) }
def self.extensions = []
sig { override.params(_path: Pathname).returns(T::Boolean) }
def self.can_extract?(_path) = false
sig {
params(
to: T.nilable(Pathname),

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Xar
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".xar"]
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Xz
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".xz"]
end

View File

@ -6,12 +6,12 @@ module UnpackStrategy
class Zip
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".zip"]
end
sig { params(path: Pathname).returns(T::Boolean) }
sig { override.params(path: Pathname).returns(T::Boolean) }
def self.can_extract?(path)
path.magic_number.match?(/\APK(\003\004|\005\006)/n)
end

View File

@ -6,7 +6,7 @@ module UnpackStrategy
class Zstd
include UnpackStrategy
sig { returns(T::Array[String]) }
sig { override.returns(T::Array[String]) }
def self.extensions
[".zst"]
end