workspace 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.circleci/config.yml +11 -0
- data/.gitignore +4 -0
- data/.rspec +8 -0
- data/.rubocop.yml +193 -0
- data/Gemfile +3 -0
- data/README.md +50 -0
- data/lib/workspace.rb +22 -0
- data/lib/workspace/dir.rb +108 -0
- data/lib/workspace/file.rb +102 -0
- data/lib/workspace/version.rb +3 -0
- data/spec/spec_helper.rb +8 -0
- data/spec/workspace/dir_spec.rb +120 -0
- data/spec/workspace/file_spec.rb +97 -0
- data/spec/workspace_spec.rb +24 -0
- data/workspace.gemspec +27 -0
- metadata +163 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: '0820d45a42fc51c68fe25a77e024015511f6c817'
|
4
|
+
data.tar.gz: c6fdef4a4e5b687e706fab4aeba2b0870c0e458d
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: fe590c87851b4d6d571cd06d028f82c110c4acb6a7c9e602754120a55067bb5d1abe5e209b3e06eb4607d77e4f7d9c18ceed7ba2d274eece5f0b1a6c52ead6bb
|
7
|
+
data.tar.gz: b7eb61ba2f04148ef66d23d6517b2332c1b07237d19add8fc0cfc428949f073e84152c3be5b34e90f59b6a77ce2a2492fc410d3c1bf5d1f66f409adc1f1d7f59
|
data/.gitignore
ADDED
data/.rspec
ADDED
data/.rubocop.yml
ADDED
@@ -0,0 +1,193 @@
|
|
1
|
+
Style/SymbolArray:
|
2
|
+
Enabled: true
|
3
|
+
EnforcedStyle: brackets
|
4
|
+
|
5
|
+
# kind_of? is a good way to check a type
|
6
|
+
Style/ClassCheck:
|
7
|
+
EnforcedStyle: kind_of?
|
8
|
+
|
9
|
+
# It's better to be more explicit about the type
|
10
|
+
Style/BracesAroundHashParameters:
|
11
|
+
Enabled: false
|
12
|
+
|
13
|
+
Style/TernaryParentheses:
|
14
|
+
Enabled: true
|
15
|
+
EnforcedStyle: require_parentheses_when_complex
|
16
|
+
|
17
|
+
# specs sometimes have useless assignments, which is fine
|
18
|
+
Lint/UselessAssignment:
|
19
|
+
Exclude:
|
20
|
+
- '**/spec/**/*'
|
21
|
+
|
22
|
+
# We could potentially enable the 2 below:
|
23
|
+
Layout/IndentHash:
|
24
|
+
Enabled: false
|
25
|
+
|
26
|
+
Layout/AlignHash:
|
27
|
+
Enabled: false
|
28
|
+
|
29
|
+
# HoundCI doesn't like this rule
|
30
|
+
Layout/DotPosition:
|
31
|
+
Enabled: false
|
32
|
+
|
33
|
+
# We allow !! as it's an easy way to convert ot boolean
|
34
|
+
Style/DoubleNegation:
|
35
|
+
Enabled: false
|
36
|
+
|
37
|
+
Style/NumericPredicate:
|
38
|
+
Enabled: false
|
39
|
+
|
40
|
+
# Sometimes we allow a rescue block that doesn't contain code
|
41
|
+
Lint/HandleExceptions:
|
42
|
+
Enabled: false
|
43
|
+
|
44
|
+
# Cop supports --auto-correct.
|
45
|
+
Lint/UnusedBlockArgument:
|
46
|
+
Enabled: false
|
47
|
+
|
48
|
+
# Needed for $verbose
|
49
|
+
Style/GlobalVars:
|
50
|
+
Enabled: false
|
51
|
+
|
52
|
+
# We want to allow class Fastlane::Class
|
53
|
+
Style/ClassAndModuleChildren:
|
54
|
+
Enabled: false
|
55
|
+
|
56
|
+
# $? Exit
|
57
|
+
Style/SpecialGlobalVars:
|
58
|
+
Enabled: false
|
59
|
+
|
60
|
+
Metrics/AbcSize:
|
61
|
+
Enabled: false
|
62
|
+
|
63
|
+
Metrics/MethodLength:
|
64
|
+
Enabled: false
|
65
|
+
|
66
|
+
Metrics/ModuleLength:
|
67
|
+
Enabled: true
|
68
|
+
Max: 110
|
69
|
+
|
70
|
+
Metrics/CyclomaticComplexity:
|
71
|
+
Enabled: false
|
72
|
+
|
73
|
+
Metrics/BlockNesting:
|
74
|
+
Max: 4
|
75
|
+
|
76
|
+
Metrics/BlockLength:
|
77
|
+
Enabled: false
|
78
|
+
|
79
|
+
# The %w might be confusing for new users
|
80
|
+
Style/WordArray:
|
81
|
+
MinSize: 19
|
82
|
+
|
83
|
+
# raise and fail are both okay
|
84
|
+
Style/SignalException:
|
85
|
+
Enabled: false
|
86
|
+
|
87
|
+
# Better too much 'return' than one missing
|
88
|
+
Style/RedundantReturn:
|
89
|
+
Enabled: false
|
90
|
+
|
91
|
+
# Having if in the same line might not always be good
|
92
|
+
Style/IfUnlessModifier:
|
93
|
+
Enabled: false
|
94
|
+
|
95
|
+
# and and or is okay
|
96
|
+
Style/AndOr:
|
97
|
+
Enabled: false
|
98
|
+
|
99
|
+
# Configuration parameters: CountComments.
|
100
|
+
Metrics/ClassLength:
|
101
|
+
Max: 400
|
102
|
+
|
103
|
+
# Configuration parameters: AllowURI, URISchemes.
|
104
|
+
Metrics/LineLength:
|
105
|
+
Enabled: false
|
106
|
+
Max: 370
|
107
|
+
|
108
|
+
# Configuration parameters: CountKeywordArgs.
|
109
|
+
Metrics/ParameterLists:
|
110
|
+
Max: 17
|
111
|
+
|
112
|
+
Metrics/PerceivedComplexity:
|
113
|
+
Max: 25
|
114
|
+
|
115
|
+
# Sometimes it's easier to read without guards
|
116
|
+
Style/GuardClause:
|
117
|
+
Enabled: false
|
118
|
+
|
119
|
+
# We allow both " and '
|
120
|
+
Style/StringLiterals:
|
121
|
+
Enabled: false
|
122
|
+
|
123
|
+
# something = if something_else
|
124
|
+
# that's confusing
|
125
|
+
Style/ConditionalAssignment:
|
126
|
+
Enabled: false
|
127
|
+
|
128
|
+
# Better to have too much self than missing a self
|
129
|
+
Style/RedundantSelf:
|
130
|
+
Enabled: false
|
131
|
+
|
132
|
+
# e.g.
|
133
|
+
# def self.is_supported?(platform)
|
134
|
+
# we may never use `platform`
|
135
|
+
Lint/UnusedMethodArgument:
|
136
|
+
Enabled: false
|
137
|
+
|
138
|
+
# the let(:key) { ... }
|
139
|
+
Lint/ParenthesesAsGroupedExpression:
|
140
|
+
Exclude:
|
141
|
+
- '**/spec/**/*'
|
142
|
+
|
143
|
+
# This would reject is_ in front of methods
|
144
|
+
# We use `is_supported?` everywhere already
|
145
|
+
Style/PredicateName:
|
146
|
+
Enabled: false
|
147
|
+
|
148
|
+
# We allow the $
|
149
|
+
Style/PerlBackrefs:
|
150
|
+
Enabled: false
|
151
|
+
|
152
|
+
# Disable '+ should be surrounded with a single space' for xcodebuild_spec.rb
|
153
|
+
Layout/SpaceAroundOperators:
|
154
|
+
Exclude:
|
155
|
+
- '**/spec/actions_specs/xcodebuild_spec.rb'
|
156
|
+
|
157
|
+
# We're not there yet
|
158
|
+
Style/Documentation:
|
159
|
+
Enabled: false
|
160
|
+
|
161
|
+
# Added after upgrade to 0.38.0
|
162
|
+
Style/MutableConstant:
|
163
|
+
Enabled: false
|
164
|
+
|
165
|
+
# length > 0 is good
|
166
|
+
Style/ZeroLengthPredicate:
|
167
|
+
Enabled: false
|
168
|
+
|
169
|
+
# Adds complexity
|
170
|
+
Style/IfInsideElse:
|
171
|
+
Enabled: false
|
172
|
+
|
173
|
+
Style/RescueModifier:
|
174
|
+
Enabled: false
|
175
|
+
|
176
|
+
Style/VariableNumber:
|
177
|
+
Enabled: false
|
178
|
+
|
179
|
+
Style/ClassVars:
|
180
|
+
Enabled: false
|
181
|
+
|
182
|
+
Style/FrozenStringLiteralComment:
|
183
|
+
Enabled: false
|
184
|
+
|
185
|
+
AllCops:
|
186
|
+
Exclude:
|
187
|
+
- './vendor/**/*'
|
188
|
+
- './db/**/*'
|
189
|
+
- './tmp/**/*'
|
190
|
+
- './log/**/*'
|
191
|
+
- './public/**/*'
|
192
|
+
- './bin/**/*'
|
193
|
+
- './Gemfile'
|
data/Gemfile
ADDED
data/README.md
ADDED
@@ -0,0 +1,50 @@
|
|
1
|
+
# Workspace for Ruby
|
2
|
+
|
3
|
+
> Simplified Files and Directories handling
|
4
|
+
|
5
|
+
[![CircleCI](https://circleci.com/gh/MagLoft/workspace/tree/master.svg?style=svg)](https://circleci.com/gh/MagLoft/workspace/tree/master)
|
6
|
+
|
7
|
+
## Description
|
8
|
+
|
9
|
+
Workspace makes it a breeze to work with files and directories.
|
10
|
+
|
11
|
+
## Synopsis
|
12
|
+
|
13
|
+
Workspace::Dir and Workspace::File are abstractions of the ruby Dir and File classes (although not extending them).
|
14
|
+
|
15
|
+
When working with files and folders, these abstractions can significantly help with keeping your code simple, consistent and easy to read.
|
16
|
+
|
17
|
+
```ruby
|
18
|
+
require "workspace"
|
19
|
+
|
20
|
+
root = Workspace.dir # initializes a workspace in the current directory
|
21
|
+
root = Workspace.tmpdir # initializes a new workspace in a temporary directory
|
22
|
+
|
23
|
+
root.file("file.txt").write("hello world") # creates the file "file.txt" with contents "hello world"
|
24
|
+
root.dir("dir").file("file.txt").create # both the file "file.txt" and its parent directory "dir"
|
25
|
+
|
26
|
+
root.dir("dir").exists? # => true
|
27
|
+
root.dir("dir").delete # deletes the physical file, but keeps the Workspace::Dir
|
28
|
+
root.dir("dir").exists? # => false
|
29
|
+
|
30
|
+
file = root.dir("dir1").file("file.txt")
|
31
|
+
file.relative_path(root.dir("dir2")) # => "../dir1/file.txt"
|
32
|
+
|
33
|
+
root.dir("build").clean # delete and re-create directory
|
34
|
+
|
35
|
+
root.files # [file1, file2, file3...]
|
36
|
+
root.directories # [dir1, dir2, dir3...]
|
37
|
+
root.children("**/*.rb") # [...] recursive matched files with .rb extension
|
38
|
+
```
|
39
|
+
|
40
|
+
## Installation
|
41
|
+
|
42
|
+
# install globally
|
43
|
+
gem install workspace
|
44
|
+
|
45
|
+
# install using bundler / Gemfile
|
46
|
+
gem "workspace"
|
47
|
+
|
48
|
+
## License
|
49
|
+
|
50
|
+
workspace is available under an MIT-style license.
|
data/lib/workspace.rb
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
require "workspace/dir"
|
2
|
+
require "workspace/file"
|
3
|
+
|
4
|
+
module Workspace
|
5
|
+
def self.dir(path = "/")
|
6
|
+
Workspace::Dir.new(path)
|
7
|
+
end
|
8
|
+
|
9
|
+
def self.tmpdir(path = nil, &block)
|
10
|
+
if block.nil?
|
11
|
+
dir(::Dir.mktmpdir(path))
|
12
|
+
else
|
13
|
+
::Dir.mktmpdir(path) do |tmppath|
|
14
|
+
yield(dir(tmppath))
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
def self.file(path, workspace: ".")
|
20
|
+
Workspace::File.new(workspace, path)
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,108 @@
|
|
1
|
+
module Workspace
|
2
|
+
class Dir
|
3
|
+
attr_accessor :workspace, :path
|
4
|
+
|
5
|
+
def ==(other)
|
6
|
+
other.class == self.class && other.to_s == self.to_s
|
7
|
+
end
|
8
|
+
|
9
|
+
def initialize(workspace, path = "/")
|
10
|
+
@workspace = workspace
|
11
|
+
@path = path
|
12
|
+
end
|
13
|
+
|
14
|
+
def to_s
|
15
|
+
::File.join(@workspace, @path)
|
16
|
+
end
|
17
|
+
|
18
|
+
def relative_path(relative_dir = nil)
|
19
|
+
if relative_dir
|
20
|
+
relative_dir = relative_dir.dir if relative_dir.class == Workspace::File
|
21
|
+
first = Pathname.new(relative_dir.path)
|
22
|
+
second = Pathname.new(path)
|
23
|
+
result = second.relative_path_from(first).to_s
|
24
|
+
result
|
25
|
+
else
|
26
|
+
@path.gsub(%r{^/}, "")
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
def absolute_path
|
31
|
+
to_s
|
32
|
+
end
|
33
|
+
|
34
|
+
def name
|
35
|
+
::File.basename(to_s)
|
36
|
+
end
|
37
|
+
|
38
|
+
def create
|
39
|
+
FileUtils.mkdir_p(to_s)
|
40
|
+
self
|
41
|
+
end
|
42
|
+
|
43
|
+
def exists?
|
44
|
+
::File.directory?(to_s)
|
45
|
+
end
|
46
|
+
|
47
|
+
def empty?
|
48
|
+
!exists? or children.count == 0
|
49
|
+
end
|
50
|
+
|
51
|
+
def copy(target_dir)
|
52
|
+
target_dir.parent_dir.create unless target_dir.parent_dir.exists?
|
53
|
+
FileUtils.cp_r(to_s, target_dir.to_s)
|
54
|
+
self
|
55
|
+
end
|
56
|
+
|
57
|
+
def move(target_dir)
|
58
|
+
target_dir.parent_dir.create unless target_dir.parent_dir.exists?
|
59
|
+
FileUtils.mv(to_s, target_dir.to_s)
|
60
|
+
self
|
61
|
+
end
|
62
|
+
|
63
|
+
def delete
|
64
|
+
FileUtils.rm_rf(to_s)
|
65
|
+
end
|
66
|
+
|
67
|
+
def clean
|
68
|
+
delete
|
69
|
+
create
|
70
|
+
end
|
71
|
+
|
72
|
+
def file(file_path)
|
73
|
+
Workspace::File.new(@workspace, ::File.join(@path, file_path))
|
74
|
+
end
|
75
|
+
|
76
|
+
def dir(dir_path)
|
77
|
+
Workspace::Dir.new(@workspace, ::File.join(@path, dir_path))
|
78
|
+
end
|
79
|
+
|
80
|
+
def root_dir
|
81
|
+
Workspace::Dir.new(@workspace, "")
|
82
|
+
end
|
83
|
+
|
84
|
+
def parent_dir
|
85
|
+
root_dir.dir(::File.expand_path("..", @path))
|
86
|
+
end
|
87
|
+
|
88
|
+
def children(glob = "*", &block)
|
89
|
+
entries = []
|
90
|
+
::Dir.chdir(to_s) do
|
91
|
+
::Dir[glob].each do |path|
|
92
|
+
entry = dir(path)
|
93
|
+
yield entry if block_given?
|
94
|
+
entries.push(entry)
|
95
|
+
end
|
96
|
+
end
|
97
|
+
entries
|
98
|
+
end
|
99
|
+
|
100
|
+
def files(&block)
|
101
|
+
children("*.*", &block)
|
102
|
+
end
|
103
|
+
|
104
|
+
def directories(&block)
|
105
|
+
children("*/", &block)
|
106
|
+
end
|
107
|
+
end
|
108
|
+
end
|
@@ -0,0 +1,102 @@
|
|
1
|
+
require "mime/types"
|
2
|
+
|
3
|
+
module Workspace
|
4
|
+
class File
|
5
|
+
attr_accessor :workspace, :path
|
6
|
+
|
7
|
+
def initialize(workspace, path)
|
8
|
+
@workspace = workspace
|
9
|
+
@path = path
|
10
|
+
end
|
11
|
+
|
12
|
+
def to_s
|
13
|
+
::File.join(@workspace, @path)
|
14
|
+
end
|
15
|
+
|
16
|
+
def name
|
17
|
+
"#{basename}.#{extension}"
|
18
|
+
end
|
19
|
+
|
20
|
+
def basename
|
21
|
+
::File.basename(path, ".*")
|
22
|
+
end
|
23
|
+
|
24
|
+
def extension
|
25
|
+
::File.extname(to_s).gsub(/^\./, "")
|
26
|
+
end
|
27
|
+
|
28
|
+
def mimetype
|
29
|
+
type = MIME::Types.of(name).first
|
30
|
+
type ? type.to_s : nil
|
31
|
+
end
|
32
|
+
|
33
|
+
def relative_path(relative_dir = nil)
|
34
|
+
if relative_dir
|
35
|
+
relative_dir = relative_dir.dir if relative_dir.class == Workspace::File
|
36
|
+
first = Pathname.new(relative_dir.path)
|
37
|
+
second = Pathname.new(path)
|
38
|
+
result = second.relative_path_from(first).to_s
|
39
|
+
result
|
40
|
+
else
|
41
|
+
@path.gsub(%r{^/}, "")
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def absolute_path
|
46
|
+
::File.absolute_path(to_s)
|
47
|
+
end
|
48
|
+
|
49
|
+
def dir
|
50
|
+
Workspace::Dir.new(@workspace, ::File.dirname(@path))
|
51
|
+
end
|
52
|
+
|
53
|
+
def exists?
|
54
|
+
::File.exist?(to_s)
|
55
|
+
end
|
56
|
+
|
57
|
+
def read
|
58
|
+
@contents ||= ::File.open(to_s).read
|
59
|
+
end
|
60
|
+
|
61
|
+
def read_json
|
62
|
+
JSON.parse(read)
|
63
|
+
end
|
64
|
+
|
65
|
+
def set(data)
|
66
|
+
@contents = data
|
67
|
+
self
|
68
|
+
end
|
69
|
+
|
70
|
+
def replace(key, value)
|
71
|
+
read.gsub!(key, value)
|
72
|
+
self
|
73
|
+
end
|
74
|
+
|
75
|
+
def write(data = nil)
|
76
|
+
data ||= @contents
|
77
|
+
dir.create unless dir.exists?
|
78
|
+
::File.open(to_s, "wb") { |file| file << data }
|
79
|
+
self
|
80
|
+
end
|
81
|
+
|
82
|
+
def copy(target_file)
|
83
|
+
target_file.dir.create unless target_file.dir.exists?
|
84
|
+
FileUtils.cp(to_s, target_file.to_s)
|
85
|
+
end
|
86
|
+
|
87
|
+
def rename(filename)
|
88
|
+
FileUtils.mv(to_s, dir.file(filename).to_s) if exists?
|
89
|
+
@path = dir.file(filename).path
|
90
|
+
end
|
91
|
+
|
92
|
+
def move(target_file)
|
93
|
+
target_file.dir.create unless target_file.dir.exists?
|
94
|
+
FileUtils.mv(to_s, target_file.to_s)
|
95
|
+
target_file
|
96
|
+
end
|
97
|
+
|
98
|
+
def delete
|
99
|
+
FileUtils.rm_f(to_s)
|
100
|
+
end
|
101
|
+
end
|
102
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,120 @@
|
|
1
|
+
describe Workspace::Dir do
|
2
|
+
let(:root) { Workspace.tmpdir("workspace-spec") }
|
3
|
+
let(:root_with_contents) do
|
4
|
+
result = Workspace.tmpdir("workspace-spec")
|
5
|
+
result.dir("folder1").create
|
6
|
+
result.dir("folder2").create
|
7
|
+
result.dir("folder2").file("file1.txt").write("file1")
|
8
|
+
result.dir("folder2").file("file2.txt").write("file2")
|
9
|
+
result.file("file1.txt").write("file1")
|
10
|
+
result.file("file2.txt").write("file2")
|
11
|
+
result
|
12
|
+
end
|
13
|
+
|
14
|
+
it "casts to string" do
|
15
|
+
expect(root.to_s).to match("workspace-spec")
|
16
|
+
end
|
17
|
+
|
18
|
+
it "returns a relative path" do
|
19
|
+
path = root.dir("subdir1").relative_path(root.dir("subdir2"))
|
20
|
+
expect(path).to eq("../subdir1")
|
21
|
+
expect(root.dir("subdir1").relative_path).to eq("subdir1")
|
22
|
+
end
|
23
|
+
|
24
|
+
it "returns an absolute path" do
|
25
|
+
expect(root.absolute_path).to match("workspace-spec")
|
26
|
+
end
|
27
|
+
|
28
|
+
it "returns a name" do
|
29
|
+
expect(root.dir("source").name).to eq("source")
|
30
|
+
end
|
31
|
+
|
32
|
+
it "creates a sub-directory" do
|
33
|
+
source = root.dir("source").create
|
34
|
+
expect(source.exists?).to be_truthy
|
35
|
+
end
|
36
|
+
|
37
|
+
it "checks for existance" do
|
38
|
+
source = root.dir("source")
|
39
|
+
expect(source.exists?).to be_falsy
|
40
|
+
source.create
|
41
|
+
expect(source.exists?).to be_truthy
|
42
|
+
source.delete
|
43
|
+
expect(source.exists?).to be_falsy
|
44
|
+
end
|
45
|
+
|
46
|
+
it "checks if a folder is empty" do
|
47
|
+
source = root.dir("source").create
|
48
|
+
expect(source.empty?).to be_truthy
|
49
|
+
source.file("foobar.txt").write("helloworld")
|
50
|
+
expect(source.empty?).to be_falsy
|
51
|
+
end
|
52
|
+
|
53
|
+
it "copies to another folder" do
|
54
|
+
source = root.dir("source").create
|
55
|
+
target = root.dir("target")
|
56
|
+
source.copy(target)
|
57
|
+
expect(target.exists?).to be_truthy
|
58
|
+
end
|
59
|
+
|
60
|
+
it "moves to another folder" do
|
61
|
+
source = root.dir("source").create
|
62
|
+
target = root.dir("target")
|
63
|
+
source.move(target)
|
64
|
+
expect(target.exists?).to be_truthy
|
65
|
+
expect(source.exists?).to be_falsy
|
66
|
+
end
|
67
|
+
|
68
|
+
it "deletes a folder" do
|
69
|
+
source = root.dir("source").create
|
70
|
+
expect(source.exists?).to be_truthy
|
71
|
+
source.delete
|
72
|
+
expect(source.exists?).to be_falsy
|
73
|
+
end
|
74
|
+
|
75
|
+
it "cleans a folder" do
|
76
|
+
source = root.dir("source").create
|
77
|
+
source.file("foobar.txt").write("helloworld")
|
78
|
+
expect(source.empty?).to be_falsy
|
79
|
+
source.clean
|
80
|
+
expect(source.empty?).to be_truthy
|
81
|
+
end
|
82
|
+
|
83
|
+
it "instantiates a file" do
|
84
|
+
expect(root.file("sample")).to be_a Workspace::File
|
85
|
+
end
|
86
|
+
|
87
|
+
it "instantiates a directory" do
|
88
|
+
expect(root.dir("sample")).to be_a Workspace::Dir
|
89
|
+
end
|
90
|
+
|
91
|
+
it "returns the root dir" do
|
92
|
+
expect(root.dir("sample").dir("sample").root_dir).to eq(root)
|
93
|
+
end
|
94
|
+
|
95
|
+
it "returns the parent dir" do
|
96
|
+
expect(root.dir("sample").parent_dir).to eq(root)
|
97
|
+
end
|
98
|
+
|
99
|
+
it "returns a list of children" do
|
100
|
+
expect(root_with_contents.children.count).to eq 4
|
101
|
+
expect(root_with_contents.children("*/").count).to eq 2
|
102
|
+
expect(root_with_contents.children("*.txt").count).to eq 2
|
103
|
+
expect(root_with_contents.children("**/*.txt").count).to eq 4
|
104
|
+
end
|
105
|
+
|
106
|
+
it "traverses through children" do
|
107
|
+
expect { |b| root_with_contents.children("*", &b) }.to yield_control.exactly(4).times
|
108
|
+
expect { |b| root_with_contents.children("*/", &b) }.to yield_control.exactly(2).times
|
109
|
+
expect { |b| root_with_contents.children("*.txt", &b) }.to yield_control.exactly(2).times
|
110
|
+
expect { |b| root_with_contents.children("**/*.txt", &b) }.to yield_control.exactly(4).times
|
111
|
+
end
|
112
|
+
|
113
|
+
it "traverses through files" do
|
114
|
+
expect { |b| root_with_contents.files(&b) }.to yield_control.exactly(2).times
|
115
|
+
end
|
116
|
+
|
117
|
+
it "traverses through directories" do
|
118
|
+
expect { |b| root_with_contents.directories(&b) }.to yield_control.exactly(2).times
|
119
|
+
end
|
120
|
+
end
|
@@ -0,0 +1,97 @@
|
|
1
|
+
describe Workspace::File do
|
2
|
+
let(:root) { Workspace.tmpdir("workspace-spec") }
|
3
|
+
let(:file) { root.file("sample.txt").write("hello world") }
|
4
|
+
|
5
|
+
it "casts to string" do
|
6
|
+
expect(file.to_s).to match("sample.txt$")
|
7
|
+
end
|
8
|
+
|
9
|
+
it "returns a name" do
|
10
|
+
expect(file.name).to eq("sample.txt")
|
11
|
+
end
|
12
|
+
|
13
|
+
it "returns an basename" do
|
14
|
+
expect(file.basename).to eq("sample")
|
15
|
+
end
|
16
|
+
|
17
|
+
it "returns an extension" do
|
18
|
+
expect(file.extension).to eq("txt")
|
19
|
+
end
|
20
|
+
|
21
|
+
it "returns an mimetype" do
|
22
|
+
expect(file.mimetype).to eq("text/plain")
|
23
|
+
end
|
24
|
+
|
25
|
+
it "returns a relative path" do
|
26
|
+
relative_dir = root.dir("subdir").create
|
27
|
+
expect(file.relative_path(relative_dir)).to eq("../sample.txt")
|
28
|
+
file2 = relative_dir.file("sample.txt")
|
29
|
+
expect(file2.relative_path).to eq("subdir/sample.txt")
|
30
|
+
end
|
31
|
+
|
32
|
+
it "returns an absolute path" do
|
33
|
+
expect(file.absolute_path).to match("workspace-spec")
|
34
|
+
end
|
35
|
+
|
36
|
+
it "returns its directory" do
|
37
|
+
expect(file.dir).to eq(root)
|
38
|
+
end
|
39
|
+
|
40
|
+
it "checks for existance" do
|
41
|
+
source = root.file("foobar.txt")
|
42
|
+
expect(source.exists?).to be_falsy
|
43
|
+
source.write("sample")
|
44
|
+
expect(source.exists?).to be_truthy
|
45
|
+
end
|
46
|
+
|
47
|
+
it "reads a file" do
|
48
|
+
expect(file.read).to eq("hello world")
|
49
|
+
end
|
50
|
+
|
51
|
+
it "reads a json file" do
|
52
|
+
json_data = { "foo" => "bar" }
|
53
|
+
json_file = root.file("sample.json").write(JSON.dump(json_data))
|
54
|
+
expect(json_file.read_json).to eq(json_data)
|
55
|
+
end
|
56
|
+
|
57
|
+
it "sets contents without writing" do
|
58
|
+
file.set("hello bar")
|
59
|
+
expect(file.read).to eq("hello bar")
|
60
|
+
expect(root.file("sample.txt").read).to eq("hello world")
|
61
|
+
end
|
62
|
+
|
63
|
+
it "replaces contents" do
|
64
|
+
file.replace("world", "bar")
|
65
|
+
expect(file.read).to eq("hello bar")
|
66
|
+
end
|
67
|
+
|
68
|
+
it "writes a file" do
|
69
|
+
file.write("hello bar")
|
70
|
+
expect(file.read).to eq("hello bar")
|
71
|
+
end
|
72
|
+
|
73
|
+
it "copies a file" do
|
74
|
+
result = root.file("result.txt")
|
75
|
+
file.copy(result)
|
76
|
+
expect(result.exists?).to be_truthy
|
77
|
+
expect(file.read).to eq(result.read)
|
78
|
+
end
|
79
|
+
|
80
|
+
it "renames to another name" do
|
81
|
+
file.rename("foobar.txt")
|
82
|
+
expect(root.file("foobar.txt").exists?).to be_truthy
|
83
|
+
expect(root.file("foobar.txt").read).to eq("hello world")
|
84
|
+
end
|
85
|
+
|
86
|
+
it "moves a file to another file" do
|
87
|
+
target_file = root.file("foobar.txt")
|
88
|
+
file.move(target_file)
|
89
|
+
expect(target_file.exists?).to be_truthy
|
90
|
+
expect(target_file.read).to eq("hello world")
|
91
|
+
end
|
92
|
+
|
93
|
+
it "deletes a file" do
|
94
|
+
file.delete
|
95
|
+
expect(file.exists?).to be_falsy
|
96
|
+
end
|
97
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
describe Workspace do
|
2
|
+
it "creates a Workspace::Dir" do
|
3
|
+
expect(Workspace.dir(".")).to be_a Workspace::Dir
|
4
|
+
end
|
5
|
+
|
6
|
+
it "creates a temporary Workspace::Dir for a block" do
|
7
|
+
Workspace.tmpdir do |dir|
|
8
|
+
expect(dir).to be_a Workspace::Dir
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
it "creates a temporary Workspace::Dir without a block" do
|
13
|
+
dir = Workspace.tmpdir("sample")
|
14
|
+
expect(dir).to be_a Workspace::Dir
|
15
|
+
expect(dir.name).to match(/^sample/)
|
16
|
+
expect(dir.exists?).to be_truthy
|
17
|
+
dir.delete
|
18
|
+
expect(dir.exists?).to be_falsy
|
19
|
+
end
|
20
|
+
|
21
|
+
it "creates a Workspace::File" do
|
22
|
+
expect(Workspace.file("sample.txt")).to be_a Workspace::File
|
23
|
+
end
|
24
|
+
end
|
data/workspace.gemspec
ADDED
@@ -0,0 +1,27 @@
|
|
1
|
+
lib = File.expand_path('../lib', __FILE__)
|
2
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
3
|
+
require 'workspace/version'
|
4
|
+
|
5
|
+
Gem::Specification.new do |s|
|
6
|
+
s.name = "workspace"
|
7
|
+
s.version = Workspace::VERSION
|
8
|
+
s.licenses = ["BSD-3-Clause"]
|
9
|
+
s.platform = Gem::Platform::RUBY
|
10
|
+
s.authors = ["Tobias Strebitzer"]
|
11
|
+
s.email = ["tobias.strebitzer@magloft.com"]
|
12
|
+
s.homepage = "https://github.com/magloft/workspace"
|
13
|
+
s.summary = "Simplified Files and Directories handling"
|
14
|
+
s.description = "Workspace makes it a breeze to work with files and directories"
|
15
|
+
s.required_ruby_version = '~> 2.0'
|
16
|
+
s.required_rubygems_version = '~> 2.4'
|
17
|
+
s.add_dependency "bundler", '>= 1.3.0', '< 2.0'
|
18
|
+
s.add_runtime_dependency "mime-types", "~> 3.1"
|
19
|
+
s.add_development_dependency "rspec", "~> 3.6"
|
20
|
+
s.add_development_dependency "pry", "~> 0.10"
|
21
|
+
s.add_development_dependency "rubocop", "~> 0.49"
|
22
|
+
s.add_development_dependency "simplecov", "~> 0.10"
|
23
|
+
s.add_development_dependency "simplecov-console", "~> 0.4"
|
24
|
+
s.files = `git ls-files`.split("\n")
|
25
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map { |f| File.basename(f) }
|
26
|
+
s.require_path = 'lib'
|
27
|
+
end
|
metadata
ADDED
@@ -0,0 +1,163 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: workspace
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 1.0.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Tobias Strebitzer
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2017-08-10 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: bundler
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - ">="
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: 1.3.0
|
20
|
+
- - "<"
|
21
|
+
- !ruby/object:Gem::Version
|
22
|
+
version: '2.0'
|
23
|
+
type: :runtime
|
24
|
+
prerelease: false
|
25
|
+
version_requirements: !ruby/object:Gem::Requirement
|
26
|
+
requirements:
|
27
|
+
- - ">="
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: 1.3.0
|
30
|
+
- - "<"
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: '2.0'
|
33
|
+
- !ruby/object:Gem::Dependency
|
34
|
+
name: mime-types
|
35
|
+
requirement: !ruby/object:Gem::Requirement
|
36
|
+
requirements:
|
37
|
+
- - "~>"
|
38
|
+
- !ruby/object:Gem::Version
|
39
|
+
version: '3.1'
|
40
|
+
type: :runtime
|
41
|
+
prerelease: false
|
42
|
+
version_requirements: !ruby/object:Gem::Requirement
|
43
|
+
requirements:
|
44
|
+
- - "~>"
|
45
|
+
- !ruby/object:Gem::Version
|
46
|
+
version: '3.1'
|
47
|
+
- !ruby/object:Gem::Dependency
|
48
|
+
name: rspec
|
49
|
+
requirement: !ruby/object:Gem::Requirement
|
50
|
+
requirements:
|
51
|
+
- - "~>"
|
52
|
+
- !ruby/object:Gem::Version
|
53
|
+
version: '3.6'
|
54
|
+
type: :development
|
55
|
+
prerelease: false
|
56
|
+
version_requirements: !ruby/object:Gem::Requirement
|
57
|
+
requirements:
|
58
|
+
- - "~>"
|
59
|
+
- !ruby/object:Gem::Version
|
60
|
+
version: '3.6'
|
61
|
+
- !ruby/object:Gem::Dependency
|
62
|
+
name: pry
|
63
|
+
requirement: !ruby/object:Gem::Requirement
|
64
|
+
requirements:
|
65
|
+
- - "~>"
|
66
|
+
- !ruby/object:Gem::Version
|
67
|
+
version: '0.10'
|
68
|
+
type: :development
|
69
|
+
prerelease: false
|
70
|
+
version_requirements: !ruby/object:Gem::Requirement
|
71
|
+
requirements:
|
72
|
+
- - "~>"
|
73
|
+
- !ruby/object:Gem::Version
|
74
|
+
version: '0.10'
|
75
|
+
- !ruby/object:Gem::Dependency
|
76
|
+
name: rubocop
|
77
|
+
requirement: !ruby/object:Gem::Requirement
|
78
|
+
requirements:
|
79
|
+
- - "~>"
|
80
|
+
- !ruby/object:Gem::Version
|
81
|
+
version: '0.49'
|
82
|
+
type: :development
|
83
|
+
prerelease: false
|
84
|
+
version_requirements: !ruby/object:Gem::Requirement
|
85
|
+
requirements:
|
86
|
+
- - "~>"
|
87
|
+
- !ruby/object:Gem::Version
|
88
|
+
version: '0.49'
|
89
|
+
- !ruby/object:Gem::Dependency
|
90
|
+
name: simplecov
|
91
|
+
requirement: !ruby/object:Gem::Requirement
|
92
|
+
requirements:
|
93
|
+
- - "~>"
|
94
|
+
- !ruby/object:Gem::Version
|
95
|
+
version: '0.10'
|
96
|
+
type: :development
|
97
|
+
prerelease: false
|
98
|
+
version_requirements: !ruby/object:Gem::Requirement
|
99
|
+
requirements:
|
100
|
+
- - "~>"
|
101
|
+
- !ruby/object:Gem::Version
|
102
|
+
version: '0.10'
|
103
|
+
- !ruby/object:Gem::Dependency
|
104
|
+
name: simplecov-console
|
105
|
+
requirement: !ruby/object:Gem::Requirement
|
106
|
+
requirements:
|
107
|
+
- - "~>"
|
108
|
+
- !ruby/object:Gem::Version
|
109
|
+
version: '0.4'
|
110
|
+
type: :development
|
111
|
+
prerelease: false
|
112
|
+
version_requirements: !ruby/object:Gem::Requirement
|
113
|
+
requirements:
|
114
|
+
- - "~>"
|
115
|
+
- !ruby/object:Gem::Version
|
116
|
+
version: '0.4'
|
117
|
+
description: Workspace makes it a breeze to work with files and directories
|
118
|
+
email:
|
119
|
+
- tobias.strebitzer@magloft.com
|
120
|
+
executables: []
|
121
|
+
extensions: []
|
122
|
+
extra_rdoc_files: []
|
123
|
+
files:
|
124
|
+
- ".circleci/config.yml"
|
125
|
+
- ".gitignore"
|
126
|
+
- ".rspec"
|
127
|
+
- ".rubocop.yml"
|
128
|
+
- Gemfile
|
129
|
+
- README.md
|
130
|
+
- lib/workspace.rb
|
131
|
+
- lib/workspace/dir.rb
|
132
|
+
- lib/workspace/file.rb
|
133
|
+
- lib/workspace/version.rb
|
134
|
+
- spec/spec_helper.rb
|
135
|
+
- spec/workspace/dir_spec.rb
|
136
|
+
- spec/workspace/file_spec.rb
|
137
|
+
- spec/workspace_spec.rb
|
138
|
+
- workspace.gemspec
|
139
|
+
homepage: https://github.com/magloft/workspace
|
140
|
+
licenses:
|
141
|
+
- BSD-3-Clause
|
142
|
+
metadata: {}
|
143
|
+
post_install_message:
|
144
|
+
rdoc_options: []
|
145
|
+
require_paths:
|
146
|
+
- lib
|
147
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
148
|
+
requirements:
|
149
|
+
- - "~>"
|
150
|
+
- !ruby/object:Gem::Version
|
151
|
+
version: '2.0'
|
152
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
153
|
+
requirements:
|
154
|
+
- - "~>"
|
155
|
+
- !ruby/object:Gem::Version
|
156
|
+
version: '2.4'
|
157
|
+
requirements: []
|
158
|
+
rubyforge_project:
|
159
|
+
rubygems_version: 2.6.10
|
160
|
+
signing_key:
|
161
|
+
specification_version: 4
|
162
|
+
summary: Simplified Files and Directories handling
|
163
|
+
test_files: []
|