vfs-momolog 0.0.1

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.
Files changed (51) hide show
  1. data/.gitignore +8 -0
  2. data/Gemfile +4 -0
  3. data/LICENSE +22 -0
  4. data/Rakefile +2 -0
  5. data/docs/basics.rb +116 -0
  6. data/docs/s3_backup.rb +29 -0
  7. data/docs/s3_backup/app/files/bos.png +0 -0
  8. data/docs/s3_basics.rb +19 -0
  9. data/docs/s3_sandbox.rb +24 -0
  10. data/docs/site/404.html +8 -0
  11. data/docs/site/basics.html +305 -0
  12. data/docs/site/index.html +8 -0
  13. data/docs/site/s3_backup.html +111 -0
  14. data/docs/site/s3_basics.html +84 -0
  15. data/docs/site/s3_sandbox.html +99 -0
  16. data/docs/site/ssh_basics.html +84 -0
  17. data/docs/site/ssh_deployment.html +125 -0
  18. data/docs/site/ssh_sandbox.html +103 -0
  19. data/docs/ssh_basics.rb +19 -0
  20. data/docs/ssh_deployment.rb +35 -0
  21. data/docs/ssh_deployment/app/app.rb +0 -0
  22. data/docs/ssh_sandbox.rb +28 -0
  23. data/lib/vfs.rb +18 -0
  24. data/lib/vfs/drivers/local.rb +180 -0
  25. data/lib/vfs/drivers/specification.rb +169 -0
  26. data/lib/vfs/entries/dir.rb +256 -0
  27. data/lib/vfs/entries/entry.rb +152 -0
  28. data/lib/vfs/entries/file.rb +155 -0
  29. data/lib/vfs/entries/universal_entry.rb +24 -0
  30. data/lib/vfs/entry_proxy.rb +42 -0
  31. data/lib/vfs/error.rb +4 -0
  32. data/lib/vfs/integration.rb +30 -0
  33. data/lib/vfs/path.rb +123 -0
  34. data/lib/vfs/version.rb +3 -0
  35. data/lib/vfs/vfs.rb +38 -0
  36. data/old/hash_fs.rb +216 -0
  37. data/old/hash_fs_spec.rb +10 -0
  38. data/readme.md +143 -0
  39. data/spec/container_spec.rb +31 -0
  40. data/spec/dir_spec.rb +253 -0
  41. data/spec/entry_spec.rb +42 -0
  42. data/spec/file_spec.rb +215 -0
  43. data/spec/misc_spec.rb +19 -0
  44. data/spec/path_spec.rb +127 -0
  45. data/spec/spec_helper.rb +50 -0
  46. data/spec/storages/local_spec.rb +24 -0
  47. data/spec/storages/local_spec/emptygit +0 -0
  48. data/spec/universal_entry_spec.rb +69 -0
  49. data/todo.md +19 -0
  50. data/vfs.gemspec +17 -0
  51. metadata +105 -0
data/.gitignore ADDED
@@ -0,0 +1,8 @@
1
+ tmp/*
2
+ spec/config.yml
3
+
4
+ *~
5
+ .DS_Store
6
+ .idea
7
+ .idea/**/*
8
+ Thumbs.db
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in vfs.gemspec
4
+ gemspec
data/LICENSE ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2012 Alexander Presber
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/Rakefile ADDED
@@ -0,0 +1,2 @@
1
+ #!/usr/bin/env rake
2
+ require "bundler/gem_tasks"
data/docs/basics.rb ADDED
@@ -0,0 +1,116 @@
1
+ # Virtual File System provides **clean, simple and unified API over different storages** (Local File System, AWS S3, SFTP, ...).
2
+ #
3
+ # - very simple and intuitive API.
4
+ # - same API for different storages.
5
+ # - work simultaneously with multiple storages.
6
+ # - small codebase, easy to learn and extend.
7
+ # - driver implementation is very simple, it is easy to create new drivers.
8
+ #
9
+ # Such unified API is possible because although the API of storages are different the core concept are almost the same.
10
+ #
11
+ # Install Vfs with Rubygems:
12
+ #
13
+ # gem install vfs
14
+ #
15
+ # Once installed, You can proceed with the example below. It uses local file system as storage, there's also [S3 version][s3_basics] and [SFTP version][ssh_basics] (also [S3 backup][s3_backup] and [SSH/SFTP deployment][ssh_deployment] examples availiable).
16
+ #
17
+ # The project is [hosted on GitHub][project]. You can report bugs and discuss features on the [issues page][issues].
18
+
19
+ # ### Example
20
+
21
+ # Preparing sandbox for our sample and cleaning it before starting
22
+ # (ignore the `$sandbox` variable, it's needed to reuse this code in S3 and SSH samples).
23
+ require 'vfs'
24
+ sandbox = $sandbox || '/tmp/vfs_sandbox'.to_dir.destroy
25
+
26
+ # Creating simple Hello World project.
27
+ project = sandbox['hello_world']
28
+
29
+ # Writing readme file (note that parent dirs where created automatically).
30
+ project['readme.txt'].write 'My App'
31
+
32
+ # We can assign files and dirs to variables, now the `readme` variable refers to our readme.txt file.
33
+ readme = project['readme.txt']
34
+
35
+ # Let's ensure that it's all ok with our readme file and check its attributes.
36
+ p readme.name # => readme.txt
37
+ p [readme.basename, readme.extension] # => ['readme', 'txt']
38
+ p readme.path # => /.../readme.txt
39
+ p readme.exist? # => true
40
+ p readme.file? # => true
41
+ p readme.dir? # => false
42
+ p readme.size # => 6
43
+ p readme.created_at # => 2011-09-09 13:20:43 +0400
44
+ p readme.updated_at # => 2011-09-09 13:20:43 +0400
45
+
46
+ # Reading - You can read all at once or do it sequentially (input stream
47
+ # will be automatically splitted into chunks of reasonable size).
48
+ p readme.read # => "My shiny App"
49
+ readme.read{|chunk| p chunk} # => "My shiny App"
50
+
51
+ # The same for writing - write all at once or do it sequentially
52
+ # (if there's no file it will be created, if it exists it will be rewriten).
53
+ readme.write "My App v2"
54
+ readme.write{|stream| stream.write "My App v3"}
55
+ p readme.read # => "My shiny App v3"
56
+
57
+ # Appending content to existing file.
58
+ readme.append "How to install ..."
59
+ p readme.size # => 27
60
+
61
+ # Copying and Moving. It also works exactly the same
62
+ # way if You copy or move files and dirs to other storages.
63
+ readme.copy_to project['docs/readme.txt']
64
+ p project['docs/readme.txt'].exist? # => true
65
+ p readme.exist? # => true
66
+
67
+ readme.move_to project['docs/readme.txt']
68
+ p project['docs/readme.txt'].exist? # => true
69
+ p readme.exist? # => false
70
+
71
+ # Let's add empty Rakefile to our project.
72
+ project['Rakefile'].write
73
+
74
+ # Operations with directories - checking our project exists and not empty.
75
+ p project.exist? # => true
76
+ p project.empty? # => false
77
+
78
+ # Listing dir content. There are two versions of methods -
79
+ # without block the result will be Array of Entries, with block
80
+ # it will iterate over directory sequentially.
81
+ p project.entries # => [/.../docs, /.../Rakefile]
82
+ p project.files # => [/.../Rakefile]
83
+ p project.dirs # => [/.../docs]
84
+ project.entries do |entry| # => ["docs", false]
85
+ p [entry.name, entry.file?] # => ["Rakefile", true]
86
+ end
87
+ p project.include?('Rakefile') # => true
88
+
89
+ # You can also use glob (if storage support it).
90
+ if project.driver.local?
91
+ p project.entries('**/Rake*') # => [/.../Rakefile]
92
+ p project['**/Rake*'] # => [/.../Rakefile]
93
+
94
+ # The result of dir listing is just an array of Entries, so
95
+ # You can use it to do interesting things. For example this code will
96
+ # calculates the size of sources in our project.
97
+ project['**/*.rb'].collect(&:size).reduce(0, :+)
98
+ end
99
+
100
+ # Copying and moving - let's create another project by cloning our hello_world.
101
+ project.copy_to sandbox['another_project']
102
+ p sandbox['another_project'].entries # => [/.../docs, .../Rakefile]
103
+
104
+ # Cleaning sandbox.
105
+ sandbox.destroy
106
+
107
+ # In this example we covering basics of **Virtual File System**, if You are interesting You can also take
108
+ # a look at [S3 backup][s3_backup] and [SSH/SFTP deployment][ssh_deployment] examples.
109
+ #
110
+ # [s3_basics]: s3_basics.html
111
+ # [s3_backup]: s3_backup.html
112
+ # [ssh_basics]: ssh_basics.html
113
+ # [ssh_deployment]: ssh_deployment.html
114
+ #
115
+ # [project]: https://github.com/alexeypetrushin/vfs
116
+ # [issues]: https://github.com/alexeypetrushin/vfs/issues
data/docs/s3_backup.rb ADDED
@@ -0,0 +1,29 @@
1
+ # Example of creating AWS S3 Backup with [Virtual File System][vfs].
2
+ #
3
+ # In this example we uploading sample files to S3 and then
4
+ # copying it back to local folder.
5
+
6
+ # Connecting to S3 and preparing sandbox. You may take a look at
7
+ # the [docs/s3_sandbox.rb][s3_sandbox] to see the actual code.
8
+ $LOAD_PATH << File.expand_path("#{__FILE__}/../..")
9
+ require 'docs/s3_sandbox'
10
+ s3 = $sandbox
11
+
12
+ # Preparing sample files located in our local folder in
13
+ # current directory.
14
+ current_dir = __FILE__.to_entry.parent
15
+ sample_files = current_dir['s3_backup/app']
16
+
17
+ # Uploading sample files to S3.
18
+ sample_files.copy_to s3['app']
19
+ p s3['app/files/bos.png'].exist? # => true
20
+
21
+ # Preparing local storage for S3 backup.
22
+ local_backup = '/tmp/vfs_sandbox/backup'.to_dir.destroy
23
+
24
+ # Copying files from S3 to local backup directory.
25
+ s3['app'].copy_to local_backup['app']
26
+ p local_backup['app/files/bos.png'].exist? # => true
27
+
28
+ # [vfs]: index.html
29
+ # [s3_sandbox]: s3_sandbox.html
Binary file
data/docs/s3_basics.rb ADDED
@@ -0,0 +1,19 @@
1
+ # Example of [Virtual File System][vfs] working with AWS S3.
2
+ #
3
+ # This is exactly the same [basic example][basics] but this time
4
+ # we using S3 as storage instead of local file system.
5
+
6
+ # Adding examples folder to load paths.
7
+ $LOAD_PATH << File.expand_path("#{__FILE__}/../..")
8
+
9
+ # Connecting to S3 and preparing sandbox. You may take a look at
10
+ # the [docs/s3_sandbox.rb][s3_sandbox] to see the actual code.
11
+ require 'docs/s3_sandbox'
12
+
13
+ # Now we just executig [basic example][basics]
14
+ # but with the `$storage` set to AWS S3.
15
+ require 'docs/basics'
16
+
17
+ # [vfs]: index.html
18
+ # [basics]: basics.html
19
+ # [s3_sandbox]: s3_sandbox.html
@@ -0,0 +1,24 @@
1
+ # Example of using AWS S3 as a storage for [Virtual File System][vfs]
2
+
3
+ # To use S3 we need the S3 driver, You need 'vos' and 'aws-sdk' gems installed.
4
+ #
5
+ # gem install vos aws-sdk
6
+ #
7
+ require 'vfs'
8
+ require 'vos'
9
+ require 'vos/drivers/s3'
10
+
11
+ # Initializing S3 driver, You need to provide Your AWS credentials.
12
+ driver = Vos::Drivers::S3.new \
13
+ access_key_id: 'xxx',
14
+ secret_access_key: 'xxx',
15
+ bucket: 'xxx'
16
+
17
+ # After creating driver we can create storage.
18
+ box = Vos::Box.new driver
19
+
20
+ # Preparing temporary dir (actually, S3 has no dirs, but it can mimic it)
21
+ # for sandbox and cleaning it before starting.
22
+ $sandbox = box['/tmp/vfs_sandbox'].to_dir.destroy
23
+
24
+ # [vfs]: index.html
@@ -0,0 +1,8 @@
1
+ <html>
2
+ <head>
3
+ <meta http-equiv="Refresh" content="0; url=basics.html" />
4
+ </head>
5
+ <body>
6
+ <p>Page not exists, redirecting to <a href="basics.html">home</a>.</p>
7
+ </body>
8
+ </html>
@@ -0,0 +1,305 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <meta http-equiv="content-type" content="text/html;charset=utf-8">
5
+ <title>basics.rb</title>
6
+ <link rel="stylesheet" href="http://jashkenas.github.com/docco/resources/docco.css">
7
+ </head>
8
+ <body>
9
+ <div id='container'>
10
+ <div id="background"></div>
11
+ <div id="jump_to">
12
+ Jump To &hellip;
13
+ <div id="jump_wrapper">
14
+ <div id="jump_page">
15
+ <a class="source" href="basics.html">basics.rb</a>
16
+ <a class="source" href="s3_backup.html">s3_backup.rb</a>
17
+ <a class="source" href="s3_basics.html">s3_basics.rb</a>
18
+ <a class="source" href="s3_sandbox.html">s3_sandbox.rb</a>
19
+ <a class="source" href="ssh_basics.html">ssh_basics.rb</a>
20
+ <a class="source" href="ssh_deployment.html">ssh_deployment.rb</a>
21
+ <a class="source" href="ssh_sandbox.html">ssh_sandbox.rb</a>
22
+ </div>
23
+ </div>
24
+ </div>
25
+ <table cellspacing=0 cellpadding=0>
26
+ <thead>
27
+ <tr>
28
+ <th class=docs><h1>basics.rb</h1></th>
29
+ <th class=code></th>
30
+ </tr>
31
+ </thead>
32
+ <tbody>
33
+ <tr id='section-1'>
34
+ <td class=docs>
35
+ <div class="pilwrap">
36
+ <a class="pilcrow" href="#section-1">&#182;</a>
37
+ </div>
38
+ <p>Virtual File System provides <strong>clean, simple and unified API over different storages</strong> (Local File System, AWS S3, SFTP, &hellip;).</p>
39
+
40
+ <ul>
41
+ <li>very simple and intuitive API.</li>
42
+ <li>same API for different storages.</li>
43
+ <li>work simultaneously with multiple storages.</li>
44
+ <li>small codebase, easy to learn and extend.</li>
45
+ <li>driver implementation is very simple, it is easy to create new drivers.</li>
46
+ </ul>
47
+
48
+ <p>Such unified API is possible because although the API of storages are different the core concept are almost the same.</p>
49
+
50
+ <p>Install Vfs with Rubygems:</p>
51
+
52
+ <pre><code>gem install vfs
53
+ </code></pre>
54
+
55
+ <p>Once installed, You can proceed with the example below. It uses local file system as storage, there&rsquo;s also <a href="s3_basics.html">S3 version</a> and <a href="ssh_basics.html">SFTP version</a> (also <a href="s3_backup.html">S3 backup</a> and <a href="ssh_deployment.html">SSH/SFTP deployment</a> examples availiable).</p>
56
+
57
+ <p>The project is <a href="https://github.com/alexeypetrushin/vfs">hosted on GitHub</a>. You can report bugs and discuss features on the <a href="https://github.com/alexeypetrushin/vfs/issues">issues page</a>.</p>
58
+ </td>
59
+ <td class=code>
60
+ <div class='highlight'><pre></pre></div>
61
+ </td>
62
+ </tr>
63
+ <tr id='section-Example'>
64
+ <td class=docs>
65
+ <div class="pilwrap">
66
+ <a class="pilcrow" href="#section-Example">&#182;</a>
67
+ </div>
68
+ <h3>Example</h3>
69
+ </td>
70
+ <td class=code>
71
+ <div class='highlight'><pre></pre></div>
72
+ </td>
73
+ </tr>
74
+ <tr id='section-3'>
75
+ <td class=docs>
76
+ <div class="pilwrap">
77
+ <a class="pilcrow" href="#section-3">&#182;</a>
78
+ </div>
79
+ <p>Preparing sandbox for our sample and cleaning it before starting
80
+ (ignore the <code>$sandbox</code> variable, it&rsquo;s needed to reuse this code in S3 and SSH samples).</p>
81
+ </td>
82
+ <td class=code>
83
+ <div class='highlight'><pre><span class="nb">require</span> <span class="s1">&#39;vfs&#39;</span>
84
+ <span class="n">sandbox</span> <span class="o">=</span> <span class="vg">$sandbox</span> <span class="o">||</span> <span class="s1">&#39;/tmp/vfs_sandbox&#39;</span><span class="o">.</span><span class="n">to_dir</span><span class="o">.</span><span class="n">destroy</span></pre></div>
85
+ </td>
86
+ </tr>
87
+ <tr id='section-4'>
88
+ <td class=docs>
89
+ <div class="pilwrap">
90
+ <a class="pilcrow" href="#section-4">&#182;</a>
91
+ </div>
92
+ <p>Creating simple Hello World project.</p>
93
+ </td>
94
+ <td class=code>
95
+ <div class='highlight'><pre><span class="n">project</span> <span class="o">=</span> <span class="n">sandbox</span><span class="o">[</span><span class="s1">&#39;hello_world&#39;</span><span class="o">]</span></pre></div>
96
+ </td>
97
+ </tr>
98
+ <tr id='section-5'>
99
+ <td class=docs>
100
+ <div class="pilwrap">
101
+ <a class="pilcrow" href="#section-5">&#182;</a>
102
+ </div>
103
+ <p>Writing readme file (note that parent dirs where created automatically).</p>
104
+ </td>
105
+ <td class=code>
106
+ <div class='highlight'><pre><span class="n">project</span><span class="o">[</span><span class="s1">&#39;readme.txt&#39;</span><span class="o">].</span><span class="n">write</span> <span class="s1">&#39;My App&#39;</span></pre></div>
107
+ </td>
108
+ </tr>
109
+ <tr id='section-6'>
110
+ <td class=docs>
111
+ <div class="pilwrap">
112
+ <a class="pilcrow" href="#section-6">&#182;</a>
113
+ </div>
114
+ <p>We can assign files and dirs to variables, now the <code>readme</code> variable refers to our readme.txt file.</p>
115
+ </td>
116
+ <td class=code>
117
+ <div class='highlight'><pre><span class="n">readme</span> <span class="o">=</span> <span class="n">project</span><span class="o">[</span><span class="s1">&#39;readme.txt&#39;</span><span class="o">]</span></pre></div>
118
+ </td>
119
+ </tr>
120
+ <tr id='section-7'>
121
+ <td class=docs>
122
+ <div class="pilwrap">
123
+ <a class="pilcrow" href="#section-7">&#182;</a>
124
+ </div>
125
+ <p>Let&rsquo;s ensure that it&rsquo;s all ok with our readme file and check it&rsquo;s attributes.</p>
126
+ </td>
127
+ <td class=code>
128
+ <div class='highlight'><pre><span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">name</span> <span class="c1"># =&gt; readme.txt</span>
129
+ <span class="nb">p</span> <span class="o">[</span><span class="n">readme</span><span class="o">.</span><span class="n">basename</span><span class="p">,</span> <span class="n">readme</span><span class="o">.</span><span class="n">extension</span><span class="o">]</span> <span class="c1"># =&gt; [&#39;readme&#39;, &#39;txt&#39;]</span>
130
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">path</span> <span class="c1"># =&gt; /.../readme.txt</span>
131
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">exist?</span> <span class="c1"># =&gt; true</span>
132
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">file?</span> <span class="c1"># =&gt; true</span>
133
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">dir?</span> <span class="c1"># =&gt; false</span>
134
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">size</span> <span class="c1"># =&gt; 6</span>
135
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">created_at</span> <span class="c1"># =&gt; 2011-09-09 13:20:43 +0400</span>
136
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">updated_at</span> <span class="c1"># =&gt; 2011-09-09 13:20:43 +0400</span></pre></div>
137
+ </td>
138
+ </tr>
139
+ <tr id='section-8'>
140
+ <td class=docs>
141
+ <div class="pilwrap">
142
+ <a class="pilcrow" href="#section-8">&#182;</a>
143
+ </div>
144
+ <p>Reading &ndash; You can read all at once or do it sequentially (input stream
145
+ will be automatically splitted into chunks of reasonable size).</p>
146
+ </td>
147
+ <td class=code>
148
+ <div class='highlight'><pre><span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">read</span> <span class="c1"># =&gt; &quot;My shiny App&quot;</span>
149
+ <span class="n">readme</span><span class="o">.</span><span class="n">read</span><span class="p">{</span><span class="o">|</span><span class="n">chunk</span><span class="o">|</span> <span class="nb">p</span> <span class="n">chunk</span><span class="p">}</span> <span class="c1"># =&gt; &quot;My shiny App&quot;</span></pre></div>
150
+ </td>
151
+ </tr>
152
+ <tr id='section-9'>
153
+ <td class=docs>
154
+ <div class="pilwrap">
155
+ <a class="pilcrow" href="#section-9">&#182;</a>
156
+ </div>
157
+ <p>The same for writing &ndash; write all at once or do it sequentially
158
+ (if there&rsquo;s no file it will be created, if it exists it will be rewriten).</p>
159
+ </td>
160
+ <td class=code>
161
+ <div class='highlight'><pre><span class="n">readme</span><span class="o">.</span><span class="n">write</span> <span class="s2">&quot;My App v2&quot;</span>
162
+ <span class="n">readme</span><span class="o">.</span><span class="n">write</span><span class="p">{</span><span class="o">|</span><span class="n">stream</span><span class="o">|</span> <span class="n">stream</span><span class="o">.</span><span class="n">write</span> <span class="s2">&quot;My App v3&quot;</span><span class="p">}</span>
163
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">read</span> <span class="c1"># =&gt; &quot;My shiny App v3&quot;</span></pre></div>
164
+ </td>
165
+ </tr>
166
+ <tr id='section-10'>
167
+ <td class=docs>
168
+ <div class="pilwrap">
169
+ <a class="pilcrow" href="#section-10">&#182;</a>
170
+ </div>
171
+ <p>Appending content to existing file.</p>
172
+ </td>
173
+ <td class=code>
174
+ <div class='highlight'><pre><span class="n">readme</span><span class="o">.</span><span class="n">append</span> <span class="s2">&quot;How to install ...&quot;</span>
175
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">size</span> <span class="c1"># =&gt; 27</span></pre></div>
176
+ </td>
177
+ </tr>
178
+ <tr id='section-11'>
179
+ <td class=docs>
180
+ <div class="pilwrap">
181
+ <a class="pilcrow" href="#section-11">&#182;</a>
182
+ </div>
183
+ <p>Copying and Moving. It also works exactly the same
184
+ way if You copy or move files and dirs to other storages.</p>
185
+ </td>
186
+ <td class=code>
187
+ <div class='highlight'><pre><span class="n">readme</span><span class="o">.</span><span class="n">copy_to</span> <span class="n">project</span><span class="o">[</span><span class="s1">&#39;docs/readme.txt&#39;</span><span class="o">]</span>
188
+ <span class="nb">p</span> <span class="n">project</span><span class="o">[</span><span class="s1">&#39;docs/readme.txt&#39;</span><span class="o">].</span><span class="n">exist?</span> <span class="c1"># =&gt; true</span>
189
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">exist?</span> <span class="c1"># =&gt; true</span>
190
+
191
+ <span class="n">readme</span><span class="o">.</span><span class="n">move_to</span> <span class="n">project</span><span class="o">[</span><span class="s1">&#39;docs/readme.txt&#39;</span><span class="o">]</span>
192
+ <span class="nb">p</span> <span class="n">project</span><span class="o">[</span><span class="s1">&#39;docs/readme.txt&#39;</span><span class="o">].</span><span class="n">exist?</span> <span class="c1"># =&gt; true</span>
193
+ <span class="nb">p</span> <span class="n">readme</span><span class="o">.</span><span class="n">exist?</span> <span class="c1"># =&gt; false</span></pre></div>
194
+ </td>
195
+ </tr>
196
+ <tr id='section-12'>
197
+ <td class=docs>
198
+ <div class="pilwrap">
199
+ <a class="pilcrow" href="#section-12">&#182;</a>
200
+ </div>
201
+ <p>Let&rsquo;s add empty Rakefile to our project.</p>
202
+ </td>
203
+ <td class=code>
204
+ <div class='highlight'><pre><span class="n">project</span><span class="o">[</span><span class="s1">&#39;Rakefile&#39;</span><span class="o">].</span><span class="n">write</span></pre></div>
205
+ </td>
206
+ </tr>
207
+ <tr id='section-13'>
208
+ <td class=docs>
209
+ <div class="pilwrap">
210
+ <a class="pilcrow" href="#section-13">&#182;</a>
211
+ </div>
212
+ <p>Operations with directories &ndash; checking our project exists and not empty.</p>
213
+ </td>
214
+ <td class=code>
215
+ <div class='highlight'><pre><span class="nb">p</span> <span class="n">project</span><span class="o">.</span><span class="n">exist?</span> <span class="c1"># =&gt; true</span>
216
+ <span class="nb">p</span> <span class="n">project</span><span class="o">.</span><span class="n">empty?</span> <span class="c1"># =&gt; false</span></pre></div>
217
+ </td>
218
+ </tr>
219
+ <tr id='section-14'>
220
+ <td class=docs>
221
+ <div class="pilwrap">
222
+ <a class="pilcrow" href="#section-14">&#182;</a>
223
+ </div>
224
+ <p>Listing dir content. There are two versions of methods &ndash;
225
+ without block the result will be Array of Entries, with block
226
+ it will iterate over directory sequentially.</p>
227
+ </td>
228
+ <td class=code>
229
+ <div class='highlight'><pre><span class="nb">p</span> <span class="n">project</span><span class="o">.</span><span class="n">entries</span> <span class="c1"># =&gt; [/.../docs, /.../Rakefile]</span>
230
+ <span class="nb">p</span> <span class="n">project</span><span class="o">.</span><span class="n">files</span> <span class="c1"># =&gt; [/.../Rakefile]</span>
231
+ <span class="nb">p</span> <span class="n">project</span><span class="o">.</span><span class="n">dirs</span> <span class="c1"># =&gt; [/.../docs]</span>
232
+ <span class="n">project</span><span class="o">.</span><span class="n">entries</span> <span class="k">do</span> <span class="o">|</span><span class="n">entry</span><span class="o">|</span> <span class="c1"># =&gt; [&quot;docs&quot;, false]</span>
233
+ <span class="nb">p</span> <span class="o">[</span><span class="n">entry</span><span class="o">.</span><span class="n">name</span><span class="p">,</span> <span class="n">entry</span><span class="o">.</span><span class="n">file?</span><span class="o">]</span> <span class="c1"># =&gt; [&quot;Rakefile&quot;, true]</span>
234
+ <span class="k">end</span>
235
+ <span class="nb">p</span> <span class="n">project</span><span class="o">.</span><span class="n">include?</span><span class="p">(</span><span class="s1">&#39;Rakefile&#39;</span><span class="p">)</span> <span class="c1"># =&gt; true</span></pre></div>
236
+ </td>
237
+ </tr>
238
+ <tr id='section-15'>
239
+ <td class=docs>
240
+ <div class="pilwrap">
241
+ <a class="pilcrow" href="#section-15">&#182;</a>
242
+ </div>
243
+ <p>You can also use glob (if storage support it).</p>
244
+ </td>
245
+ <td class=code>
246
+ <div class='highlight'><pre><span class="k">if</span> <span class="n">project</span><span class="o">.</span><span class="n">driver</span><span class="o">.</span><span class="n">local?</span>
247
+ <span class="nb">p</span> <span class="n">project</span><span class="o">.</span><span class="n">entries</span><span class="p">(</span><span class="s1">&#39;**/Rake*&#39;</span><span class="p">)</span> <span class="c1"># =&gt; [/.../Rakefile]</span>
248
+ <span class="nb">p</span> <span class="n">project</span><span class="o">[</span><span class="s1">&#39;**/Rake*&#39;</span><span class="o">]</span> <span class="c1"># =&gt; [/.../Rakefile]</span>
249
+ <span class="k">end</span></pre></div>
250
+ </td>
251
+ </tr>
252
+ <tr id='section-16'>
253
+ <td class=docs>
254
+ <div class="pilwrap">
255
+ <a class="pilcrow" href="#section-16">&#182;</a>
256
+ </div>
257
+ <p>The result of dir listing is just an array of Entries, so
258
+ You can use it to do interesting things. For example this code will
259
+ calculates the size of sources in our project.</p>
260
+ </td>
261
+ <td class=code>
262
+ <div class='highlight'><pre><span class="k">if</span> <span class="n">project</span><span class="o">.</span><span class="n">driver</span><span class="o">.</span><span class="n">local?</span>
263
+ <span class="n">project</span><span class="o">[</span><span class="s1">&#39;**/*.rb&#39;</span><span class="o">].</span><span class="n">collect</span><span class="p">(</span><span class="o">&amp;</span><span class="ss">:size</span><span class="p">)</span><span class="o">.</span><span class="n">reduce</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="ss">:+</span><span class="p">)</span>
264
+ <span class="k">end</span></pre></div>
265
+ </td>
266
+ </tr>
267
+ <tr id='section-17'>
268
+ <td class=docs>
269
+ <div class="pilwrap">
270
+ <a class="pilcrow" href="#section-17">&#182;</a>
271
+ </div>
272
+ <p>Copying and moving &ndash; let&rsquo;s create another project by cloning our hello_world.</p>
273
+ </td>
274
+ <td class=code>
275
+ <div class='highlight'><pre><span class="n">project</span><span class="o">.</span><span class="n">copy_to</span> <span class="n">sandbox</span><span class="o">[</span><span class="s1">&#39;another_project&#39;</span><span class="o">]</span>
276
+ <span class="nb">p</span> <span class="n">sandbox</span><span class="o">[</span><span class="s1">&#39;another_project&#39;</span><span class="o">].</span><span class="n">entries</span> <span class="c1"># =&gt; [/.../docs, .../Rakefile]</span></pre></div>
277
+ </td>
278
+ </tr>
279
+ <tr id='section-18'>
280
+ <td class=docs>
281
+ <div class="pilwrap">
282
+ <a class="pilcrow" href="#section-18">&#182;</a>
283
+ </div>
284
+ <p>Cleaning sandbox.</p>
285
+ </td>
286
+ <td class=code>
287
+ <div class='highlight'><pre><span class="n">sandbox</span><span class="o">.</span><span class="n">destroy</span></pre></div>
288
+ </td>
289
+ </tr>
290
+ <tr id='section-19'>
291
+ <td class=docs>
292
+ <div class="pilwrap">
293
+ <a class="pilcrow" href="#section-19">&#182;</a>
294
+ </div>
295
+ <p>In this example we covering basics of <strong>Virtual File System</strong>, if You are interesting You can also take
296
+ a look at <a href="s3_backup.html">S3 backup</a> and <a href="ssh_deployment.html">SSH/SFTP deployment</a> examples.</p>
297
+
298
+ </td>
299
+ <td class=code>
300
+ <div class='highlight'><pre></pre></div>
301
+ </td>
302
+ </tr>
303
+ </table>
304
+ </div>
305
+ </body>