rom-files 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.editorconfig +9 -0
- data/.gitignore +11 -0
- data/.rspec +3 -0
- data/.rubocop.yml +112 -0
- data/.rubocop_todo.yml +7 -0
- data/.ruby-version +1 -0
- data/.simplecov +6 -0
- data/.travis.yml +24 -0
- data/.yardopts +6 -0
- data/CHANGELOG.md +10 -0
- data/Gemfile +25 -0
- data/Guardfile +48 -0
- data/LICENSE.md +21 -0
- data/README.md +44 -0
- data/Rakefile +37 -0
- data/Roadmap.taskpaper +44 -0
- data/bin/_guard-core +21 -0
- data/bin/console +7 -0
- data/bin/guard +21 -0
- data/bin/rake +21 -0
- data/bin/rspec +21 -0
- data/bin/yard +21 -0
- data/bin/yardoc +21 -0
- data/bin/yri +21 -0
- data/lib/dry/types/pathname.rb +25 -0
- data/lib/pathname/extensions.rb +32 -0
- data/lib/pathname/extensions/constants.rb +12 -0
- data/lib/pathname/extensions/explode.rb +27 -0
- data/lib/pathname/extensions/ext.rb +28 -0
- data/lib/pathname/extensions/partial.rb +30 -0
- data/lib/pathname/extensions/pathmap.rb +128 -0
- data/lib/rom-files.rb +3 -0
- data/lib/rom/files.rb +28 -0
- data/lib/rom/files/associations.rb +6 -0
- data/lib/rom/files/associations/many_to_many.rb +12 -0
- data/lib/rom/files/associations/many_to_one.rb +12 -0
- data/lib/rom/files/associations/one_to_many.rb +12 -0
- data/lib/rom/files/associations/one_to_one.rb +12 -0
- data/lib/rom/files/attribute.rb +21 -0
- data/lib/rom/files/commands/create.rb +18 -0
- data/lib/rom/files/commands/delete.rb +17 -0
- data/lib/rom/files/commands/update.rb +17 -0
- data/lib/rom/files/connection.rb +120 -0
- data/lib/rom/files/constants.rb +16 -0
- data/lib/rom/files/dataset.rb +89 -0
- data/lib/rom/files/dataset/filtering.rb +96 -0
- data/lib/rom/files/dataset/mime_type.rb +44 -0
- data/lib/rom/files/dataset/paths.rb +79 -0
- data/lib/rom/files/dataset/sorting.rb +27 -0
- data/lib/rom/files/extensions.rb +30 -0
- data/lib/rom/files/extensions/gem.rb +29 -0
- data/lib/rom/files/extensions/gem/relations/documentations.rb +18 -0
- data/lib/rom/files/extensions/gem/relations/executables.rb +20 -0
- data/lib/rom/files/extensions/gem/relations/implementations.rb +29 -0
- data/lib/rom/files/extensions/gem/relations/specifications.rb +29 -0
- data/lib/rom/files/extensions/markdown/attributes_inferrer.rb +20 -0
- data/lib/rom/files/extensions/markdown/types.rb +18 -0
- data/lib/rom/files/extensions/markup/attributes_inferrer.rb +32 -0
- data/lib/rom/files/extensions/ruby/attributes_inferrer.rb +21 -0
- data/lib/rom/files/extensions/ruby/types.rb +45 -0
- data/lib/rom/files/extensions/text/attributes_inferrer.rb +20 -0
- data/lib/rom/files/gateway.rb +63 -0
- data/lib/rom/files/plugins/configuration/gem.rb +30 -0
- data/lib/rom/files/plugins/relation/instrumentation.rb +28 -0
- data/lib/rom/files/plugins/schema/contents.rb +72 -0
- data/lib/rom/files/plugins/schema/mime.rb +59 -0
- data/lib/rom/files/plugins/schema/shebang.rb +79 -0
- data/lib/rom/files/plugins/schema/stat.rb +108 -0
- data/lib/rom/files/relation.rb +143 -0
- data/lib/rom/files/schema.rb +77 -0
- data/lib/rom/files/schema/attributes_inferrer.rb +79 -0
- data/lib/rom/files/schema/inferrer.rb +36 -0
- data/lib/rom/files/types.rb +37 -0
- data/lib/rom/files/version.rb +7 -0
- data/rom-files.gemspec +48 -0
- data/spec/integration/rom/files/gateway_spec.rb +28 -0
- data/spec/integration/rom/files/gem_spec.rb +98 -0
- data/spec/integration/rom/files/relations_spec.rb +63 -0
- data/spec/integration/rom/files/schema/inferrer_spec.rb +77 -0
- data/spec/lib/dry/types/pathname_spec.rb +50 -0
- data/spec/lib/pathname/extensions/explode_spec.rb +25 -0
- data/spec/lib/pathname/extensions/ext_spec.rb +33 -0
- data/spec/lib/pathname/extensions/partial_spec.rb +17 -0
- data/spec/lib/pathname/extensions/pathmap_spec.rb +147 -0
- data/spec/lib/rom/files/attribute_spec.rb +43 -0
- data/spec/lib/rom/files/connection_spec.rb +76 -0
- data/spec/lib/rom/files/dataset/inside_spec.rb +22 -0
- data/spec/lib/rom/files/dataset/mime_type_spec.rb +23 -0
- data/spec/lib/rom/files/dataset/recursive_question_mark_spec.rb +42 -0
- data/spec/lib/rom/files/dataset/recursive_spec.rb +29 -0
- data/spec/lib/rom/files/dataset/reject_append_spec.rb +68 -0
- data/spec/lib/rom/files/dataset/reject_spec.rb +26 -0
- data/spec/lib/rom/files/dataset/select_append_spec.rb +69 -0
- data/spec/lib/rom/files/dataset/select_spec.rb +38 -0
- data/spec/lib/rom/files/dataset/sort_spec.rb +22 -0
- data/spec/lib/rom/files/dataset_spec.rb +52 -0
- data/spec/lib/rom/files/extensions/text/attributes_inferrer_spec.rb +54 -0
- data/spec/lib/rom/files/gateway_spec.rb +39 -0
- data/spec/lib/rom/files/plugins/schema/contents_spec.rb +66 -0
- data/spec/lib/rom/files/plugins/schema/mime_spec.rb +66 -0
- data/spec/lib/rom/files/plugins/schema/stat_spec.rb +109 -0
- data/spec/lib/rom/files/relation/pluck_spec.rb +20 -0
- data/spec/lib/rom/files/relation/reject_spec.rb +22 -0
- data/spec/lib/rom/files/relation/select_spec.rb +35 -0
- data/spec/lib/rom/files/relation/sort_spec.rb +21 -0
- data/spec/lib/rom/files/relation/to_a_spec.rb +39 -0
- data/spec/lib/rom/files/relation_spec.rb +10 -0
- data/spec/lib/rom/files/schema/attributes_inferrer_spec.rb +45 -0
- data/spec/lib/rom/files/schema/inferrer_spec.rb +29 -0
- data/spec/lib/rom/files/schema_spec.rb +109 -0
- data/spec/lib/rom/files/types/mime_type_spec.rb +9 -0
- data/spec/lib/rom/files/types/path_spec.rb +10 -0
- data/spec/lib/rom/files/types_spec.rb +6 -0
- data/spec/shared/rom/files/files_setup.rb +19 -0
- data/spec/shared/rom/files/filesystem_setup.rb +10 -0
- data/spec/shared/rom/files/gateway_setup.rb +17 -0
- data/spec/shared/rom/files/media_dataset.rb +10 -0
- data/spec/shared/rom/files/media_files.rb +17 -0
- data/spec/shared/rom/files/media_relation.rb +30 -0
- data/spec/spec_helper.rb +10 -0
- metadata +421 -0
data/bin/console
ADDED
data/bin/guard
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
#
|
|
5
|
+
# This file was generated by Bundler.
|
|
6
|
+
#
|
|
7
|
+
# The application 'guard' is installed as part of a gem, and
|
|
8
|
+
# this file is here to facilitate running it.
|
|
9
|
+
#
|
|
10
|
+
|
|
11
|
+
bundle_binstub = File.expand_path("../bundle", __FILE__)
|
|
12
|
+
load(bundle_binstub) if File.file?(bundle_binstub)
|
|
13
|
+
|
|
14
|
+
require "pathname"
|
|
15
|
+
ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../../Gemfile",
|
|
16
|
+
Pathname.new(__FILE__).realpath)
|
|
17
|
+
|
|
18
|
+
require "rubygems"
|
|
19
|
+
require "bundler/setup"
|
|
20
|
+
|
|
21
|
+
load Gem.bin_path("guard", "guard")
|
data/bin/rake
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
#
|
|
5
|
+
# This file was generated by Bundler.
|
|
6
|
+
#
|
|
7
|
+
# The application 'rake' is installed as part of a gem, and
|
|
8
|
+
# this file is here to facilitate running it.
|
|
9
|
+
#
|
|
10
|
+
|
|
11
|
+
bundle_binstub = File.expand_path("../bundle", __FILE__)
|
|
12
|
+
load(bundle_binstub) if File.file?(bundle_binstub)
|
|
13
|
+
|
|
14
|
+
require "pathname"
|
|
15
|
+
ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../../Gemfile",
|
|
16
|
+
Pathname.new(__FILE__).realpath)
|
|
17
|
+
|
|
18
|
+
require "rubygems"
|
|
19
|
+
require "bundler/setup"
|
|
20
|
+
|
|
21
|
+
load Gem.bin_path("rake", "rake")
|
data/bin/rspec
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
#
|
|
5
|
+
# This file was generated by Bundler.
|
|
6
|
+
#
|
|
7
|
+
# The application 'rspec' is installed as part of a gem, and
|
|
8
|
+
# this file is here to facilitate running it.
|
|
9
|
+
#
|
|
10
|
+
|
|
11
|
+
bundle_binstub = File.expand_path("../bundle", __FILE__)
|
|
12
|
+
load(bundle_binstub) if File.file?(bundle_binstub)
|
|
13
|
+
|
|
14
|
+
require "pathname"
|
|
15
|
+
ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../../Gemfile",
|
|
16
|
+
Pathname.new(__FILE__).realpath)
|
|
17
|
+
|
|
18
|
+
require "rubygems"
|
|
19
|
+
require "bundler/setup"
|
|
20
|
+
|
|
21
|
+
load Gem.bin_path("rspec-core", "rspec")
|
data/bin/yard
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
#
|
|
5
|
+
# This file was generated by Bundler.
|
|
6
|
+
#
|
|
7
|
+
# The application 'yard' is installed as part of a gem, and
|
|
8
|
+
# this file is here to facilitate running it.
|
|
9
|
+
#
|
|
10
|
+
|
|
11
|
+
bundle_binstub = File.expand_path("../bundle", __FILE__)
|
|
12
|
+
load(bundle_binstub) if File.file?(bundle_binstub)
|
|
13
|
+
|
|
14
|
+
require "pathname"
|
|
15
|
+
ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../../Gemfile",
|
|
16
|
+
Pathname.new(__FILE__).realpath)
|
|
17
|
+
|
|
18
|
+
require "rubygems"
|
|
19
|
+
require "bundler/setup"
|
|
20
|
+
|
|
21
|
+
load Gem.bin_path("yard", "yard")
|
data/bin/yardoc
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
#
|
|
5
|
+
# This file was generated by Bundler.
|
|
6
|
+
#
|
|
7
|
+
# The application 'yardoc' is installed as part of a gem, and
|
|
8
|
+
# this file is here to facilitate running it.
|
|
9
|
+
#
|
|
10
|
+
|
|
11
|
+
bundle_binstub = File.expand_path("../bundle", __FILE__)
|
|
12
|
+
load(bundle_binstub) if File.file?(bundle_binstub)
|
|
13
|
+
|
|
14
|
+
require "pathname"
|
|
15
|
+
ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../../Gemfile",
|
|
16
|
+
Pathname.new(__FILE__).realpath)
|
|
17
|
+
|
|
18
|
+
require "rubygems"
|
|
19
|
+
require "bundler/setup"
|
|
20
|
+
|
|
21
|
+
load Gem.bin_path("yard", "yardoc")
|
data/bin/yri
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
#
|
|
5
|
+
# This file was generated by Bundler.
|
|
6
|
+
#
|
|
7
|
+
# The application 'yri' is installed as part of a gem, and
|
|
8
|
+
# this file is here to facilitate running it.
|
|
9
|
+
#
|
|
10
|
+
|
|
11
|
+
bundle_binstub = File.expand_path("../bundle", __FILE__)
|
|
12
|
+
load(bundle_binstub) if File.file?(bundle_binstub)
|
|
13
|
+
|
|
14
|
+
require "pathname"
|
|
15
|
+
ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../../Gemfile",
|
|
16
|
+
Pathname.new(__FILE__).realpath)
|
|
17
|
+
|
|
18
|
+
require "rubygems"
|
|
19
|
+
require "bundler/setup"
|
|
20
|
+
|
|
21
|
+
load Gem.bin_path("yard", "yri")
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'dry-types'
|
|
4
|
+
require 'dry/types/core'
|
|
5
|
+
require 'pathname'
|
|
6
|
+
|
|
7
|
+
module Dry
|
|
8
|
+
module Types
|
|
9
|
+
def self.register_if_needed(key, value)
|
|
10
|
+
register(key, value) unless registered?(key)
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def self.Pathname(path)
|
|
14
|
+
path.is_a?(Pathname) ? path : Kernel::Pathname(path.to_s)
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
register_if_needed 'pathname', simple = Definition[Pathname].new(Pathname)
|
|
18
|
+
register_if_needed 'strict.pathname', strict = simple.constrained(type: Pathname)
|
|
19
|
+
register_if_needed 'coercible.pathname',
|
|
20
|
+
coercible = simple.constructor(method(:Pathname))
|
|
21
|
+
register_if_needed 'optional.pathname', simple.optional
|
|
22
|
+
register_if_needed 'optional.strict.pathname', strict.optional
|
|
23
|
+
register_if_needed 'optional.coercible.pathname', coercible.optional
|
|
24
|
+
end
|
|
25
|
+
end
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'pathname'
|
|
4
|
+
require 'dry/core/extensions'
|
|
5
|
+
|
|
6
|
+
class Pathname
|
|
7
|
+
extend Dry::Core::Extensions
|
|
8
|
+
|
|
9
|
+
register_extension :constants do
|
|
10
|
+
require_relative 'extensions/constants'
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
register_extension :explode do
|
|
14
|
+
require_relative 'extensions/explode'
|
|
15
|
+
include Extensions::Explode
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
register_extension :ext do
|
|
19
|
+
require_relative 'extensions/ext'
|
|
20
|
+
include Extensions::Ext
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
register_extension :partial do
|
|
24
|
+
require_relative 'extensions/partial'
|
|
25
|
+
include Extensions::Partial
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
register_extension :pathmap do
|
|
29
|
+
require_relative 'extensions/pathmap'
|
|
30
|
+
include Extensions::Pathmap
|
|
31
|
+
end
|
|
32
|
+
end
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'pathname/extensions'
|
|
4
|
+
|
|
5
|
+
class Pathname
|
|
6
|
+
module Extensions
|
|
7
|
+
module Explode
|
|
8
|
+
def self.included(host)
|
|
9
|
+
super
|
|
10
|
+
host.load_extensions :constants
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
# Explode a path into individual components
|
|
14
|
+
#
|
|
15
|
+
# @return [Array<Pathname>]
|
|
16
|
+
#
|
|
17
|
+
# @see Pathmap#pathmap Used by `#pathmap`
|
|
18
|
+
def explode
|
|
19
|
+
head, tail = split
|
|
20
|
+
return [self] if head == self
|
|
21
|
+
return [tail] if head == HERE || tail == ROOT
|
|
22
|
+
return [head, tail] if head == ROOT
|
|
23
|
+
head.explode + [tail]
|
|
24
|
+
end
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
end
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'pathname/extensions'
|
|
4
|
+
|
|
5
|
+
class Pathname
|
|
6
|
+
module Extensions
|
|
7
|
+
# Changes extension of file
|
|
8
|
+
module Ext
|
|
9
|
+
def self.included(host)
|
|
10
|
+
host.load_extensions :constants
|
|
11
|
+
super
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
# Replace the file extension with +new_extension+.
|
|
15
|
+
# If there is no extension on the string, append the new extension to the end.
|
|
16
|
+
# If the new extension is not given, or is the empty string, remove any existing extension.
|
|
17
|
+
# @param new_extension [String]
|
|
18
|
+
# @return [Pathname]
|
|
19
|
+
def ext(new_extension = EMPTY_STRING)
|
|
20
|
+
return dup if [HERE, UPPER].include? self
|
|
21
|
+
unless new_extension == EMPTY_STRING
|
|
22
|
+
new_extension = '.' + new_extension unless new_extension.match?(/^\./)
|
|
23
|
+
end
|
|
24
|
+
sub_ext(new_extension)
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
end
|
|
28
|
+
end
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'pathname/extensions'
|
|
4
|
+
|
|
5
|
+
class Pathname
|
|
6
|
+
module Extensions
|
|
7
|
+
module Partial
|
|
8
|
+
def self.included(host)
|
|
9
|
+
host.load_extensions :explode
|
|
10
|
+
super
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
# Extract a partial path from the path. Include +n+ directories from the
|
|
14
|
+
# front end (left hand side) if +n+ is positive. Include |+n+|
|
|
15
|
+
# directories from the back end (right hand side) if +n+ is negative.
|
|
16
|
+
def partial(n)
|
|
17
|
+
dirs = dirname.explode
|
|
18
|
+
partial_dirs =
|
|
19
|
+
if n.positive?
|
|
20
|
+
dirs[0...n]
|
|
21
|
+
elsif n.negative?
|
|
22
|
+
dirs.reverse[0...-n].reverse
|
|
23
|
+
else
|
|
24
|
+
HERE
|
|
25
|
+
end
|
|
26
|
+
Pathname(File.join(partial_dirs))
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
end
|
|
30
|
+
end
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'pathname/extensions'
|
|
4
|
+
|
|
5
|
+
class Pathname
|
|
6
|
+
module Extensions
|
|
7
|
+
module Pathmap
|
|
8
|
+
def self.included(host)
|
|
9
|
+
host.load_extensions :ext, :explode, :partial
|
|
10
|
+
super
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
# Map the path according to the given specification. The specification
|
|
14
|
+
# controls the details of the mapping. The following special patterns are
|
|
15
|
+
# recognized:
|
|
16
|
+
#
|
|
17
|
+
# * `%p` - The complete path.
|
|
18
|
+
# * `%f` - The base file name of the path, with its file extension,
|
|
19
|
+
# but without any directories.
|
|
20
|
+
# * `%n` - The file name of the path without its file extension.
|
|
21
|
+
# * `%d` - The directory list of the path.
|
|
22
|
+
# * `%x` - The file extension of the path. An empty string if there
|
|
23
|
+
# is no extension.
|
|
24
|
+
# * `%X` - Everything *but* the file extension.
|
|
25
|
+
# * `%s` - The alternate file separator if defined, otherwise use #
|
|
26
|
+
# the standard file separator.
|
|
27
|
+
# * `%%` - A percent sign.
|
|
28
|
+
#
|
|
29
|
+
# @note
|
|
30
|
+
# The `%d` specifier can also have a numeric prefix (e.g. `%2d`).
|
|
31
|
+
#
|
|
32
|
+
# If the number is positive, only return (up to) `n` directories in the
|
|
33
|
+
# path, starting from the left hand side.
|
|
34
|
+
#
|
|
35
|
+
# If `n` is negative, return (up to) `n` directories from the
|
|
36
|
+
# right hand side of the path.
|
|
37
|
+
#
|
|
38
|
+
# @example
|
|
39
|
+
# 'a/b/c/d/file.txt'.pathmap("%2d") => 'a/b'
|
|
40
|
+
# 'a/b/c/d/file.txt'.pathmap("%-2d") => 'c/d'
|
|
41
|
+
#
|
|
42
|
+
# Also the `%d`, `%p`, `%f`, `%n`,
|
|
43
|
+
# `%x`, and `%X` operators can take a pattern/replacement
|
|
44
|
+
# argument to perform simple string substitutions on a particular part of
|
|
45
|
+
# the path. The pattern and replacement are separated by a comma and are
|
|
46
|
+
# enclosed by curly braces. The replacement spec comes after the %
|
|
47
|
+
# character but before the operator letter. (e.g. `%{old,new}d`).
|
|
48
|
+
# Multiple replacement specs should be separated by semi-colons (e.g.
|
|
49
|
+
# `%{old,new;src,bin}d`).
|
|
50
|
+
#
|
|
51
|
+
# Regular expressions may be used for the pattern, and back refs may be
|
|
52
|
+
# used in the replacement text. Curly braces, commas and semi-colons are
|
|
53
|
+
# excluded from both the pattern and replacement text (let's keep parsing
|
|
54
|
+
# reasonable).
|
|
55
|
+
#
|
|
56
|
+
# @example
|
|
57
|
+
# "src/org/onestepback/proj/A.java".pathmap("%{^src,class}X.class")
|
|
58
|
+
# #=> "class/org/onestepback/proj/A.class"
|
|
59
|
+
#
|
|
60
|
+
#
|
|
61
|
+
# @example If the replacement text is '*', then a block may be provided to perform some arbitrary calculation for the replacement.
|
|
62
|
+
# "/path/to/file.TXT".pathmap("%X%{.*,*}x") { |ext|
|
|
63
|
+
# ext.downcase
|
|
64
|
+
# } #=> "/path/to/file.txt"
|
|
65
|
+
def pathmap(spec = nil, &block)
|
|
66
|
+
return self if spec.nil?
|
|
67
|
+
result = +''
|
|
68
|
+
# noinspection SpellCheckingInspection
|
|
69
|
+
spec.scan(/%\{[^}]*\}-?\d*[sdpfnxX%]|%-?\d+d|%.|[^%]+/) do |frag|
|
|
70
|
+
# noinspection SpellCheckingInspection
|
|
71
|
+
case frag
|
|
72
|
+
when '%f'
|
|
73
|
+
result << basename.to_s
|
|
74
|
+
when '%n'
|
|
75
|
+
result << basename.ext.to_s
|
|
76
|
+
when '%d'
|
|
77
|
+
result << dirname.to_s
|
|
78
|
+
when '%x'
|
|
79
|
+
result << extname.to_s
|
|
80
|
+
when '%X'
|
|
81
|
+
result << ext.to_s
|
|
82
|
+
when '%p'
|
|
83
|
+
result << to_s
|
|
84
|
+
when '%s'
|
|
85
|
+
result << (File::ALT_SEPARATOR || File::SEPARATOR)
|
|
86
|
+
when '%-'
|
|
87
|
+
result
|
|
88
|
+
when '%%'
|
|
89
|
+
result << '%'
|
|
90
|
+
when /%(-?\d+)d/
|
|
91
|
+
result << partial(Regexp.last_match(1).to_i).to_s
|
|
92
|
+
when /^%{([^}]*)}(\d*[dpfnxX])/
|
|
93
|
+
patterns = Regexp.last_match(1)
|
|
94
|
+
operator = Regexp.last_match(2)
|
|
95
|
+
result << pathmap('%' + operator).pathmap_replace(patterns, &block).to_s
|
|
96
|
+
when /^%/
|
|
97
|
+
raise ArgumentError, "Unknown pathmap specifier #{frag} in '#{spec}'"
|
|
98
|
+
else
|
|
99
|
+
result << frag
|
|
100
|
+
end
|
|
101
|
+
end
|
|
102
|
+
Pathname(result)
|
|
103
|
+
end
|
|
104
|
+
|
|
105
|
+
# Perform the pathmap replacement operations on the given path. The
|
|
106
|
+
# patterns take the form 'pat1,rep1;pat2,rep2...'.
|
|
107
|
+
#
|
|
108
|
+
# @param patterns [String]
|
|
109
|
+
# @param block [Proc]
|
|
110
|
+
# @return [Pathname]
|
|
111
|
+
def pathmap_replace(patterns, &block)
|
|
112
|
+
result = self
|
|
113
|
+
patterns.split(';').each do |pair|
|
|
114
|
+
pattern, replacement = pair.split(',')
|
|
115
|
+
pattern = Regexp.new(pattern)
|
|
116
|
+
result = if replacement == '*' && block_given?
|
|
117
|
+
result.sub(pattern, &block)
|
|
118
|
+
elsif replacement
|
|
119
|
+
result.sub(pattern, replacement)
|
|
120
|
+
else
|
|
121
|
+
result.sub(pattern, '')
|
|
122
|
+
end
|
|
123
|
+
end
|
|
124
|
+
result
|
|
125
|
+
end
|
|
126
|
+
end
|
|
127
|
+
end
|
|
128
|
+
end
|
data/lib/rom-files.rb
ADDED
data/lib/rom/files.rb
ADDED
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'dry/types/pathname'
|
|
4
|
+
require 'rom'
|
|
5
|
+
|
|
6
|
+
require 'rom/files/version'
|
|
7
|
+
require 'rom/files/gateway'
|
|
8
|
+
require 'rom/files/relation'
|
|
9
|
+
|
|
10
|
+
ROM.register_adapter :files, ROM::Files
|
|
11
|
+
|
|
12
|
+
require 'rom/files/plugins/relation/instrumentation'
|
|
13
|
+
require 'rom/files/plugins/schema/contents'
|
|
14
|
+
require 'rom/files/plugins/schema/mime'
|
|
15
|
+
require 'rom/files/plugins/schema/shebang'
|
|
16
|
+
require 'rom/files/plugins/schema/stat'
|
|
17
|
+
require 'rom/files/plugins/configuration/gem'
|
|
18
|
+
|
|
19
|
+
ROM.plugins do
|
|
20
|
+
adapter :files do
|
|
21
|
+
register :instrumentation, ROM::Files::Plugins::Relation::Instrumentation, type: :relation
|
|
22
|
+
register :contents, ROM::Files::Plugins::Schema::Contents, type: :schema
|
|
23
|
+
register :mime, ROM::Files::Plugins::Schema::Mime, type: :schema
|
|
24
|
+
register :shebang, ROM::Files::Plugins::Schema::Shebang, type: :schema
|
|
25
|
+
register :stat, ROM::Files::Plugins::Schema::Stat, type: :schema
|
|
26
|
+
end
|
|
27
|
+
register :gem, ROM::Files::Plugins::Configuration::Gem, type: :configuration
|
|
28
|
+
end
|