sundae 1.0.1 → 1.0.2

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.
data/.gitignore ADDED
@@ -0,0 +1,19 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ coverage
6
+ InstalledFiles
7
+ lib/bundler/man
8
+ pkg
9
+ doc
10
+ rdoc
11
+ spec/reports
12
+ test/tmp
13
+ test/version_tmp
14
+ tmp
15
+
16
+ # YARD artifacts
17
+ .yardoc
18
+ _yardoc
19
+ doc/
data/README.rdoc CHANGED
@@ -38,6 +38,10 @@ works. Like this:
38
38
  ~> ls
39
39
  bin Desktop doc etc lib local mnt share src tmp var WualaDrive
40
40
 
41
+ And that's it. When called, Sundae creates links so that you can
42
+ work on your files from seperate parts of life as if they were side
43
+ by side.
44
+
41
45
  == Install
42
46
 
43
47
  sudo gem install sundae
@@ -66,16 +70,22 @@ this:
66
70
  `-- collection2/
67
71
  ` ...
68
72
 
69
- Why is this double layer "collection" stuff going on? Because while
70
- most of the time you can share a whole folder between computers,
71
- sometimes you want to mix your config files into a folder that also
72
- contains nonsymlinked files.
73
+ Sundae will act on all of the <em>mnt</em>s--subdirectories of the
74
+ <em>collection</em>s, that is, the sub-subdirectories of the
75
+ <em>path</em>. The "collections" are only there to facilitate
76
+ grouping common files and syncronizing them between computers.
73
77
 
74
- For example, your ~/.ssh folder probably has a public and private key
75
- that you want to stay unique to that machine, but you might want to
76
- mix in a "config" file that has host aliases that you share between
77
- machines. This is how you do that. I do it with my .unison, .mocp,
78
- .ssh, and .lftp folders.
78
+ By default, all of the contents in each of the <em>mnt</em>s are
79
+ placed in the user's home directory. This can be altered by creating
80
+ a file called <tt>.sundae_path</tt> in the top of the <em>mnt</em>;
81
+ the file should contain one line, which is the absolute path to where
82
+ that directory should be "mounted."
83
+
84
+ There's one exception to the "by default everything is placed in the
85
+ home directory" rule. If the mnt directory starts with "dot-" or
86
+ "dot_" then it is placed in the dot folder formed using the rest of
87
+ the name. For example, the files in a "dot-ssh" mnt are placed in
88
+ "~/.ssh" by default.
79
89
 
80
90
  For example, the hierarchy in my <em>path</em>s looks sort of like this:
81
91
 
@@ -86,13 +96,13 @@ For example, the hierarchy in my <em>path</em>s looks sort of like this:
86
96
  | | |-- etc/ (~/etc will point here)
87
97
  | | ` ...
88
98
  | |-- dot-unison
89
- | | |-- .sundae_path (says "~/.unison")
99
+ | | |-- .sundae_path (says "~/.unison", but not required)
90
100
  | | |-- default.prf (~/.unison/default.prf will point here)
91
101
  | | `
92
102
  | |
93
103
  |-- osx/
94
- | |-- home_library/ (says "~/Library")
95
- | | |-- .sundae_path
104
+ | |-- home_library/
105
+ | | |-- .sundae_path (says "~/Library", required)
96
106
  | | `-- Library-Keyboard_Layouts/
97
107
  | | `-- Keyboard Layouts/
98
108
  | | ` Colemak.keylayout
@@ -112,20 +122,30 @@ For example, the hierarchy in my <em>path</em>s looks sort of like this:
112
122
  | ` ...
113
123
  ` ...
114
124
 
115
- Sundae will act on all of the <em>mnt</em>s--subdirectories of the
116
- <em>collection</em>s, that is, the sub-subdirectories of the
117
- <em>path</em>. The "collections" are only there to facilitate
118
- grouping common files and syncronizing them between computers.
119
-
120
- By default, all of the contents in each of the <em>mnt</em>s are
121
- placed in the user's home directory. This can be altered by
122
- creating a file called <tt>.sundae_path</tt> in the top of the
123
- <em>mnt</em>; the file should contain one line, which is the
124
- absolute path to where that directory should be "mounted."
125
+ Why is this double layer "collection" stuff going on? Because while
126
+ most of the time you can share a whole folder between computers,
127
+ sometimes you want to mix your config files into a folder that also
128
+ contains nonsymlinked files.
125
129
 
126
- And that's it. When called, Sundae creates links so that you can
127
- work on your files from seperate parts of life as if they were side
128
- by side.
130
+ For example, your ~/.ssh folder probably has a public and private key
131
+ that you want to stay unique to that machine, but you might want to
132
+ mix in a "config" file that has host aliases that you share between
133
+ machines. You can put the file in "~/mnt/nix/.ssh/config" in the
134
+ above example, and it will get created alongside the other static
135
+ files in the "~/.ssh/" directory.
136
+
137
+ However, every time you run sundae it will check the target locations
138
+ of each file and directory (recursively) in every mnt directory for
139
+ dangling symlinks and other stuff that sundae might have created. If
140
+ you put the the file in "~/mnt/nix/dot-ssh/config", it will be placed
141
+ in the correct place and only "config" will be checked when sundae is
142
+ run (not all of the other files in "~/.ssh/").
143
+
144
+ It obviously doesn't make much of a speed difference in this case, but
145
+ if you're mixing in one file into "~/a/b/c/d/file", and there are lots
146
+ of files beneath "~/a/", then you don't want sundae to look through
147
+ everything every time it runs. Just put it in a mnt directory with a
148
+ <tt>.sundae_path</tt> of "~/a/b/c/d".
129
149
 
130
150
  == Author
131
151
  <don@ohspite.net>
data/lib/sundae.rb CHANGED
@@ -2,6 +2,7 @@
2
2
  require 'configatron'
3
3
  require 'fileutils'
4
4
  require 'find'
5
+ require 'pathname'
5
6
 
6
7
  # A collection of methods to mix the contents of several directories
7
8
  # together using symbolic links.
@@ -13,20 +14,21 @@ module Sundae
13
14
  # :startdoc:
14
15
  VERSION = ::File.read(PATH + 'version.txt').strip
15
16
 
16
- DEFAULT_CONFIG_FILE = File.expand_path(File.join(ENV['HOME'], '.sundae'))
17
+ DEFAULT_CONFIG_FILE = (Pathname.new(Dir.home) + '.sundae').expand_path
17
18
 
18
19
  @config_file = DEFAULT_CONFIG_FILE
19
20
 
20
21
  # Read configuration from <tt>.sundae</tt>.
21
22
  #
22
23
  def self.load_config_file(config_file = DEFAULT_CONFIG_FILE)
23
- config_file ||= DEFAULT_CONFIG_FILE
24
- config_file = File.join(config_file, '.sundae') if File.directory?(config_file)
24
+ config_file ||= DEFAULT_CONFIG_FILE # if nil is passed
25
+ config_file = Pathname.new(config_file).expand_path
26
+ config_file += '.sundae' if config_file.directory?
25
27
 
26
- create_template_config_file(config_file) unless File.file?(config_file)
28
+ create_template_config_file(config_file) unless config_file.file?
27
29
 
28
30
  load(config_file)
29
- configatron.paths.map! { |p| File.expand_path(p) }
31
+ configatron.paths.map! { |p| Pathname.new(p).expand_path }
30
32
 
31
33
  # An array which lists the directories where mnts are stored.
32
34
  @paths = configatron.paths
@@ -39,13 +41,14 @@ module Sundae
39
41
  # asking the user.
40
42
  #
41
43
  def self.create_template_config_file(config_file)
44
+ config_file = Pathname.new(config_file).expand_path
42
45
  loop do
43
46
  print "#{config_file} does not exist. Create template there? (y/n): "
44
47
  ans = gets.downcase.strip
45
48
  if ans == "y" || ans == "yes"
46
49
  File.open(config_file, "w") do |f|
47
50
  f.puts <<-EOM.gsub(/^ {14}/, '')
48
- # -*-Ruby-*-
51
+ # -*-Ruby-*-
49
52
 
50
53
  # An array which lists the directories where mnts are stored.
51
54
  configatron.paths = ["~/mnt"]
@@ -76,13 +79,15 @@ module Sundae
76
79
  # ignored (i.e., no link will be made pointing to it).
77
80
  #
78
81
  def self.ignore_file?(file) # :doc:
79
- return true if File.basename(file) =~ /^\.\.?$/
80
- return true if File.basename(file) == ".sundae_path"
82
+ file = Pathname.new(file)
83
+ basename = file.basename.to_s
84
+ return true if basename =~ /^\.\.?$/
85
+ return true if basename == ".sundae_path"
81
86
  @ignore_rules.each do |r|
82
87
  if r.kind_of? Regexp
83
- return true if File.basename(file) =~ r
88
+ return true if basename =~ r
84
89
  else
85
- return true if File.fnmatch(r, file)
90
+ return true if file.fnmatch(r)
86
91
  end
87
92
  end
88
93
  return false
@@ -92,12 +97,19 @@ module Sundae
92
97
  # where in the file system links should be created for this mnt.
93
98
  #
94
99
  def self.install_location(mnt)
95
- mnt_config = File.join(mnt, '.sundae_path')
96
- if File.exist?(mnt_config)
97
- location = File.readlines(mnt_config)[0].strip
100
+ mnt = Pathname.new(mnt).expand_path
101
+ mnt_config = mnt + '.sundae_path'
102
+ if mnt_config.exist?
103
+ return Pathname.new(mnt_config.readlines[0].strip).expand_path
98
104
  end
99
105
 
100
- location ||= ENV['HOME']
106
+ base = mnt.basename.to_s
107
+ match = (/dot[-_](.*)/).match(base)
108
+ if match
109
+ return Pathname.new(Dir.home) + ('.' + match[1])
110
+ end
111
+
112
+ return Pathname.new(Dir.home)
101
113
  end
102
114
 
103
115
  # Return an array of all paths in the file system where links will
@@ -111,11 +123,12 @@ module Sundae
111
123
  # as an array.
112
124
  #
113
125
  def self.mnts_in_path(path)
126
+ Pathname.new(path).expand_path
114
127
  mnts = []
115
- collections = Dir.entries(path).delete_if {|a| a=~/^\./}
128
+ collections = path.children(false).delete_if {|c| c.to_s =~ /^\./}
116
129
  collections.each do |c|
117
- collection_mnts = Dir.entries(File.join(path, c)).delete_if {|a| a=~/^\./}
118
- collection_mnts.map! { |mnt| File.join(c, mnt) }
130
+ collection_mnts = (path + c).children(false).delete_if {|c| c.to_s =~ /^\./}
131
+ collection_mnts.map! { |mnt| (c + mnt) }
119
132
  mnts |= collection_mnts # |= is the union
120
133
  end
121
134
 
@@ -128,87 +141,109 @@ module Sundae
128
141
  mnts = []
129
142
 
130
143
  @paths.each do |path|
131
- next unless File.exist?(path)
132
- mnts |= mnts_in_path(path).map { |mnt| File.join(path, mnt) } # |= is the union operator
144
+ next unless path.exist?
145
+ mnts |= mnts_in_path(path).map { |mnt| path + mnt } # |= is the union operator
133
146
  end
134
-
135
147
  return mnts
136
148
  end
137
149
 
138
- # Return all subdirectories of the mnts returned by all_mnts. These
139
- # are the 'mirror' directories that are generated by sundae.
150
+ # Return all subdirectories and files in the mnts returned by
151
+ # all_mnts. These are the 'mirror' files and directories that are
152
+ # generated by sundae.
140
153
  #
141
- def self.generated_directories
154
+ def self.generated_files
142
155
  dirs = Array.new
143
156
 
144
157
  all_mnts.each do |mnt|
145
- mnt_dirs = Dir.entries(mnt).delete_if { |e| ignore_file?(e) }
158
+ mnt_dirs = mnt.children(false).delete_if { |e| ignore_file?(e) }
146
159
  mnt_dirs.each do |dir|
147
- dirs << File.join(install_location(mnt), dir)
160
+ dirs << (install_location(mnt) + dir)
148
161
  end
149
162
  end
150
163
 
151
- return dirs.sort.uniq.select { |d| File.directory?(d) }
164
+ return dirs.sort.uniq#.select { |d| d.directory? }
165
+ end
166
+
167
+ # Return all subdirectories of the mnts returned by all_mnts. These
168
+ # are the 'mirror' directories that are generated by sundae.
169
+ #
170
+ def self.generated_directories
171
+ generated_files.select {|f| f.directory?}
152
172
  end
153
173
 
154
174
  # Check for symlinks in the base directories that are missing their
155
175
  # targets.
156
176
  #
157
177
  def self.remove_dead_links
158
- removed_list = []
159
178
  install_locations.each do |location|
160
- next unless File.exist?(location)
161
- files = Dir.entries(location).map {|f| File.join(location, f)}
179
+ next unless location.exist?
180
+ files = location.entries.map { |f| location + f }
162
181
  files.each do |file|
163
- next unless File.symlink?(file)
164
- next if File.exist? File.readlink(file)
165
- FileUtils.rm(file)
166
- removed_list << file
182
+ next unless file.symlink?
183
+ next if file.readlink.exist?
184
+ next unless root_path(file.readlink)
185
+ file.delete
167
186
  end
168
187
  end
169
- return removed_list
170
188
  end
171
189
 
190
+ # Search through _directory_ and return the first static file found,
191
+ # nil otherwise.
192
+ #
193
+ def self.find_static_file(directory)
194
+ directory = Pathname.new(directory).expand_path
195
+
196
+ directory.find do |path|
197
+ return path if path.exist? && path.ftype == 'file'
198
+ end
199
+ return nil
200
+ end
201
+
172
202
  # Delete each generated directory if there aren't any real files in
173
203
  # them.
174
204
  #
175
205
  def self.remove_generated_directories
176
- removed_list = []
177
206
  generated_directories.each do |dir|
178
- next if File.basename(dir) == ('.sundae')
179
-
180
- # Do a search to make sure no non-symlink file is being
181
- # deleted. That would suck.
182
- if sf = find_static_file(dir)
183
- puts "found static file: #{sf}"
184
- else
185
- FileUtils.rmtree(dir)
186
- removed_list << dir
187
- end
207
+ # don't get rid of the linked config file
208
+ next if dir.basename.to_s == '.sundae'
209
+ remove_generated_stuff dir
210
+
211
+ # if sf = find_static_file(dir)
212
+ # puts "found static file: #{sf}"
213
+ # else
214
+ # dir.rmtree
215
+ # end
188
216
  end
189
- return removed_list
190
217
  end
191
218
 
192
- # Search through _directory_ and return the first static file found,
193
- # nil otherwise.
194
- #
195
- def self.find_static_file(directory)
196
- Find.find(directory) do |path|
197
- return path if File.exist?(path) && File.ftype(path) == 'file'
219
+ def self.remove_generated_files
220
+ generated_files.each do |fod|
221
+ # don't get rid of the linked config file
222
+ next if fod.basename.to_s == '.sundae'
223
+ remove_generated_stuff fod
198
224
  end
199
- return nil
200
225
  end
201
226
 
227
+ def self.remove_generated_stuff(fod)
228
+ return unless fod.exist?
229
+ if fod.ftype == 'directory'
230
+ fod.each_child do |c|
231
+ remove_generated_stuff c
232
+ end
233
+ fod.rmdir if fod.children.empty?
234
+ else
235
+ return unless fod.symlink?
236
+ fod.delete if root_path(fod.readlink) # try to only delete sundae links
237
+ end
238
+ end
239
+
202
240
  # Call minimally_create_links for each mnt.
203
241
  #
204
242
  def self.create_filesystem
205
- mnt_list = []
206
243
  all_mnts.each do |mnt|
207
- FileUtils.mkdir_p(File.expand_path(install_location(mnt)))
244
+ install_location(mnt).expand_path.mkpath
208
245
  minimally_create_links(mnt, install_location(mnt))
209
- mnt_list << mnt
210
246
  end
211
- return mnt_list
212
247
  end
213
248
 
214
249
  # For each directory and file in _target_, create a link at <em>link_name</em>. If
@@ -240,11 +275,15 @@ module Sundae
240
275
  # Starting at _dir_, walk up the directory hierarchy and return the
241
276
  # directory that is contained in _@paths_.
242
277
  #
243
- def self.root_path(dir)
244
- raise ArgumentError if dir == '/'
278
+ def self.root_path(path)
279
+ path = Pathname.new(path).expand_path
280
+ last = path
281
+ path.ascend do |v|
282
+ return last if @paths.include? v
283
+ last = v
284
+ end
245
285
 
246
- parent = File.expand_path(File.join(dir, '..'))
247
- return (@paths.include?(parent)) ? dir : root_path(parent)
286
+ return nil
248
287
  end
249
288
 
250
289
  # Dispatch calls to create_directory_link and create_file_link.
@@ -266,7 +305,7 @@ module Sundae
266
305
  def self.create_file_link(target, link_name)
267
306
  raise ArgumentError, "#{target} does not exist" unless File.file?(target)
268
307
  if File.exist?(link_name)
269
- raise ArgumentError, "#{link_name} cannot be overwritten" unless File.symlink?(link_name)
308
+ raise ArgumentError, "#{link_name} cannot be overwritten for #{target}." unless File.symlink?(link_name)
270
309
  if (not File.exist?(File.readlink(link_name)))
271
310
  FileUtils.ln_sf(target, link_name)
272
311
  else
@@ -285,18 +324,19 @@ module Sundae
285
324
  #
286
325
  def self.create_directory_link(target, link_name)
287
326
  raise ArgumentError unless File.directory?(target)
288
- if (not File.exist?(link_name)) || (File.symlink?(link_name) && (not File.exist?(File.readlink(link_name))))
327
+ if (not File.exist?(link_name)) ||
328
+ (File.symlink?(link_name) && (not File.exist?(File.readlink(link_name))))
289
329
  FileUtils.ln_sf(target, link_name)
290
330
  else
291
331
  case File.ftype(link_name)
292
332
  when 'file'
293
- raise "Could not link #{target} to #{link_name}"
333
+ raise "Could not link #{link_name} to #{target}: target exists."
294
334
  when 'directory'
295
335
  minimally_create_links(target, link_name)
296
336
  when 'link'
297
337
  case File.ftype(File.readlink(link_name))
298
338
  when 'file'
299
- raise "Could not link #{target} to #{link_name}"
339
+ raise "Could not link #{link_name} to #{target}: another link exists there."
300
340
  when 'directory'
301
341
  combine_directories(link_name, target, File.readlink(link_name))
302
342
  end
@@ -308,6 +348,7 @@ module Sundae
308
348
  # <em>target_path1</em> and <em>target_path2</em>.
309
349
  #
310
350
  def self.combine_directories(link_name, target_path1, target_path2)
351
+ raise unless File.symlink?(link_name)
311
352
  return if target_path1 == target_path2
312
353
 
313
354
  FileUtils.rm(link_name)
@@ -318,13 +359,13 @@ module Sundae
318
359
 
319
360
  def self.update_filesystem
320
361
  remove_dead_links
321
- remove_generated_directories
362
+ remove_generated_files
322
363
  create_filesystem
323
364
  end
324
365
 
325
366
  def self.remove_filesystem
326
367
  remove_dead_links
327
- remove_generated_directories
368
+ remove_generated_files
328
369
  end
329
370
 
330
371
  # Return an array of mnts that are installing to +path+.
data/test/test_sundae.rb CHANGED
@@ -3,41 +3,34 @@ require 'test/unit'
3
3
  $:.unshift File.join(File.dirname(__FILE__), "..", "bin") # add ../bin to the Ruby library path
4
4
  $:.unshift File.join(File.dirname(__FILE__), "..", "lib") # ../lib
5
5
  require 'sundae'
6
+ require 'pathname'
6
7
 
7
8
  class TestSundae < Test::Unit::TestCase
8
9
 
9
- @@testdir = File.dirname(File.expand_path(__FILE__))
10
- @@sandbox = File.join(@@testdir, 'sandbox')
11
- @@static_dir = File.join(@@sandbox, 'static')
12
- @@mnts_dir = File.join(@@sandbox, 'mnts')
10
+ @@testdir = Pathname.new(__FILE__).parent.expand_path
11
+ @@sandbox = @@testdir + 'sandbox'
12
+ @@static_dir = @@sandbox + 'static'
13
+ @@mnts_dir = @@sandbox + 'mnts'
13
14
 
14
15
  def setup
15
- FileUtils.mkdir_p(@@sandbox)
16
-
17
- FileUtils.mkdir_p(@@static_dir)
18
- File.open(File.join(@@static_dir, 'static'), 'w')
19
- FileUtils.mkdir_p(File.join(@@mnts_dir, 'c1'))
20
- FileUtils.mkdir_p(File.join(@@mnts_dir, 'c2'))
21
- FileUtils.mkdir_p(File.join(@@mnts_dir, 'c1/d1'))
22
- FileUtils.mkdir_p(File.join(@@mnts_dir, 'c1/d2'))
23
- FileUtils.mkdir_p(File.join(@@mnts_dir, 'c2/d1'))
24
- FileUtils.mkdir_p(File.join(@@mnts_dir, 'c2/d3'))
25
- FileUtils.mkdir_p(File.join(@@mnts_dir, 'c2/d3/d31'))
26
- File.open(File.join(@@mnts_dir, 'c1/d1/f11'), 'w')
27
- File.open(File.join(@@mnts_dir, 'c1/d1/f12'), 'w')
28
- File.open(File.join(@@mnts_dir, 'c1/d2/f21'), 'w')
29
- File.open(File.join(@@mnts_dir, 'c2/d1/f13'), 'w')
30
- File.open(File.join(@@mnts_dir, 'c2/d1/f14'), 'w')
31
- File.open(File.join(@@mnts_dir, 'c2/d3/f31'), 'w')
32
- ['c1/d1', 'c1/d2', 'c2/d1', 'c2/d3'].each do |d|
33
- File.open(File.join(@@mnts_dir, d, '.sundae_path'), 'w') do |f|
34
- f.puts @@sandbox
35
- end
16
+ @@sandbox.mkpath
17
+ @@static_dir.mkpath
18
+
19
+ (@@static_dir + 'static').open('w')
20
+ %w(c1 c2 c1/d1 c1/d2 c2/d1 c2/d3 c2/d3/d31).each do |x|
21
+ (@@mnts_dir + x).mkpath
22
+ end
23
+
24
+ %w(c1/d1/f11 c1/d1/f12 c1/d2/f21 c2/d1/f13 c2/d1/f14 c2/d3/f31).each do |x|
25
+ (@@mnts_dir + x).open('w')
36
26
  end
37
27
 
38
- @@path1 = File.join(@@sandbox, 'mnts')
28
+ %w(c1/d1 c1/d2 c2/d1 c2/d3).each do |d|
29
+ (@@mnts_dir + d + '.sundae_path').open('w') {|f| f.puts @@sandbox}
30
+ end
39
31
 
40
- @@config_file = File.join(@@sandbox, ".sundae")
32
+ @@path1 = @@sandbox + 'mnts'
33
+ @@config_file = @@sandbox + '.sundae'
41
34
  File.open(@@config_file, 'w+') do |f|
42
35
  f.puts "configatron.paths = [\"#{@@path1}\"]"
43
36
  f.puts "configatron.ignore_rules = %w("
@@ -49,24 +42,24 @@ class TestSundae < Test::Unit::TestCase
49
42
  end
50
43
 
51
44
  def teardown
52
- FileUtils.rm_r(@@sandbox)
45
+ @@sandbox.rmtree
53
46
  end
54
47
 
55
48
  def test_class_all_mnts
56
49
  all_mnts = Sundae.all_mnts
57
50
  mnts = Sundae.mnts_in_path(@@path1)
58
51
  mnts.each do |m|
59
- assert all_mnts.include?(File.join(@@path1,m))
52
+ assert all_mnts.include?(@@path1 + m)
60
53
  end
61
54
  end
62
55
 
63
56
  def test_class_combine_directories
64
- d1 = File.join(@@mnts_dir, 'c1/d1')
65
- d2 = File.join(@@mnts_dir, 'c1/d2')
66
- link = File.join(@@sandbox, 'link')
57
+ d1 = @@mnts_dir + 'c1/d1'
58
+ d2 = @@mnts_dir + 'c1/d2'
59
+ link = @@sandbox + 'link'
67
60
  FileUtils.ln_s(d1, link)
68
61
  Sundae.combine_directories(link, d1, d2)
69
- assert File.symlink?(File.join(link, 'f11'))
62
+ assert File.symlink?(link + 'f11')
70
63
  end
71
64
 
72
65
  def test_class_create_directory_link
@@ -125,6 +118,12 @@ class TestSundae < Test::Unit::TestCase
125
118
  assert_equal 1, Sundae.generated_directories.size
126
119
  end
127
120
 
121
+ def test_class_generated_files
122
+ Sundae.create_filesystem
123
+ # assert Sundae.generated_files.include?(File.join(@@sandbox, 'f11'))
124
+ assert_equal 7, Sundae.generated_files.size
125
+ end
126
+
128
127
  def test_class_ignore_file_eh
129
128
  assert Sundae.ignore_file?('.sundae_path')
130
129
  assert Sundae.ignore_file?('..')
@@ -135,45 +134,45 @@ class TestSundae < Test::Unit::TestCase
135
134
  end
136
135
 
137
136
  def test_class_install_location
138
- assert_equal Sundae.install_location('/'), ENV['HOME']
139
- assert_equal Sundae.install_location(File.join(@@mnts_dir, 'c1/d1')), @@sandbox
137
+ assert_equal Pathname.new(Dir.home), Sundae.install_location('/')
138
+ assert_equal @@sandbox, Sundae.install_location(@@mnts_dir + 'c1/d1')
140
139
  end
141
140
 
142
141
  def test_class_install_locations
143
- assert_equal Sundae.install_locations, [@@sandbox]
142
+ assert_equal [@@sandbox], Sundae.install_locations
144
143
  end
145
144
 
146
145
  def test_class_load_config_file
147
146
  sundae_paths = Sundae.instance_variable_get(:@paths)
148
- assert_equal sundae_paths[0], File.expand_path(@@path1)
147
+ assert_equal sundae_paths[0], Pathname.new(@@path1).expand_path
149
148
  end
150
149
 
151
150
  def test_class_minimally_create_links
152
151
  c1 = File.join(@@mnts_dir, 'c1')
153
152
  c2 = File.join(@@mnts_dir, 'c2')
154
153
  Sundae.minimally_create_links(c1, @@sandbox)
155
- assert File.symlink?(File.join(@@sandbox, 'd1'))
156
- assert File.symlink?(File.join(@@sandbox, 'd2'))
154
+ assert((@@sandbox + 'd1').symlink?)
155
+ assert((@@sandbox + 'd2').symlink?)
157
156
  Sundae.minimally_create_links(c2, @@sandbox)
158
- assert File.directory?(File.join(@@sandbox, 'd1'))
159
- assert File.symlink?(File.join(@@sandbox, 'd1/f11'))
160
- assert File.symlink?(File.join(@@sandbox, 'd1/f14'))
161
- assert File.symlink?(File.join(@@sandbox, 'd2'))
162
- assert File.symlink?(File.join(@@sandbox, 'd3'))
157
+ assert((@@sandbox + 'd1').directory?)
158
+ assert((@@sandbox + 'd1/f11').symlink?)
159
+ assert((@@sandbox + 'd1/f14').symlink?)
160
+ assert((@@sandbox + 'd2').symlink?)
161
+ assert((@@sandbox + 'd3').symlink?)
163
162
  end
164
163
 
165
164
  def test_class_mnts_in_path
166
- assert_equal Sundae.mnts_in_path(@@path1), ['c1/d1', 'c1/d2', 'c2/d1', 'c2/d3']
165
+ assert_equal ['c1/d1', 'c1/d2', 'c2/d1', 'c2/d3'].map {|x| Pathname.new(x)},
166
+ Sundae.mnts_in_path(@@path1)
167
167
  end
168
168
 
169
169
  def test_class_remove_dead_links
170
- File.open(File.join(@@sandbox, 'temp_file'), 'w')
171
- File.open(File.join(@@sandbox, 'perm_file'), 'w')
170
+ (@@sandbox + 'temp_file').open('w')
171
+ (@@sandbox + 'perm_file').open('w')
172
172
  FileUtils.ln_s(File.join(@@sandbox, 'temp_file'), File.join(@@sandbox, 'link'))
173
- FileUtils.rm(File.join(@@sandbox, 'temp_file'))
174
- assert_equal Sundae.remove_dead_links, [File.join(@@sandbox, 'link')]
175
- assert ! File.exist?(File.join(@@sandbox, 'link'))
176
- assert File.exist?(File.join(@@sandbox, 'perm_file'))
173
+ (@@sandbox + 'temp_file').delete
174
+ assert ! (@@sandbox + 'link').exist?
175
+ assert (@@sandbox + 'perm_file').exist?
177
176
  end
178
177
 
179
178
  def test_class_remove_generated_directories
@@ -185,12 +184,9 @@ class TestSundae < Test::Unit::TestCase
185
184
  end
186
185
 
187
186
  def test_class_root_path
188
- assert_equal Sundae.root_path(File.join(@@mnts_dir, 'c1')), File.join(@@mnts_dir, 'c1')
189
- assert_equal Sundae.root_path(File.join(@@mnts_dir, 'c1/d1')), File.join(@@mnts_dir, 'c1')
190
-
191
- assert_raise ArgumentError do
192
- Sundae.root_path('/')
193
- end
187
+ assert_equal @@mnts_dir +'c1', Sundae.root_path(@@mnts_dir + 'c1')
188
+ assert_equal @@mnts_dir + 'c1', Sundae.root_path(@@mnts_dir + 'c1/d1')
189
+ assert_equal nil, Sundae.root_path('/')
194
190
  end
195
191
 
196
192
  def test_class_create_link
data/unison/common ADDED
@@ -0,0 +1,17 @@
1
+ fastcheck = true
2
+
3
+ # Roots of the synchronization
4
+ include local_mnt_path
5
+
6
+ ui = text
7
+ log = false
8
+ auto = true
9
+
10
+ # Names and paths to ignore:
11
+ ignore = Name temp.*
12
+ ignore = Name *~
13
+ ignore = Name .*~
14
+ ignore = Name *.o
15
+ ignore = Name *.tmp
16
+ ignore = Name .emacs_autosaves
17
+ ignore = Name .emacs_backups
@@ -0,0 +1,12 @@
1
+ include common
2
+
3
+ root = ssh://donmarch.org//home/14129/users/don%donmarch.org/var/unison/mnts
4
+ sshargs = "-l don%donmarch.org"
5
+
6
+ path = linux
7
+ path = nix
8
+ path = personal
9
+ path = personal_private
10
+ path = proprietorship
11
+ path = personal_archive
12
+ path = reference
data/version.txt CHANGED
@@ -1 +1 @@
1
- 1.0.1
1
+ 1.0.2
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sundae
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.1
4
+ version: 1.0.2
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,11 +9,11 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2012-02-27 00:00:00.000000000 Z
12
+ date: 2012-02-28 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: highline
16
- requirement: &74378590 !ruby/object:Gem::Requirement
16
+ requirement: &79306580 !ruby/object:Gem::Requirement
17
17
  none: false
18
18
  requirements:
19
19
  - - ! '>='
@@ -21,10 +21,10 @@ dependencies:
21
21
  version: 1.6.11
22
22
  type: :runtime
23
23
  prerelease: false
24
- version_requirements: *74378590
24
+ version_requirements: *79306580
25
25
  - !ruby/object:Gem::Dependency
26
26
  name: configatron
27
- requirement: &74378180 !ruby/object:Gem::Requirement
27
+ requirement: &79306020 !ruby/object:Gem::Requirement
28
28
  none: false
29
29
  requirements:
30
30
  - - ! '>='
@@ -32,10 +32,10 @@ dependencies:
32
32
  version: 2.9.0
33
33
  type: :runtime
34
34
  prerelease: false
35
- version_requirements: *74378180
35
+ version_requirements: *79306020
36
36
  - !ruby/object:Gem::Dependency
37
37
  name: rdoc
38
- requirement: &74377570 !ruby/object:Gem::Requirement
38
+ requirement: &79305190 !ruby/object:Gem::Requirement
39
39
  none: false
40
40
  requirements:
41
41
  - - ! '>='
@@ -43,10 +43,10 @@ dependencies:
43
43
  version: '3.12'
44
44
  type: :runtime
45
45
  prerelease: false
46
- version_requirements: *74377570
46
+ version_requirements: *79305190
47
47
  - !ruby/object:Gem::Dependency
48
48
  name: bones
49
- requirement: &74376910 !ruby/object:Gem::Requirement
49
+ requirement: &79303240 !ruby/object:Gem::Requirement
50
50
  none: false
51
51
  requirements:
52
52
  - - ! '>='
@@ -54,7 +54,7 @@ dependencies:
54
54
  version: 3.7.3
55
55
  type: :development
56
56
  prerelease: false
57
- version_requirements: *74376910
57
+ version_requirements: *79303240
58
58
  description: Mix collections of files while maintaining complete separation.
59
59
  email: don@ohspite.net
60
60
  executables:
@@ -67,6 +67,8 @@ extra_rdoc_files:
67
67
  - !binary |-
68
68
  YmluL3N1bmRhZQ==
69
69
  files:
70
+ - !binary |-
71
+ LmdpdGlnbm9yZQ==
70
72
  - !binary |-
71
73
  Q0hBTkdFTE9H
72
74
  - !binary |-
@@ -81,6 +83,10 @@ files:
81
83
  bGliL3N1bmRhZS5yYg==
82
84
  - !binary |-
83
85
  dGVzdC90ZXN0X3N1bmRhZS5yYg==
86
+ - !binary |-
87
+ dW5pc29uL2NvbW1vbg==
88
+ - !binary |-
89
+ dW5pc29uL210X2V4YW1wbGUucHJm
84
90
  - !binary |-
85
91
  dmVyc2lvbi50eHQ=
86
92
  homepage: https://github.com/ohspite/sundae