fs_template 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,15 @@
1
+ ---
2
+ !binary "U0hBMQ==":
3
+ metadata.gz: !binary |-
4
+ ZTBhMDk4ODljMTRkMjQ5MzQ0MWI5YWU5MzA1OTRjNjhhZGZlMjg3Mw==
5
+ data.tar.gz: !binary |-
6
+ NDkwZjhhMDAzYjkwYjIzZTEzNTc4MDk4OThlNmE1M2M2NDUzNWYyNg==
7
+ !binary "U0hBNTEy":
8
+ metadata.gz: !binary |-
9
+ ZWY4YzA2NjUzZmNiNDM3MTRjNThkNWI3YjdkMTE4ZTQ0OGNhYWM3ZjVhM2U0
10
+ MzI3MjA2OTg1Y2Y2MWQ4ZjcxYTVmMjNiMmIyMTcwNDcwMTE1ZjY1OTQ1Yjhk
11
+ YTEzMmM0ZjA4NTJiOTM4NDcxNGJjNjlkNmIwMjc2ODE2ZWVkMDI=
12
+ data.tar.gz: !binary |-
13
+ OGU4ZjY2MWZkMmY2YTE1M2IwYTI4ZGY1MzA5YmMxMTVmNTM2ZWVkOTJhNjc5
14
+ YTM0NzhmZGMyOGQ2ZDY5YjBiZDNjYWQzYzlkZjlhM2U3MGI4NjczM2E3NDA4
15
+ YjEyMmY1MWJiMGE5M2Y5YWFhYjc4YTYwNTIwNDYyMmM1Mjc4YWE=
data/.document ADDED
@@ -0,0 +1,5 @@
1
+ lib/**/*.rb
2
+ bin/*
3
+ -
4
+ features/**/*.feature
5
+ LICENSE.txt
data/.rspec ADDED
@@ -0,0 +1 @@
1
+ --color
data/Gemfile ADDED
@@ -0,0 +1,31 @@
1
+ source "http://rubygems.org"
2
+ # Add dependencies required to use your gem here.
3
+ # Example:
4
+ # gem "activesupport", ">= 2.3.5"
5
+
6
+ # Add dependencies to develop your gem here.
7
+ # Include everything needed to run rake, tests, features, etc.
8
+ group :development do
9
+ gem "rspec", "~> 2.8.0"
10
+ gem "rdoc", "~> 3.12"
11
+ gem "bundler", ">= 1.0.0"
12
+ gem "jeweler", "~> 1.8.4"
13
+ #gem "rcov", ">= 0"
14
+
15
+ gem 'guard'
16
+ gem 'guard-rspec'
17
+ gem 'guard-spork'
18
+
19
+ gem 'rb-fsevent', '~> 0.9'
20
+
21
+ gem 'lre'
22
+ end
23
+
24
+ gem 'mharris_ext'
25
+ #gem "rchoice", :path => "/users/mharris717/gems/rchoice-0.2.0"
26
+ #gem 'rchoice','0.2.0'
27
+ #gem 'rchoice', :git => "git@github.com:mharris717/rchoice.git", :branch => "gemdir"
28
+
29
+ gem 'andand'
30
+
31
+ gem 'simplecov', :require => false, :group => :test
data/Gemfile.lock ADDED
@@ -0,0 +1,122 @@
1
+ GEM
2
+ remote: http://rubygems.org/
3
+ specs:
4
+ addressable (2.3.5)
5
+ andand (1.3.3)
6
+ builder (3.2.2)
7
+ celluloid (0.15.2)
8
+ timers (~> 1.1.0)
9
+ childprocess (0.3.9)
10
+ ffi (~> 1.0, >= 1.0.11)
11
+ coderay (1.0.9)
12
+ diff-lcs (1.1.3)
13
+ facets (2.9.3)
14
+ faraday (0.8.8)
15
+ multipart-post (~> 1.2.0)
16
+ fattr (2.2.1)
17
+ ffi (1.9.0)
18
+ formatador (0.2.4)
19
+ git (1.2.6)
20
+ github_api (0.10.1)
21
+ addressable
22
+ faraday (~> 0.8.1)
23
+ hashie (>= 1.2)
24
+ multi_json (~> 1.4)
25
+ nokogiri (~> 1.5.2)
26
+ oauth2
27
+ guard (2.0.3)
28
+ formatador (>= 0.2.4)
29
+ listen (~> 2.0)
30
+ lumberjack (~> 1.0)
31
+ pry (>= 0.9.12)
32
+ thor (>= 0.18.1)
33
+ guard-rspec (1.2.1)
34
+ guard (>= 1.1)
35
+ guard-spork (1.5.1)
36
+ childprocess (>= 0.2.3)
37
+ guard (>= 1.1)
38
+ spork (>= 0.8.4)
39
+ hashie (2.0.5)
40
+ highline (1.6.19)
41
+ httpauth (0.2.0)
42
+ jeweler (1.8.7)
43
+ builder
44
+ bundler (~> 1.0)
45
+ git (>= 1.2.5)
46
+ github_api (= 0.10.1)
47
+ highline (>= 1.6.15)
48
+ nokogiri (= 1.5.10)
49
+ rake
50
+ rdoc
51
+ json (1.8.1)
52
+ jwt (0.1.8)
53
+ multi_json (>= 1.5)
54
+ listen (2.0.3)
55
+ celluloid (>= 0.15.2)
56
+ rb-fsevent (>= 0.9.3)
57
+ rb-inotify (>= 0.9)
58
+ lre (0.3.0)
59
+ fattr
60
+ mharris_ext
61
+ watchr
62
+ lumberjack (1.0.4)
63
+ method_source (0.8.2)
64
+ mharris_ext (1.7.0)
65
+ facets
66
+ fattr
67
+ multi_json (1.8.2)
68
+ multi_xml (0.5.5)
69
+ multipart-post (1.2.0)
70
+ nokogiri (1.5.10)
71
+ oauth2 (0.9.2)
72
+ faraday (~> 0.8)
73
+ httpauth (~> 0.2)
74
+ jwt (~> 0.1.4)
75
+ multi_json (~> 1.0)
76
+ multi_xml (~> 0.5)
77
+ rack (~> 1.2)
78
+ pry (0.9.12.2)
79
+ coderay (~> 1.0.5)
80
+ method_source (~> 0.8)
81
+ slop (~> 3.4)
82
+ rack (1.5.2)
83
+ rake (10.1.0)
84
+ rb-fsevent (0.9.3)
85
+ rb-inotify (0.9.2)
86
+ ffi (>= 0.5.0)
87
+ rdoc (3.12.2)
88
+ json (~> 1.4)
89
+ rspec (2.8.0)
90
+ rspec-core (~> 2.8.0)
91
+ rspec-expectations (~> 2.8.0)
92
+ rspec-mocks (~> 2.8.0)
93
+ rspec-core (2.8.0)
94
+ rspec-expectations (2.8.0)
95
+ diff-lcs (~> 1.1.2)
96
+ rspec-mocks (2.8.0)
97
+ simplecov (0.7.1)
98
+ multi_json (~> 1.0)
99
+ simplecov-html (~> 0.7.1)
100
+ simplecov-html (0.7.1)
101
+ slop (3.4.6)
102
+ spork (0.9.2)
103
+ thor (0.18.1)
104
+ timers (1.1.0)
105
+ watchr (0.7)
106
+
107
+ PLATFORMS
108
+ ruby
109
+
110
+ DEPENDENCIES
111
+ andand
112
+ bundler (>= 1.0.0)
113
+ guard
114
+ guard-rspec
115
+ guard-spork
116
+ jeweler (~> 1.8.4)
117
+ lre
118
+ mharris_ext
119
+ rb-fsevent (~> 0.9)
120
+ rdoc (~> 3.12)
121
+ rspec (~> 2.8.0)
122
+ simplecov
data/Guardfile ADDED
@@ -0,0 +1,32 @@
1
+ # A sample Guardfile
2
+ # More info at https://github.com/guard/guard#readme
3
+
4
+ guard 'spork', :rspec_port => 5830 do
5
+ watch('config/application.rb')
6
+ watch('config/environment.rb')
7
+ watch('config/environments/test.rb')
8
+ watch(%r{^config/initializers/.+\.rb$})
9
+ watch('Gemfile')
10
+ watch('Gemfile.lock')
11
+ watch('spec/spec_helper.rb') { :rspec }
12
+ watch('test/test_helper.rb') { :test_unit }
13
+ watch(%r{features/support/}) { :cucumber }
14
+ watch(%r{^spec/support/.+\.rb$})
15
+ end
16
+
17
+
18
+
19
+
20
+ guard 'rspec', :cli => "--drb --drb-port 5830" do
21
+ watch(%r{^spec/.+_spec\.rb$})
22
+ watch(%r{^lib/(.+)\.rb$}) { "spec" } # { |m| "spec/lib/#{m[1]}_spec.rb" }
23
+ watch(%r{^lib/(.+)\.treetop$}) { "spec" }
24
+ watch(%r{^lib/(.+)\.csv$}) { "spec" }
25
+ #watch(%r{^spec/support/(.+)\.rb$}) { "spec" }
26
+ watch('spec/spec_helper.rb') { "spec" }
27
+ end
28
+
29
+
30
+
31
+
32
+
data/LICENSE.txt ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2013 Mike Harris
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.rdoc ADDED
@@ -0,0 +1,19 @@
1
+ = fs_template
2
+
3
+ Description goes here.
4
+
5
+ == Contributing to fs_template
6
+
7
+ * Check out the latest master to make sure the feature hasn't been implemented or the bug hasn't been fixed yet.
8
+ * Check out the issue tracker to make sure someone already hasn't requested it and/or contributed it.
9
+ * Fork the project.
10
+ * Start a feature/bugfix branch.
11
+ * Commit and push until you are happy with your contribution.
12
+ * Make sure to add tests for it. This is important so I don't break it in a future version unintentionally.
13
+ * Please try not to mess with the Rakefile, version, or history. If you want to have your own version, or is otherwise necessary, that is fine, but please isolate to its own commit so I can cherry-pick around it.
14
+
15
+ == Copyright
16
+
17
+ Copyright (c) 2013 Mike Harris. See LICENSE.txt for
18
+ further details.
19
+
data/Rakefile ADDED
@@ -0,0 +1,49 @@
1
+ # encoding: utf-8
2
+
3
+ require 'rubygems'
4
+ require 'bundler'
5
+ begin
6
+ Bundler.setup(:default, :development)
7
+ rescue Bundler::BundlerError => e
8
+ $stderr.puts e.message
9
+ $stderr.puts "Run `bundle install` to install missing gems"
10
+ exit e.status_code
11
+ end
12
+ require 'rake'
13
+
14
+ require 'jeweler'
15
+ Jeweler::Tasks.new do |gem|
16
+ # gem is a Gem::Specification... see http://docs.rubygems.org/read/chapter/20 for more options
17
+ gem.name = "fs_template"
18
+ gem.homepage = "http://github.com/mharris717/fs_template"
19
+ gem.license = "MIT"
20
+ gem.summary = %Q{fs_template}
21
+ gem.description = %Q{fs_template}
22
+ gem.email = "mharris717@gmail.com"
23
+ gem.authors = ["Mike Harris"]
24
+ # dependencies defined in Gemfile
25
+ end
26
+ Jeweler::RubygemsDotOrgTasks.new
27
+
28
+ require 'rspec/core'
29
+ require 'rspec/core/rake_task'
30
+ RSpec::Core::RakeTask.new(:spec) do |spec|
31
+ spec.pattern = FileList['spec/**/*_spec.rb']
32
+ end
33
+
34
+ RSpec::Core::RakeTask.new(:rcov) do |spec|
35
+ spec.pattern = 'spec/**/*_spec.rb'
36
+ spec.rcov = true
37
+ end
38
+
39
+ task :default => :spec
40
+
41
+ require 'rdoc/task'
42
+ Rake::RDocTask.new do |rdoc|
43
+ version = File.exist?('VERSION') ? File.read('VERSION') : ""
44
+
45
+ rdoc.rdoc_dir = 'rdoc'
46
+ rdoc.title = "fs_template #{version}"
47
+ rdoc.rdoc_files.include('README*')
48
+ rdoc.rdoc_files.include('lib/**/*.rb')
49
+ end
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.1.0
data/bin/fs_template ADDED
@@ -0,0 +1,5 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ load File.dirname(__FILE__) + "/../lib/fs_template.rb"
4
+
5
+ FsTemplate.write_project ARGV[0],ARGV[1]
@@ -0,0 +1,102 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
4
+ # -*- encoding: utf-8 -*-
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = "fs_template"
8
+ s.version = "0.1.0"
9
+
10
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
+ s.authors = ["Mike Harris"]
12
+ s.date = "2013-10-29"
13
+ s.description = "fs_template"
14
+ s.email = "mharris717@gmail.com"
15
+ s.executables = ["fs_template"]
16
+ s.extra_rdoc_files = [
17
+ "LICENSE.txt",
18
+ "README.rdoc"
19
+ ]
20
+ s.files = [
21
+ ".document",
22
+ ".rspec",
23
+ "Gemfile",
24
+ "Gemfile.lock",
25
+ "Guardfile",
26
+ "LICENSE.txt",
27
+ "README.rdoc",
28
+ "Rakefile",
29
+ "VERSION",
30
+ "bin/fs_template",
31
+ "fs_template.gemspec",
32
+ "lib/fs_template.rb",
33
+ "lib/fs_template/files.rb",
34
+ "lib/fs_template/project.rb",
35
+ "lib/fs_template/template_file.rb",
36
+ "lib/fs_template/thor_file.rb",
37
+ "spec/fs_template_spec.rb",
38
+ "spec/input/top/.overlay",
39
+ "spec/input/top/b.txt",
40
+ "spec/input/top/c.txt",
41
+ "spec/input/top/place/d.txt",
42
+ "spec/project_note_spec.rb",
43
+ "spec/spec_helper.rb",
44
+ "spec/support/output_dir.rb",
45
+ "spec/support/setup.rb",
46
+ "vol/input/base/a.txt",
47
+ "vol/input/base/b.txt",
48
+ "vol/input/top/.fstemplate",
49
+ "vol/input/top/b.txt",
50
+ "vol/input/top/c.txt",
51
+ "vol/input/top/place/d.txt",
52
+ "vol/test_write.rb"
53
+ ]
54
+ s.homepage = "http://github.com/mharris717/fs_template"
55
+ s.licenses = ["MIT"]
56
+ s.require_paths = ["lib"]
57
+ s.rubygems_version = "2.0.7"
58
+ s.summary = "fs_template"
59
+
60
+ if s.respond_to? :specification_version then
61
+ s.specification_version = 4
62
+
63
+ if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
64
+ s.add_runtime_dependency(%q<mharris_ext>, [">= 0"])
65
+ s.add_runtime_dependency(%q<andand>, [">= 0"])
66
+ s.add_development_dependency(%q<rspec>, ["~> 2.8.0"])
67
+ s.add_development_dependency(%q<rdoc>, ["~> 3.12"])
68
+ s.add_development_dependency(%q<bundler>, [">= 1.0.0"])
69
+ s.add_development_dependency(%q<jeweler>, ["~> 1.8.4"])
70
+ s.add_development_dependency(%q<guard>, [">= 0"])
71
+ s.add_development_dependency(%q<guard-rspec>, [">= 0"])
72
+ s.add_development_dependency(%q<guard-spork>, [">= 0"])
73
+ s.add_development_dependency(%q<rb-fsevent>, ["~> 0.9"])
74
+ s.add_development_dependency(%q<lre>, [">= 0"])
75
+ else
76
+ s.add_dependency(%q<mharris_ext>, [">= 0"])
77
+ s.add_dependency(%q<andand>, [">= 0"])
78
+ s.add_dependency(%q<rspec>, ["~> 2.8.0"])
79
+ s.add_dependency(%q<rdoc>, ["~> 3.12"])
80
+ s.add_dependency(%q<bundler>, [">= 1.0.0"])
81
+ s.add_dependency(%q<jeweler>, ["~> 1.8.4"])
82
+ s.add_dependency(%q<guard>, [">= 0"])
83
+ s.add_dependency(%q<guard-rspec>, [">= 0"])
84
+ s.add_dependency(%q<guard-spork>, [">= 0"])
85
+ s.add_dependency(%q<rb-fsevent>, ["~> 0.9"])
86
+ s.add_dependency(%q<lre>, [">= 0"])
87
+ end
88
+ else
89
+ s.add_dependency(%q<mharris_ext>, [">= 0"])
90
+ s.add_dependency(%q<andand>, [">= 0"])
91
+ s.add_dependency(%q<rspec>, ["~> 2.8.0"])
92
+ s.add_dependency(%q<rdoc>, ["~> 3.12"])
93
+ s.add_dependency(%q<bundler>, [">= 1.0.0"])
94
+ s.add_dependency(%q<jeweler>, ["~> 1.8.4"])
95
+ s.add_dependency(%q<guard>, [">= 0"])
96
+ s.add_dependency(%q<guard-rspec>, [">= 0"])
97
+ s.add_dependency(%q<guard-spork>, [">= 0"])
98
+ s.add_dependency(%q<rb-fsevent>, ["~> 0.9"])
99
+ s.add_dependency(%q<lre>, [">= 0"])
100
+ end
101
+ end
102
+
@@ -0,0 +1,79 @@
1
+ module FsTemplate
2
+ class Files
3
+ include FromHash
4
+ fattr(:files) { [] }
5
+ fattr(:file_class) { TemplateFile }
6
+ def add(ops)
7
+ files << file_class.new(:path => ops[:file], :full_body => ops[:body])
8
+ end
9
+ def size
10
+ files.size
11
+ end
12
+ def apply(on_top)
13
+ res = files.clone
14
+ on_top.each do |top_file|
15
+ existing = res.find { |x| x.path == top_file.path }
16
+ if existing
17
+ res -= [existing]
18
+ res << top_file.combined(existing)
19
+ else
20
+ res << top_file
21
+ end
22
+ end
23
+ self.class.new(:files => res)
24
+ end
25
+ def each(&b)
26
+ files.each(&b)
27
+ end
28
+
29
+ def write_to!(dir)
30
+ each do |f|
31
+ f.write_to! dir
32
+ end
33
+ end
34
+
35
+ class << self
36
+ def dir_files(dir)
37
+ res = Dir["#{dir}/**/*"] + Dir["#{dir}/**/.*"]
38
+ res - [".","..",".git"]
39
+ end
40
+ def load_dir(dir)
41
+ raise "Bad dir" unless dir.present?
42
+ raise "Dir not there" unless FileTest.exist?(dir)
43
+ res = new
44
+ dir_files(dir).each do |full_file|
45
+ if FileTest.file?(full_file)
46
+ f = full_file.gsub("#{dir}/","")
47
+ raise "bad #{f}" if f == full_file
48
+ res.add :file => f, :body => File.read(full_file)
49
+ end
50
+ end
51
+ res
52
+ end
53
+
54
+ def load(descriptor)
55
+ raise "bad #{descriptor}" if descriptor.blank?
56
+ if descriptor =~ /\.git/
57
+ load_repo(descriptor)
58
+ else
59
+ load_dir(descriptor)
60
+ end
61
+ end
62
+
63
+ def write_combined(base_dir, top_dir, output_dir)
64
+ base = load(base_dir)
65
+ top = load(top_dir)
66
+ combined = base.apply(top)
67
+ combined.write_to! output_dir
68
+ end
69
+
70
+ def load_repo(url)
71
+ dir = "/tmp/#{rand(1000000000000000000)}"
72
+ ec "git clone #{url} #{dir} 2>&1", :silent => true
73
+ load dir
74
+ ensure
75
+ ec "rm -rf #{dir}", :silent => true
76
+ end
77
+ end
78
+ end
79
+ end
@@ -0,0 +1,74 @@
1
+ module FsTemplate
2
+ class Project
3
+ include FromHash
4
+ attr_accessor :path
5
+
6
+ def config_body
7
+ if FileTest.exist?("#{path}/.fstemplate")
8
+ File.read("#{path}/.fstemplate")
9
+ elsif FileTest.exist?("#{path}/.overlay")
10
+ File.read("#{path}/.overlay")
11
+ else
12
+ raise "no config"
13
+ end
14
+ end
15
+
16
+ fattr(:config) do
17
+ res = ProjectConfig.new
18
+ res.body = config_body
19
+ res.load!
20
+ res
21
+ end
22
+
23
+ def overlay_paths
24
+ config.overlays + [path]
25
+ end
26
+
27
+ fattr(:overlays) do
28
+ overlay_paths.map { |x| Files.load(x) }
29
+ end
30
+
31
+ fattr(:base_files) do
32
+ Files.load(config.base)
33
+ end
34
+
35
+ fattr(:combined_files) do
36
+ res = base_files
37
+ overlays.each do |overlay|
38
+ res = res.apply(overlay)
39
+ end
40
+ res
41
+ end
42
+
43
+ def write_to!(output_path)
44
+ base_files.write_to! output_path
45
+ `rm -rf #{output_path}/.git`
46
+ ec "cd #{output_path} && git init && git add . && git commit -m 'Base Files #{config.base}'", :silent => true
47
+ combined_files.write_to!(output_path)
48
+ ec "cd #{output_path} && git add . && git commit -m 'Overlay Files #{path}'", :silent => true
49
+ end
50
+ end
51
+
52
+ class ProjectConfig
53
+ include FromHash
54
+ attr_accessor :body, :base
55
+ fattr(:overlays) { [] }
56
+
57
+ def base(*args)
58
+ if args.empty?
59
+ @base
60
+ else
61
+ @base = args.first
62
+ end
63
+ end
64
+
65
+ def overlay(name)
66
+ self.overlays << name
67
+ end
68
+
69
+ def load!
70
+ c = self
71
+ eval(body)
72
+ end
73
+ end
74
+ end
@@ -0,0 +1,114 @@
1
+ module FsTemplate
2
+ class TemplateFile
3
+ include FromHash
4
+ attr_accessor :path, :full_body
5
+
6
+ module NewWay
7
+ def split_note_and_body_long
8
+ if full_body =~ /<overlay>(.+)<\/overlay>/m
9
+ note = $1
10
+ rest = full_body.gsub(/<overlay>.+<\/overlay>/m,"")
11
+ {:note => note, :body => rest, :format => :long}
12
+ else
13
+ nil
14
+ end
15
+ end
16
+
17
+ def note_params
18
+ res = {}
19
+ lines = note.split("\n").select { |x| x.present? }
20
+ if lines.size == 1
21
+ res[:action] = lines.first.strip
22
+ else
23
+ lines.each do |line|
24
+ parts = line.split(":").map { |x| x.strip }.select { |x| x.present? }
25
+ raise "bad" unless parts.size == 2
26
+ res[parts[0].to_sym] = parts[1]
27
+ end
28
+ end
29
+ res
30
+ end
31
+
32
+
33
+ def apply_body_to_long(base_body)
34
+ params = note_params
35
+ if note == 'append'
36
+ base_body + body
37
+ elsif params[:action] == 'insert' && params[:after]
38
+ base_body.gsub(params[:after],"#{params[:after]}#{body}").tap do |subbed|
39
+ if subbed == base_body
40
+ raise "no change, couldn't find #{params[:after]} in \n#{base_body}"
41
+ end
42
+ end
43
+ else
44
+ raise "bad"
45
+ end
46
+ end
47
+ end
48
+
49
+ module OldWay
50
+ def split_note_and_body_short
51
+ if full_body =~ /^FSTMODE:([a-z:0-9]+)\s/m
52
+ note = $1
53
+ rest = full_body.gsub(/^FSTMODE:#{note}/,"")
54
+ {:note => note, :body => rest, :format => :short}
55
+ else
56
+ nil
57
+ end
58
+ end
59
+
60
+ def apply_body_to_short(base_body)
61
+ note_parts = note.to_s.split(":")
62
+ if note == 'append'
63
+ base_body + body
64
+ elsif note_parts[0] == 'insert'
65
+ raise "bad" unless note_parts[1] == 'line'
66
+ base_lines = base_body.split("\n")
67
+ i = note_parts[2].to_i - 1
68
+ base_lines[0...i].join("\n") + body + base_lines[i..-1].join("\n")
69
+ else
70
+ raise "unknown note #{note}"
71
+ end
72
+ end
73
+ end
74
+
75
+ include OldWay
76
+ include NewWay
77
+
78
+ def split_note_and_body
79
+ [:split_note_and_body_short,:split_note_and_body_long].each do |meth|
80
+ res = send(meth)
81
+ return res if res
82
+ end
83
+ {:note => nil, :body => full_body}
84
+ end
85
+
86
+ fattr(:split_parts) { split_note_and_body }
87
+
88
+ fattr(:body) { split_parts[:body] }
89
+ fattr(:note) { split_parts[:note] }
90
+ fattr(:format) { split_parts[:format] }
91
+
92
+ def apply_body_to(base_body)
93
+ if note.present?
94
+ m = "apply_body_to_#{format}"
95
+ send(m,base_body)
96
+ else
97
+ body
98
+ end
99
+ end
100
+
101
+
102
+
103
+ def combined(base)
104
+ self.class.new(:path => path, :full_body => apply_body_to(base.body))
105
+ end
106
+
107
+ def write_to!(dir)
108
+ raise "bad path" if path.blank?
109
+ d = File.dirname("#{dir}/#{path}")
110
+ `mkdir -p #{d}`
111
+ File.create "#{dir}/#{path}",body
112
+ end
113
+ end
114
+ end
File without changes
@@ -0,0 +1,13 @@
1
+ require 'mharris_ext'
2
+
3
+ %w(files template_file thor_file project).each do |f|
4
+ load File.dirname(__FILE__) + "/fs_template/#{f}.rb"
5
+ end
6
+
7
+ module FsTemplate
8
+ class << self
9
+ def write_project(overlay_path,output_path)
10
+ FsTemplate::Project.new(:path => overlay_path).write_to!(output_path)
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,148 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe "FsTemplate" do
4
+ include_context "setup"
5
+
6
+ it 'smoke' do
7
+ 2.should == 2
8
+ end
9
+
10
+ base_file "a.txt","stuff"
11
+ on_top_file "b.txt","other"
12
+
13
+ it 'base files' do
14
+ base.files.size.should == 1
15
+ end
16
+
17
+ it 'top files' do
18
+ on_top.files.size.should == 1
19
+ end
20
+
21
+ it 'combined' do
22
+ combined.size.should == 2
23
+ end
24
+ end
25
+
26
+ describe "combine" do
27
+ include_context "setup"
28
+
29
+ base_file "a.txt","stuff"
30
+ base_file "b.txt","here"
31
+ on_top_file "b.txt","other"
32
+
33
+ it 'combined size' do
34
+ combined.size.should == 2
35
+ end
36
+
37
+ it 'combined file should overwrite' do
38
+ f = combined.files.find { |x| x.path == "b.txt" }
39
+ f.body.should == 'other'
40
+ end
41
+ end
42
+
43
+ describe "dotfile" do
44
+ include_context "setup"
45
+
46
+ base_file ".abc","stuff"
47
+ base_file "b.txt","here"
48
+ on_top_file "c.txt","other"
49
+
50
+ it 'combined size' do
51
+ combined.size.should == 3
52
+ end
53
+
54
+ it 'dotfile there' do
55
+ f = combined.files.find { |x| x.path == ".abc" }
56
+ f.body.should == 'stuff'
57
+ end
58
+ end
59
+
60
+ describe "combine - append" do
61
+ include_context "setup"
62
+
63
+ base_file "a.txt","stuff"
64
+ base_file "b.txt","here"
65
+ on_top_file "b.txt","FSTMODE:append\nother"
66
+
67
+ it 'combined size' do
68
+ combined.size.should == 2
69
+ end
70
+
71
+ it 'combined file should overwrite' do
72
+ f = combined.files.find { |x| x.path == "b.txt" }
73
+ f.body.should == "here\nother"
74
+ end
75
+ end
76
+
77
+ describe "combine - append format2" do
78
+ include_context "setup"
79
+
80
+ base_file "a.txt","stuff"
81
+ base_file "b.txt","here"
82
+ on_top_file "b.txt","<overlay>append</overlay>\nother"
83
+
84
+ it 'combined size' do
85
+ combined.size.should == 2
86
+ end
87
+
88
+ it 'combined file should overwrite' do
89
+ f = combined.files.find { |x| x.path == "b.txt" }
90
+ f.body.should == "here\nother"
91
+ end
92
+ end
93
+
94
+ describe "combine - insert" do
95
+ include_context "setup"
96
+
97
+ base_file "a.txt","stuff"
98
+ base_file "b.txt","a\nb\nc\nd"
99
+ on_top_file "b.txt","FSTMODE:insert:line:2\nother\n"
100
+
101
+ it 'combined size' do
102
+ combined.size.should == 2
103
+ end
104
+
105
+ it 'combined file should overwrite' do
106
+ f = combined.files.find { |x| x.path == "b.txt" }
107
+ f.body.should == "a\nother\nb\nc\nd"
108
+ end
109
+ end
110
+
111
+ describe "combine - insert after" do
112
+ include_context "setup"
113
+
114
+ base_file "a.txt","stuff"
115
+ base_file "b.txt","123\n456\n789"
116
+ on_top_file "b.txt","<overlay>action: insert\nafter: 456</overlay>\nabc"
117
+
118
+ it 'combined size' do
119
+ combined.size.should == 2
120
+ end
121
+
122
+ it 'combined file should overwrite' do
123
+ f = combined.files.find { |x| x.path == "b.txt" }
124
+ f.body.should == "123\n456\nabc\n789"
125
+ end
126
+ end
127
+
128
+ describe "combine - top file in new dir" do
129
+ include_context "setup"
130
+
131
+ base_file "a.txt","stuff"
132
+ on_top_file "place/b.txt","Hello"
133
+
134
+ it 'combined size' do
135
+ combined.size.should == 2
136
+ end
137
+ end
138
+
139
+ describe "combine - error" do
140
+ include_context "setup"
141
+
142
+ base_file "a.txt","stuff"
143
+ on_top_file "a.txt","FSTMODE:fgdfgdfg\nstuff"
144
+
145
+ it 'combined size' do
146
+ lambda { combined.size }.should raise_error
147
+ end
148
+ end
@@ -0,0 +1 @@
1
+ c.base "file:///code/orig/fs_template/spec/input/repo/.git"
@@ -0,0 +1,6 @@
1
+ <overlay>
2
+ action: insert
3
+ after: a
4
+ </overlay>
5
+ 1
6
+ 2
@@ -0,0 +1 @@
1
+ C Stuff
@@ -0,0 +1 @@
1
+ Hello
@@ -0,0 +1,117 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe "ProjectConfig" do
4
+ let(:config) do
5
+ res = FsTemplate::ProjectConfig.new
6
+ res.body = config_body
7
+ res
8
+ end
9
+
10
+ describe "one base" do
11
+ let(:config_body) do
12
+ "c.base :foo"
13
+ end
14
+
15
+ it 'smoke' do
16
+ config.should be
17
+ end
18
+
19
+ it 'eval' do
20
+ config.load!
21
+ config.base.should == :foo
22
+ end
23
+ end
24
+
25
+ describe "base and overlay" do
26
+ let(:config_body) do
27
+ "c.base :foo
28
+ c.overlay :bar"
29
+ end
30
+
31
+ it 'eval' do
32
+ config.load!
33
+ config.base.should == :foo
34
+ config.overlays.should == [:bar]
35
+ end
36
+ end
37
+
38
+ it 'project no config' do
39
+ lambda { FsTemplate::Project.new.config }.should raise_error
40
+ end
41
+ end
42
+
43
+ describe 'Project' do
44
+ let(:config_body) do
45
+ "c.base :foo
46
+ c.overlay :bar"
47
+ end
48
+
49
+ let(:project) do
50
+ res = FsTemplate::Project.new(:path => "/fun")
51
+ res.stub(:config_body) { config_body }
52
+ res
53
+ end
54
+
55
+ before do
56
+ FsTemplate::Files.stub(:load) { FsTemplate::Files.new }
57
+ end
58
+
59
+ it 'overlays' do
60
+ project.overlays.size.should == 2
61
+ project.overlay_paths.last.should == "/fun"
62
+ end
63
+ end
64
+
65
+ describe "write project" do
66
+ include_context "output dir"
67
+
68
+ let(:repo_dir) do
69
+ "#{input_dir}/repo"
70
+ end
71
+ let(:input_dir) do
72
+ File.expand_path(File.dirname(__FILE__) + "/input")
73
+ end
74
+ let(:overlay_dir) do
75
+ "#{input_dir}/top"
76
+ end
77
+
78
+ def files_equal(source_dir,target_dir,file)
79
+ source = File.read("#{source_dir}/#{file}")
80
+ target = File.read("#{target_dir}/#{file}")
81
+ FileTest.should be_exist("#{target_dir}/#{file}")
82
+ source.should == target
83
+ end
84
+
85
+ describe "from git" do
86
+ before do
87
+ FsTemplate.write_project overlay_dir, output_dir
88
+ end
89
+
90
+ it 'has README' do
91
+ files_equal repo_dir, output_dir, "README.md"
92
+ end
93
+
94
+ it 'c.txt' do
95
+ files_equal overlay_dir, output_dir, "c.txt"
96
+ end
97
+
98
+ it 'b.txt insert' do
99
+ File.read("#{output_dir}/b.txt").should == %w(a 1 2 b c d).join("\n") + "\n"
100
+ end
101
+ end
102
+
103
+ describe "from combined" do
104
+ before do
105
+ FsTemplate::Files.write_combined repo_dir,overlay_dir,output_dir
106
+ end
107
+
108
+ it 'has README' do
109
+ files_equal repo_dir, output_dir, "README.md"
110
+ end
111
+
112
+ it 'has .abc' do
113
+ files_equal repo_dir, output_dir, ".abc"
114
+ end
115
+
116
+ end
117
+ end
@@ -0,0 +1,33 @@
1
+ require 'rubygems'
2
+ require 'spork'
3
+
4
+
5
+ Spork.prefork do
6
+ unless ENV['DRB']
7
+ require 'simplecov'
8
+ SimpleCov.start
9
+ end
10
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
11
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
12
+
13
+ require 'rspec'
14
+
15
+
16
+ # Requires supporting files with custom matchers and macros, etc,
17
+ # in ./support/ and its subdirectories.
18
+ Dir["#{File.dirname(__FILE__)}/support/**/*.rb"].each {|f| require f}
19
+
20
+ RSpec.configure do |config|
21
+ #config.filter_run :focus => true
22
+ config.fail_fast = false
23
+ end
24
+ end
25
+
26
+ Spork.each_run do
27
+ if ENV['DRB']
28
+ require 'simplecov'
29
+ SimpleCov.start
30
+ end
31
+ load File.dirname(__FILE__) + "/../lib/fs_template.rb"
32
+ #Dir["#{File.dirname(__FILE__)}/support/**/*.rb"].each {|f| load f}
33
+ end
@@ -0,0 +1,14 @@
1
+ shared_context "output dir" do
2
+ def make_fresh_output_dir
3
+ `mkdir /tmp/fresh_output` unless FileTest.exist?("/tmp/fresh_output")
4
+ dir = "/tmp/fresh_output/#{rand(10000000000000)}"
5
+ `mkdir #{dir}`
6
+ dir
7
+ end
8
+
9
+ let(:output_dir) { make_fresh_output_dir }
10
+
11
+ after do
12
+ `rm -rf #{output_dir}`
13
+ end
14
+ end
@@ -0,0 +1,33 @@
1
+ shared_context "setup" do
2
+ class << self
3
+ fattr(:files) { [] }
4
+ def base_file(file,body)
5
+ self.files << {:loc => :base, :file => file, :body => body}
6
+ end
7
+ def on_top_file(file,body)
8
+ self.files << {:loc => :on_top, :file => file, :body => body}
9
+ end
10
+ end
11
+
12
+ let(:file_class) { FsTemplate::TemplateFile }
13
+
14
+ let(:base) do
15
+ res = FsTemplate::Files.new(:file_class => file_class)
16
+ self.class.files.select { |x| x[:loc] == :base }.each do |f|
17
+ res.add f
18
+ end
19
+ res
20
+ end
21
+
22
+ let(:on_top) do
23
+ res = FsTemplate::Files.new(:file_class => file_class)
24
+ self.class.files.select { |x| x[:loc] == :on_top }.each do |f|
25
+ res.add f
26
+ end
27
+ res
28
+ end
29
+
30
+ let(:combined) do
31
+ base.apply(on_top)
32
+ end
33
+ end
@@ -0,0 +1 @@
1
+ Stuff goes herezzz
@@ -0,0 +1,7 @@
1
+ More Stuff
2
+ a
3
+ b
4
+ c
5
+ d
6
+ e
7
+ f
@@ -0,0 +1 @@
1
+ c.base "https://github.com/mharris717/lre.git"
@@ -0,0 +1,3 @@
1
+ FSTMODE:insert:line:2
2
+ I don't belong here
3
+ Neither do I
@@ -0,0 +1 @@
1
+ C Stuff
@@ -0,0 +1 @@
1
+ Hello
data/vol/test_write.rb ADDED
@@ -0,0 +1,10 @@
1
+ load "lib/fs_template.rb"
2
+
3
+ dir = File.expand_path(File.dirname(__FILE__))
4
+
5
+ Dir["#{dir}/output/**/*.*"].each do |f|
6
+ `rm #{f}`
7
+ end
8
+
9
+ #FsTemplate::Files.write_combined "#{dir}/input/base","#{dir}/input/top","#{dir}/output"
10
+ FsTemplate.write_project "#{dir}/input/top","#{dir}/output"
metadata ADDED
@@ -0,0 +1,232 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: fs_template
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Mike Harris
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2013-10-29 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: mharris_ext
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ! '>='
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ! '>='
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: andand
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ! '>='
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ! '>='
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rspec
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ~>
46
+ - !ruby/object:Gem::Version
47
+ version: 2.8.0
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ~>
53
+ - !ruby/object:Gem::Version
54
+ version: 2.8.0
55
+ - !ruby/object:Gem::Dependency
56
+ name: rdoc
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ~>
60
+ - !ruby/object:Gem::Version
61
+ version: '3.12'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - ~>
67
+ - !ruby/object:Gem::Version
68
+ version: '3.12'
69
+ - !ruby/object:Gem::Dependency
70
+ name: bundler
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ! '>='
74
+ - !ruby/object:Gem::Version
75
+ version: 1.0.0
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ! '>='
81
+ - !ruby/object:Gem::Version
82
+ version: 1.0.0
83
+ - !ruby/object:Gem::Dependency
84
+ name: jeweler
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ~>
88
+ - !ruby/object:Gem::Version
89
+ version: 1.8.4
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ~>
95
+ - !ruby/object:Gem::Version
96
+ version: 1.8.4
97
+ - !ruby/object:Gem::Dependency
98
+ name: guard
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ! '>='
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ type: :development
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - ! '>='
109
+ - !ruby/object:Gem::Version
110
+ version: '0'
111
+ - !ruby/object:Gem::Dependency
112
+ name: guard-rspec
113
+ requirement: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - ! '>='
116
+ - !ruby/object:Gem::Version
117
+ version: '0'
118
+ type: :development
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - ! '>='
123
+ - !ruby/object:Gem::Version
124
+ version: '0'
125
+ - !ruby/object:Gem::Dependency
126
+ name: guard-spork
127
+ requirement: !ruby/object:Gem::Requirement
128
+ requirements:
129
+ - - ! '>='
130
+ - !ruby/object:Gem::Version
131
+ version: '0'
132
+ type: :development
133
+ prerelease: false
134
+ version_requirements: !ruby/object:Gem::Requirement
135
+ requirements:
136
+ - - ! '>='
137
+ - !ruby/object:Gem::Version
138
+ version: '0'
139
+ - !ruby/object:Gem::Dependency
140
+ name: rb-fsevent
141
+ requirement: !ruby/object:Gem::Requirement
142
+ requirements:
143
+ - - ~>
144
+ - !ruby/object:Gem::Version
145
+ version: '0.9'
146
+ type: :development
147
+ prerelease: false
148
+ version_requirements: !ruby/object:Gem::Requirement
149
+ requirements:
150
+ - - ~>
151
+ - !ruby/object:Gem::Version
152
+ version: '0.9'
153
+ - !ruby/object:Gem::Dependency
154
+ name: lre
155
+ requirement: !ruby/object:Gem::Requirement
156
+ requirements:
157
+ - - ! '>='
158
+ - !ruby/object:Gem::Version
159
+ version: '0'
160
+ type: :development
161
+ prerelease: false
162
+ version_requirements: !ruby/object:Gem::Requirement
163
+ requirements:
164
+ - - ! '>='
165
+ - !ruby/object:Gem::Version
166
+ version: '0'
167
+ description: fs_template
168
+ email: mharris717@gmail.com
169
+ executables:
170
+ - fs_template
171
+ extensions: []
172
+ extra_rdoc_files:
173
+ - LICENSE.txt
174
+ - README.rdoc
175
+ files:
176
+ - .document
177
+ - .rspec
178
+ - Gemfile
179
+ - Gemfile.lock
180
+ - Guardfile
181
+ - LICENSE.txt
182
+ - README.rdoc
183
+ - Rakefile
184
+ - VERSION
185
+ - bin/fs_template
186
+ - fs_template.gemspec
187
+ - lib/fs_template.rb
188
+ - lib/fs_template/files.rb
189
+ - lib/fs_template/project.rb
190
+ - lib/fs_template/template_file.rb
191
+ - lib/fs_template/thor_file.rb
192
+ - spec/fs_template_spec.rb
193
+ - spec/input/top/.overlay
194
+ - spec/input/top/b.txt
195
+ - spec/input/top/c.txt
196
+ - spec/input/top/place/d.txt
197
+ - spec/project_note_spec.rb
198
+ - spec/spec_helper.rb
199
+ - spec/support/output_dir.rb
200
+ - spec/support/setup.rb
201
+ - vol/input/base/a.txt
202
+ - vol/input/base/b.txt
203
+ - vol/input/top/.fstemplate
204
+ - vol/input/top/b.txt
205
+ - vol/input/top/c.txt
206
+ - vol/input/top/place/d.txt
207
+ - vol/test_write.rb
208
+ homepage: http://github.com/mharris717/fs_template
209
+ licenses:
210
+ - MIT
211
+ metadata: {}
212
+ post_install_message:
213
+ rdoc_options: []
214
+ require_paths:
215
+ - lib
216
+ required_ruby_version: !ruby/object:Gem::Requirement
217
+ requirements:
218
+ - - ! '>='
219
+ - !ruby/object:Gem::Version
220
+ version: '0'
221
+ required_rubygems_version: !ruby/object:Gem::Requirement
222
+ requirements:
223
+ - - ! '>='
224
+ - !ruby/object:Gem::Version
225
+ version: '0'
226
+ requirements: []
227
+ rubyforge_project:
228
+ rubygems_version: 2.0.7
229
+ signing_key:
230
+ specification_version: 4
231
+ summary: fs_template
232
+ test_files: []