giternal 0.0.1 → 0.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/.emacs-project +0 -0
- data/History.txt +7 -2
- data/Manifest.txt +8 -2
- data/README.txt +27 -4
- data/bin/giternal +17 -0
- data/config/hoe.rb +0 -1
- data/features/checking_out_externals.feature +25 -0
- data/features/freeze_externals.feature +19 -0
- data/features/steps/repository_steps.rb +105 -0
- data/features/unfreeze_externals.feature +12 -0
- data/giternal_helper.rb +108 -0
- data/lib/giternal/app.rb +27 -3
- data/lib/giternal/repository.rb +66 -8
- data/lib/giternal/version.rb +1 -1
- data/lib/giternal/yaml_config.rb +3 -2
- data/spec/giternal/app_spec.rb +38 -18
- data/spec/giternal/repository_spec.rb +96 -14
- data/spec/giternal/yaml_config_spec.rb +4 -3
- data/spec/spec_helper.rb +4 -26
- data/tasks/cucumber.rake +17 -0
- data/tasks/rspec.rake +12 -14
- metadata +15 -28
- data/PostInstall.txt +0 -8
- data/lib/tasks/giternal.rake +0 -8
data/.emacs-project
ADDED
File without changes
|
data/History.txt
CHANGED
data/Manifest.txt
CHANGED
@@ -1,17 +1,22 @@
|
|
1
|
+
.emacs-project
|
1
2
|
History.txt
|
2
3
|
License.txt
|
3
4
|
Manifest.txt
|
4
|
-
PostInstall.txt
|
5
5
|
README.txt
|
6
6
|
Rakefile
|
7
|
+
bin/giternal
|
7
8
|
config/hoe.rb
|
8
9
|
config/requirements.rb
|
10
|
+
features/checking_out_externals.feature
|
11
|
+
features/freeze_externals.feature
|
12
|
+
features/steps/repository_steps.rb
|
13
|
+
features/unfreeze_externals.feature
|
14
|
+
giternal_helper.rb
|
9
15
|
lib/giternal.rb
|
10
16
|
lib/giternal/app.rb
|
11
17
|
lib/giternal/repository.rb
|
12
18
|
lib/giternal/version.rb
|
13
19
|
lib/giternal/yaml_config.rb
|
14
|
-
lib/tasks/giternal.rake
|
15
20
|
script/console
|
16
21
|
script/destroy
|
17
22
|
script/generate
|
@@ -22,6 +27,7 @@ spec/giternal/repository_spec.rb
|
|
22
27
|
spec/giternal/yaml_config_spec.rb
|
23
28
|
spec/spec.opts
|
24
29
|
spec/spec_helper.rb
|
30
|
+
tasks/cucumber.rake
|
25
31
|
tasks/deployment.rake
|
26
32
|
tasks/environment.rake
|
27
33
|
tasks/rspec.rake
|
data/README.txt
CHANGED
@@ -26,17 +26,40 @@ rspec-rails:
|
|
26
26
|
repo: git://github.com/dchelimsky/rspec-rails.git
|
27
27
|
path: vendor/plugins
|
28
28
|
|
29
|
-
Now in project root, run '
|
29
|
+
Now in project root, run 'giternal update' to update all of your
|
30
30
|
git dependencies.
|
31
31
|
|
32
|
-
==
|
32
|
+
== FREEZING AND UNFREEZING:
|
33
33
|
|
34
|
-
|
34
|
+
Sometimes you want to freeze your dependencies, e.g. when deploying.
|
35
|
+
This lets you create a self-contained deploy tag with all externals at
|
36
|
+
a known, working version. giternal will tar up the .git history dir
|
37
|
+
for each external, and then add the external to your git index. You
|
38
|
+
can review all the changes before committing.
|
39
|
+
|
40
|
+
giternal freeze
|
41
|
+
|
42
|
+
Unfreezing, as you might guess, is the opposite of freezing. It will
|
43
|
+
remove your external dir from the git index, and extract each
|
44
|
+
external's .git dir, restoring the history and allowing you to commit
|
45
|
+
or fetch changes.
|
46
|
+
|
47
|
+
giternal unfreeze
|
48
|
+
|
49
|
+
== NOTES:
|
50
|
+
|
51
|
+
* You're probably using git for your own version control...and if so,
|
52
|
+
you need to add the giternal'd paths to .gitignore. You don't want
|
53
|
+
to check them into version control!!
|
54
|
+
|
55
|
+
* Deploying with vlad or capistrano simply requires you to run
|
56
|
+
'giternal update' after the code has been checked out, if your
|
57
|
+
externals are not frozen. If deploying a codebase with frozen
|
58
|
+
externals, there's nothing to do.
|
35
59
|
|
36
60
|
== INSTALL:
|
37
61
|
|
38
62
|
* sudo gem install giternal
|
39
|
-
* sudo sake -i 'http://giternal.rubyforge.org/git?p=giternal.git;a=blob_plain;f=lib/tasks/giternal.rake;hb=HEAD'
|
40
63
|
|
41
64
|
== LICENSE:
|
42
65
|
|
data/bin/giternal
ADDED
@@ -0,0 +1,17 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
require "rubygems"
|
3
|
+
if File.exist?(File.dirname(__FILE__) + '/../lib/giternal.rb')
|
4
|
+
$:.unshift(File.dirname(__FILE__) + '/../lib')
|
5
|
+
end
|
6
|
+
require 'giternal'
|
7
|
+
|
8
|
+
action = ARGV[0]
|
9
|
+
available_actions = %w(update freeze unfreeze)
|
10
|
+
unless available_actions.include?(action)
|
11
|
+
puts "Usage: giternal (#{available_actions.join(':')})"
|
12
|
+
exit 1
|
13
|
+
end
|
14
|
+
|
15
|
+
Giternal::Repository.verbose = true
|
16
|
+
app = Giternal::App.new(FileUtils.pwd)
|
17
|
+
app.run(action)
|
data/config/hoe.rb
CHANGED
@@ -8,7 +8,6 @@ RUBYFORGE_PROJECT = 'giternal' # The unix name for your project
|
|
8
8
|
HOMEPATH = "http://#{RUBYFORGE_PROJECT}.rubyforge.org"
|
9
9
|
DOWNLOAD_PATH = "http://rubyforge.org/projects/#{RUBYFORGE_PROJECT}"
|
10
10
|
EXTRA_DEPENDENCIES = [
|
11
|
-
['sake', '>= 1.0']
|
12
11
|
] # An array of rubygem dependencies [name, version]
|
13
12
|
|
14
13
|
@config_file = "~/.rubyforge/user-config.yml"
|
@@ -0,0 +1,25 @@
|
|
1
|
+
Feature: Checking out and updating externals
|
2
|
+
As a developer
|
3
|
+
I want to check out and update external projects via git
|
4
|
+
So that I can add functionality to my app with little effort
|
5
|
+
|
6
|
+
Scenario: Repository is not yet checked out
|
7
|
+
Given an external repository named 'first_external'
|
8
|
+
And 'first_external' is not yet checked out
|
9
|
+
When I update the externals
|
10
|
+
Then 'first_external' should be checked out
|
11
|
+
|
12
|
+
Scenario: Multiple externals
|
13
|
+
Given an external repository named 'first_external'
|
14
|
+
And an external repository named 'second_external'
|
15
|
+
When I update the externals
|
16
|
+
Then 'first_external' should be checked out
|
17
|
+
And 'second_external' should be checked out
|
18
|
+
|
19
|
+
Scenario: Repository checked out then updated
|
20
|
+
Given an external repository named 'first_external'
|
21
|
+
And the externals are up to date
|
22
|
+
And content is added to 'first_external'
|
23
|
+
Then 'first_external' should not be up to date
|
24
|
+
When I update the externals
|
25
|
+
Then 'first_external' should be up to date
|
@@ -0,0 +1,19 @@
|
|
1
|
+
Story: Freeze externals
|
2
|
+
As a developer
|
3
|
+
I want to freeze externals
|
4
|
+
So that I can test and deploy my app with no worries
|
5
|
+
|
6
|
+
Scenario: Main project has one external
|
7
|
+
Given an external repository named 'first_external'
|
8
|
+
And the externals are up to date
|
9
|
+
When I freeze the externals
|
10
|
+
Then 'first_external' should no longer be a git repo
|
11
|
+
And 'first_external' should be added to the commit index
|
12
|
+
|
13
|
+
Scenario: External has been added to .gitignore
|
14
|
+
Given an external repository named 'first_external'
|
15
|
+
And the external 'first_external' has been added to .gitignore
|
16
|
+
And the externals are up to date
|
17
|
+
When I freeze the externals
|
18
|
+
Then 'first_external' should be added to the commit index
|
19
|
+
|
@@ -0,0 +1,105 @@
|
|
1
|
+
require 'spec'
|
2
|
+
$:.unshift(File.dirname(__FILE__) + '/../../lib')
|
3
|
+
require 'giternal'
|
4
|
+
require 'giternal_helper'
|
5
|
+
|
6
|
+
def be_up_to_date
|
7
|
+
Spec::Matchers::SimpleMatcher.new("a giternal'd repository") do |repo_name|
|
8
|
+
File.directory?(GiternalHelper.checked_out_path(repo_name)).should == true
|
9
|
+
GiternalHelper.repo_contents(GiternalHelper.checked_out_path(repo_name)) ==
|
10
|
+
GiternalHelper.repo_contents(GiternalHelper.external_path(repo_name))
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
def be_a_git_repo
|
15
|
+
Spec::Matchers::SimpleMatcher.new("a giternal'd repository") do |repo_name|
|
16
|
+
File.directory?(GiternalHelper.checked_out_path(repo_name) + '/.git')
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
def be_added_to_commit_index
|
21
|
+
Spec::Matchers::SimpleMatcher.new("a giternal'd repository") do |repo_name|
|
22
|
+
Dir.chdir(GiternalHelper.tmp_path + '/main_repo') do
|
23
|
+
status = `git status`
|
24
|
+
flattened_status = status.split("\n").join(" ")
|
25
|
+
to_be_committed_regex = /new file:\W+dependencies\/#{repo_name}/
|
26
|
+
untracked_files_regex = /Untracked files:.*#{repo_name}/
|
27
|
+
status =~ to_be_committed_regex && !(flattened_status =~ untracked_files_regex)
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
Before do
|
33
|
+
GiternalHelper.clean!
|
34
|
+
GiternalHelper.create_main_repo
|
35
|
+
end
|
36
|
+
|
37
|
+
After do
|
38
|
+
GiternalHelper.clean!
|
39
|
+
end
|
40
|
+
|
41
|
+
Given /an external repository named '(.*)'/ do |repo_name|
|
42
|
+
GiternalHelper.create_repo repo_name
|
43
|
+
GiternalHelper.add_content repo_name
|
44
|
+
end
|
45
|
+
|
46
|
+
Given /'(.*)' is not yet checked out/ do |repo_name|
|
47
|
+
# TODO: Figure out why I can't use should be_false here
|
48
|
+
File.directory?(GiternalHelper.checked_out_path(repo_name)).should == false
|
49
|
+
end
|
50
|
+
|
51
|
+
Given "the externals are up to date" do
|
52
|
+
GiternalHelper.update_externals
|
53
|
+
end
|
54
|
+
|
55
|
+
Given "the externals are frozen" do
|
56
|
+
GiternalHelper.freeze_externals
|
57
|
+
end
|
58
|
+
|
59
|
+
Given /content is added to '(.*)'/ do |repo_name|
|
60
|
+
GiternalHelper.add_content(repo_name)
|
61
|
+
end
|
62
|
+
|
63
|
+
Given /^the external '(.*)' has been added to \.gitignore$/ do |repo_name|
|
64
|
+
GiternalHelper.add_external_to_ignore(repo_name)
|
65
|
+
end
|
66
|
+
|
67
|
+
When "I update the externals" do
|
68
|
+
GiternalHelper.update_externals
|
69
|
+
end
|
70
|
+
|
71
|
+
When "I freeze the externals" do
|
72
|
+
GiternalHelper.freeze_externals
|
73
|
+
end
|
74
|
+
|
75
|
+
When "I unfreeze the externals" do
|
76
|
+
GiternalHelper.unfreeze_externals
|
77
|
+
end
|
78
|
+
|
79
|
+
Then /'(.*)' should be checked out/ do |repo_name|
|
80
|
+
repo_name.should be_up_to_date
|
81
|
+
end
|
82
|
+
|
83
|
+
Then /'(.*)' should be up to date/ do |repo_name|
|
84
|
+
repo_name.should be_up_to_date
|
85
|
+
end
|
86
|
+
|
87
|
+
Then /'(.*)' should not be up to date/ do |repo_name|
|
88
|
+
repo_name.should_not be_up_to_date
|
89
|
+
end
|
90
|
+
|
91
|
+
Then /'(.*)' should no longer be a git repo/ do |repo_name|
|
92
|
+
repo_name.should_not be_a_git_repo
|
93
|
+
end
|
94
|
+
|
95
|
+
Then /'(.*)' should be a git repo/ do |repo_name|
|
96
|
+
repo_name.should be_a_git_repo
|
97
|
+
end
|
98
|
+
|
99
|
+
Then /'(.*)' should be added to the commit index/ do |repo_name|
|
100
|
+
repo_name.should be_added_to_commit_index
|
101
|
+
end
|
102
|
+
|
103
|
+
Then /'(.*)' should be removed from the commit index/ do |repo_name|
|
104
|
+
repo_name.should_not be_added_to_commit_index
|
105
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
Story: Unfreeze externals
|
2
|
+
As a developer
|
3
|
+
I want to unfreeze externals
|
4
|
+
So that I can continue to update and develop on them
|
5
|
+
|
6
|
+
Scenario: Main project has one frozen external
|
7
|
+
Given an external repository named 'first_external'
|
8
|
+
And the externals are up to date
|
9
|
+
And the externals are frozen
|
10
|
+
When I unfreeze the externals
|
11
|
+
Then 'first_external' should be a git repo
|
12
|
+
And 'first_external' should be removed from the commit index
|
data/giternal_helper.rb
ADDED
@@ -0,0 +1,108 @@
|
|
1
|
+
class GiternalHelper
|
2
|
+
@@giternal_base = File.expand_path(File.dirname(__FILE__))
|
3
|
+
|
4
|
+
def self.create_main_repo
|
5
|
+
FileUtils.mkdir_p tmp_path
|
6
|
+
Dir.chdir(tmp_path) do
|
7
|
+
FileUtils.mkdir "main_repo"
|
8
|
+
Dir.chdir('main_repo') do
|
9
|
+
`git init`
|
10
|
+
`echo 'first content' > starter_repo`
|
11
|
+
`git add starter_repo`
|
12
|
+
`git commit -m "starter repo"`
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
def self.wipe_repos
|
18
|
+
FileUtils.rm_r(tmp_path) if File.directory?(tmp_path)
|
19
|
+
end
|
20
|
+
|
21
|
+
def self.tmp_path
|
22
|
+
"/tmp/giternal_test"
|
23
|
+
end
|
24
|
+
|
25
|
+
def self.giternal_base
|
26
|
+
@@giternal_base
|
27
|
+
end
|
28
|
+
|
29
|
+
def self.base_project_dir
|
30
|
+
tmp_path + '/main_repo'
|
31
|
+
end
|
32
|
+
|
33
|
+
def self.run(*args)
|
34
|
+
`#{giternal_base}/bin/giternal #{args.join(' ')}`
|
35
|
+
end
|
36
|
+
|
37
|
+
def self.create_repo(repo_name)
|
38
|
+
Dir.chdir(tmp_path) do
|
39
|
+
FileUtils.mkdir_p "externals/#{repo_name}"
|
40
|
+
`cd externals/#{repo_name} && git init`
|
41
|
+
end
|
42
|
+
add_content repo_name
|
43
|
+
add_to_config_file repo_name
|
44
|
+
end
|
45
|
+
|
46
|
+
def self.add_to_config_file(repo_name)
|
47
|
+
config_dir = tmp_path + '/main_repo/config'
|
48
|
+
FileUtils.mkdir(config_dir) unless File.directory?(config_dir)
|
49
|
+
Dir.chdir(config_dir) do
|
50
|
+
`echo #{repo_name}: >> giternal.yml`
|
51
|
+
`echo ' repo: #{external_path(repo_name)}' >> giternal.yml`
|
52
|
+
`echo ' path: dependencies' >> giternal.yml`
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
def self.add_content(repo_name, content=repo_name)
|
57
|
+
Dir.chdir(tmp_path + "/externals/#{repo_name}") do
|
58
|
+
`echo #{content} >> #{content} && git add #{content}`
|
59
|
+
`git commit #{content} -m "added content to #{content}"`
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
def self.external_path(repo_name)
|
64
|
+
File.expand_path(tmp_path + "/externals/#{repo_name}")
|
65
|
+
end
|
66
|
+
|
67
|
+
def self.checked_out_path(repo_name)
|
68
|
+
File.expand_path(tmp_path + "/main_repo/dependencies/#{repo_name}")
|
69
|
+
end
|
70
|
+
|
71
|
+
def self.clean!
|
72
|
+
FileUtils.rm_rf tmp_path
|
73
|
+
end
|
74
|
+
|
75
|
+
def self.update_externals
|
76
|
+
Dir.chdir(tmp_path + '/main_repo') do
|
77
|
+
GiternalHelper.run('update')
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
def self.freeze_externals
|
82
|
+
Dir.chdir(tmp_path + '/main_repo') do
|
83
|
+
GiternalHelper.run('freeze')
|
84
|
+
end
|
85
|
+
end
|
86
|
+
|
87
|
+
def self.unfreeze_externals
|
88
|
+
Dir.chdir(tmp_path + '/main_repo') do
|
89
|
+
GiternalHelper.run('unfreeze')
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
def self.repo_contents(path)
|
94
|
+
Dir.chdir(path) do
|
95
|
+
contents = `git cat-file -p HEAD`
|
96
|
+
unless contents.include?('tree') && contents.include?('author')
|
97
|
+
raise "something is wrong with the repo, output doesn't contain expected git elements:\n\n #{contents}"
|
98
|
+
end
|
99
|
+
contents
|
100
|
+
end
|
101
|
+
end
|
102
|
+
|
103
|
+
def self.add_external_to_ignore(repo_name)
|
104
|
+
Dir.chdir(tmp_path + '/main_repo') do
|
105
|
+
`echo 'dependencies/#{repo_name}' >> .gitignore`
|
106
|
+
end
|
107
|
+
end
|
108
|
+
end
|
data/lib/giternal/app.rb
CHANGED
@@ -4,15 +4,39 @@ module Giternal
|
|
4
4
|
@base_dir = base_dir
|
5
5
|
end
|
6
6
|
|
7
|
-
def
|
7
|
+
def update
|
8
|
+
config.each_repo {|r| r.update }
|
9
|
+
end
|
10
|
+
|
11
|
+
def freezify
|
12
|
+
config.each_repo {|r| r.freezify }
|
13
|
+
end
|
14
|
+
|
15
|
+
def unfreezify
|
16
|
+
config.each_repo {|r| r.unfreezify }
|
17
|
+
end
|
18
|
+
|
19
|
+
def run(action)
|
20
|
+
case action
|
21
|
+
when "freeze"
|
22
|
+
freezify
|
23
|
+
when "unfreeze"
|
24
|
+
unfreezify
|
25
|
+
else
|
26
|
+
send(action)
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
def config
|
31
|
+
return @config if @config
|
32
|
+
|
8
33
|
config_file = File.expand_path(@base_dir + '/config/giternal.yml')
|
9
34
|
unless File.file?(config_file)
|
10
35
|
$stderr.puts "config/giternal.yml is missing"
|
11
36
|
exit 1
|
12
37
|
end
|
13
38
|
|
14
|
-
config = YamlConfig.new File.read(config_file)
|
15
|
-
config.each_repo {|r| r.update(@base_dir) }
|
39
|
+
@config = YamlConfig.new(@base_dir, File.read(config_file))
|
16
40
|
end
|
17
41
|
end
|
18
42
|
end
|
data/lib/giternal/repository.rb
CHANGED
@@ -1,24 +1,82 @@
|
|
1
|
+
require 'fileutils'
|
2
|
+
|
1
3
|
module Giternal
|
2
4
|
class Repository
|
3
|
-
|
5
|
+
class << self
|
6
|
+
attr_accessor :verbose
|
7
|
+
end
|
8
|
+
attr_accessor :verbose
|
9
|
+
|
10
|
+
def initialize(base_dir, name, repo_url, rel_path)
|
11
|
+
@base_dir = base_dir
|
4
12
|
@name = name
|
5
13
|
@repo_url = repo_url
|
6
14
|
@rel_path = rel_path
|
15
|
+
@verbose = self.class.verbose
|
7
16
|
end
|
8
17
|
|
9
|
-
def update
|
10
|
-
|
11
|
-
FileUtils.mkdir_p
|
12
|
-
if
|
13
|
-
if !File.exist?(
|
18
|
+
def update
|
19
|
+
return true if frozen?
|
20
|
+
FileUtils.mkdir_p checkout_path unless File.exist?(checkout_path)
|
21
|
+
if checked_out?
|
22
|
+
if !File.exist?(repo_path + '/.git')
|
14
23
|
raise "Directory '#{@name}' exists but is not a git repository"
|
15
24
|
else
|
16
|
-
|
25
|
+
update_output { `cd #{repo_path} && git pull 2>&1` }
|
17
26
|
end
|
18
27
|
else
|
19
|
-
`cd #{
|
28
|
+
update_output { `cd #{checkout_path} && git clone #{@repo_url} #{@name}` }
|
29
|
+
end
|
30
|
+
true
|
31
|
+
end
|
32
|
+
|
33
|
+
def freezify
|
34
|
+
return true if frozen? || !checked_out?
|
35
|
+
|
36
|
+
Dir.chdir(repo_path) do
|
37
|
+
`tar czf .git.frozen.tgz .git`
|
38
|
+
FileUtils.rm_r('.git')
|
39
|
+
end
|
40
|
+
`cd #{@base_dir} && git add -f #{rel_repo_path}`
|
41
|
+
true
|
42
|
+
end
|
43
|
+
|
44
|
+
def unfreezify
|
45
|
+
return true unless frozen?
|
46
|
+
|
47
|
+
Dir.chdir(repo_path) do
|
48
|
+
`tar xzf .git.frozen.tgz`
|
49
|
+
FileUtils.rm('.git.frozen.tgz')
|
20
50
|
end
|
51
|
+
`cd #{@base_dir} && git rm -r --cached #{rel_repo_path}`
|
21
52
|
true
|
22
53
|
end
|
54
|
+
|
55
|
+
def frozen?
|
56
|
+
File.exist?(repo_path + '/.git.frozen.tgz')
|
57
|
+
end
|
58
|
+
|
59
|
+
def checked_out?
|
60
|
+
File.exist?(repo_path)
|
61
|
+
end
|
62
|
+
|
63
|
+
private
|
64
|
+
def checkout_path
|
65
|
+
File.expand_path(File.join(@base_dir, @rel_path))
|
66
|
+
end
|
67
|
+
|
68
|
+
def repo_path
|
69
|
+
File.expand_path(checkout_path + '/' + @name)
|
70
|
+
end
|
71
|
+
|
72
|
+
def rel_repo_path
|
73
|
+
@rel_path + '/' + @name
|
74
|
+
end
|
75
|
+
|
76
|
+
def update_output(&block)
|
77
|
+
puts "Updating #{@name}" if verbose
|
78
|
+
block.call
|
79
|
+
puts " ..updated\n" if verbose
|
80
|
+
end
|
23
81
|
end
|
24
82
|
end
|
data/lib/giternal/version.rb
CHANGED
data/lib/giternal/yaml_config.rb
CHANGED
@@ -2,7 +2,8 @@ require 'yaml'
|
|
2
2
|
|
3
3
|
module Giternal
|
4
4
|
class YamlConfig
|
5
|
-
def initialize(yaml_string)
|
5
|
+
def initialize(base_dir, yaml_string)
|
6
|
+
@base_dir = base_dir
|
6
7
|
@config_hash = YAML.load yaml_string
|
7
8
|
end
|
8
9
|
|
@@ -13,7 +14,7 @@ module Giternal
|
|
13
14
|
private
|
14
15
|
def repositories
|
15
16
|
@config_hash.map do |name, attributes|
|
16
|
-
Repository.new(name, attributes["repo"], attributes["path"])
|
17
|
+
Repository.new(@base_dir, name, attributes["repo"], attributes["path"])
|
17
18
|
end
|
18
19
|
end
|
19
20
|
end
|
data/spec/giternal/app_spec.rb
CHANGED
@@ -4,30 +4,50 @@ module Giternal
|
|
4
4
|
describe App do
|
5
5
|
before(:each) do
|
6
6
|
@app = App.new("some_fake_dir")
|
7
|
-
File.stub!(:file?).and_return true
|
8
|
-
File.stub!(:read).and_return "yaml config"
|
9
|
-
|
10
7
|
@mock_config = stub("config", :null_object => true)
|
11
|
-
YamlConfig.stub!(:new).and_return @mock_config
|
12
8
|
end
|
13
9
|
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
10
|
+
describe "loading the config file" do
|
11
|
+
before(:each) do
|
12
|
+
File.stub!(:file?).and_return true
|
13
|
+
File.stub!(:read).and_return "yaml config"
|
14
|
+
YamlConfig.stub!(:new).and_return @mock_config
|
15
|
+
end
|
16
|
+
|
17
|
+
it "should exit with an error when no config file exists" do
|
18
|
+
File.should_receive(:file?).with(/some_fake_dir\/config\/giternal\.yml/).and_return false
|
19
|
+
$stderr.should_receive(:puts)
|
20
|
+
@app.should_receive(:exit).with(1)
|
21
|
+
@app.config
|
22
|
+
end
|
20
23
|
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
+
it "should create a config from the config file" do
|
25
|
+
YamlConfig.should_receive(:new).with('some_fake_dir', "yaml config").and_return @mock_config
|
26
|
+
@app.config
|
27
|
+
end
|
24
28
|
end
|
25
29
|
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
30
|
+
describe "app actions" do
|
31
|
+
before(:each) do
|
32
|
+
@app.stub!(:config).and_return @mock_config
|
33
|
+
@mock_repo = mock("repo")
|
34
|
+
@mock_config.stub!(:each_repo).and_yield(@mock_repo)
|
35
|
+
end
|
36
|
+
|
37
|
+
it "should update each of the repositories" do
|
38
|
+
@mock_repo.should_receive(:update)
|
39
|
+
@app.update
|
40
|
+
end
|
41
|
+
|
42
|
+
it "should freeze each of the repositories" do
|
43
|
+
@mock_repo.should_receive(:freezify)
|
44
|
+
@app.freezify
|
45
|
+
end
|
46
|
+
|
47
|
+
it "should unfreeze each of the repositories" do
|
48
|
+
@mock_repo.should_receive(:unfreezify)
|
49
|
+
@app.unfreezify
|
50
|
+
end
|
31
51
|
end
|
32
52
|
end
|
33
53
|
end
|
@@ -3,32 +3,114 @@ require File.expand_path(File.join(File.dirname(__FILE__), "..", "spec_helper"))
|
|
3
3
|
module Giternal
|
4
4
|
describe Repository do
|
5
5
|
before(:each) do
|
6
|
-
|
7
|
-
|
8
|
-
|
6
|
+
GiternalHelper.create_main_repo
|
7
|
+
GiternalHelper.create_repo 'foo'
|
8
|
+
@repository = Repository.new(GiternalHelper.base_project_dir, "foo",
|
9
|
+
GiternalHelper.external_path('foo'),
|
10
|
+
'dependencies')
|
9
11
|
end
|
10
|
-
|
12
|
+
|
11
13
|
it "should check itself out to a dir" do
|
12
|
-
@repository.update
|
13
|
-
File.file?(
|
14
|
-
File.read(
|
14
|
+
@repository.update
|
15
|
+
File.file?(GiternalHelper.checked_out_path('foo/foo')).should be_true
|
16
|
+
File.read(GiternalHelper.checked_out_path('foo/foo')).strip.
|
15
17
|
should == 'foo'
|
16
18
|
end
|
17
19
|
|
20
|
+
it "should not show any output when verbose mode is off" do
|
21
|
+
@repository.verbose = false
|
22
|
+
@repository.should_not_receive(:puts)
|
23
|
+
@repository.update
|
24
|
+
end
|
25
|
+
|
26
|
+
it "should not show output when verbose mode is on" do
|
27
|
+
@repository.verbose = true
|
28
|
+
@repository.should_receive(:puts).any_number_of_times
|
29
|
+
@repository.update
|
30
|
+
end
|
31
|
+
|
18
32
|
it "should update the repo when it's already been checked out" do
|
19
|
-
@repository.update
|
20
|
-
|
21
|
-
@repository.update
|
22
|
-
File.file?(
|
23
|
-
File.read(
|
33
|
+
@repository.update
|
34
|
+
GiternalHelper.add_content 'foo', 'newfile'
|
35
|
+
@repository.update
|
36
|
+
File.file?(GiternalHelper.checked_out_path('foo/newfile')).should be_true
|
37
|
+
File.read(GiternalHelper.checked_out_path('foo/newfile')).strip.
|
24
38
|
should == 'newfile'
|
25
39
|
end
|
26
40
|
|
27
41
|
it "should raise an error if the directory exists but there's no .git dir" do
|
28
|
-
FileUtils.mkdir_p(
|
42
|
+
FileUtils.mkdir_p(GiternalHelper.checked_out_path('foo'))
|
29
43
|
lambda {
|
30
|
-
@repository.update
|
44
|
+
@repository.update
|
31
45
|
}.should raise_error(/Directory 'foo' exists but is not a git repository/)
|
32
46
|
end
|
47
|
+
|
48
|
+
describe "freezify" do
|
49
|
+
before(:each) do
|
50
|
+
GiternalHelper.create_repo('external')
|
51
|
+
@repository = Repository.new(GiternalHelper.base_project_dir, 'external',
|
52
|
+
GiternalHelper.external_path('external'),
|
53
|
+
'dependencies')
|
54
|
+
@repository.update
|
55
|
+
end
|
56
|
+
|
57
|
+
it "should archive the .git dir" do
|
58
|
+
@repository.freezify
|
59
|
+
File.file?(GiternalHelper.checked_out_path('external/.git.frozen.tgz')).should be_true
|
60
|
+
end
|
61
|
+
|
62
|
+
it "should get rid of the .git dir" do
|
63
|
+
File.directory?(GiternalHelper.checked_out_path('external/.git')).should be_true
|
64
|
+
@repository.freezify
|
65
|
+
File.directory?(GiternalHelper.checked_out_path('external/.git')).should be_false
|
66
|
+
end
|
67
|
+
end
|
68
|
+
|
69
|
+
it "should simply return if updated when frozen" do
|
70
|
+
@repository.update
|
71
|
+
@repository.freezify
|
72
|
+
lambda { @repository.update }.should_not raise_error
|
73
|
+
end
|
74
|
+
|
75
|
+
it "should simply return when made to freeze when already frozen" do
|
76
|
+
@repository.update
|
77
|
+
@repository.freezify
|
78
|
+
lambda { @repository.freezify }.should_not raise_error
|
79
|
+
end
|
80
|
+
|
81
|
+
it "should simply return when made to freeze before checked out" do
|
82
|
+
lambda { @repository.freezify }.should_not raise_error
|
83
|
+
end
|
84
|
+
|
85
|
+
it "should simply return when made to unfreeze before checked out" do
|
86
|
+
lambda { @repository.unfreezify }.should_not raise_error
|
87
|
+
end
|
88
|
+
|
89
|
+
it "should simply return when made to unfreeze when already unfrozen" do
|
90
|
+
@repository.update
|
91
|
+
lambda { @repository.unfreezify }.should_not raise_error
|
92
|
+
end
|
93
|
+
|
94
|
+
describe "unfreezify" do
|
95
|
+
before(:each) do
|
96
|
+
GiternalHelper.create_repo('main')
|
97
|
+
GiternalHelper.create_repo('external')
|
98
|
+
@repository = Repository.new(GiternalHelper.base_project_dir, 'external',
|
99
|
+
GiternalHelper.external_path('external'),
|
100
|
+
'dependencies')
|
101
|
+
@repository.update
|
102
|
+
@repository.freezify
|
103
|
+
end
|
104
|
+
|
105
|
+
it "should unarchive the .git dir" do
|
106
|
+
@repository.unfreezify
|
107
|
+
File.directory?(GiternalHelper.checked_out_path('external/.git')).should be_true
|
108
|
+
end
|
109
|
+
|
110
|
+
it "should remove the archived file" do
|
111
|
+
@repository.unfreezify
|
112
|
+
File.file?(GiternalHelper.checked_out_path('external/.git.frozen.tgz')).should be_false
|
113
|
+
end
|
114
|
+
end
|
33
115
|
end
|
34
116
|
end
|
@@ -3,10 +3,11 @@ require File.expand_path(File.join(File.dirname(__FILE__), "..", "spec_helper"))
|
|
3
3
|
module Giternal
|
4
4
|
describe YamlConfig do
|
5
5
|
it "should create repositories from the config" do
|
6
|
-
config = YamlConfig.new(
|
6
|
+
config = YamlConfig.new('base_dir',
|
7
|
+
"rspec:\n repo: git://rspec\n path: vendor/plugins\n" +
|
7
8
|
"foo:\n repo: git://at/foo\n path: path/to/foo\n")
|
8
|
-
Repository.should_receive(:new).with("rspec", "git://rspec", "vendor/plugins").and_return :a_repo
|
9
|
-
Repository.should_receive(:new).with("foo", "git://at/foo", "path/to/foo").and_return :a_repo
|
9
|
+
Repository.should_receive(:new).with('base_dir', "rspec", "git://rspec", "vendor/plugins").and_return :a_repo
|
10
|
+
Repository.should_receive(:new).with('base_dir', "foo", "git://at/foo", "path/to/foo").and_return :a_repo
|
10
11
|
config.each_repo {|r| r.should == :a_repo}
|
11
12
|
end
|
12
13
|
end
|
data/spec/spec_helper.rb
CHANGED
@@ -7,35 +7,13 @@ end
|
|
7
7
|
|
8
8
|
$:.unshift(File.dirname(__FILE__) + '/../lib')
|
9
9
|
require 'giternal'
|
10
|
-
|
11
|
-
|
12
|
-
def self.base_project_dir
|
13
|
-
File.expand_path(File.dirname(__FILE__) + '/test_repos')
|
14
|
-
end
|
15
|
-
|
16
|
-
def self.source_dir(name)
|
17
|
-
base_project_dir + '/' + name
|
18
|
-
end
|
19
|
-
|
20
|
-
def self.create_repo(name)
|
21
|
-
FileUtils.mkdir_p(source_dir(name))
|
22
|
-
`cd #{source_dir(name)} && git init`
|
23
|
-
add_to_repo name, name
|
24
|
-
end
|
25
|
-
|
26
|
-
def self.add_to_repo(repo_name, file)
|
27
|
-
`cd #{source_dir(repo_name)} && echo #{file} > #{file} && git add #{file} && git commit -m "added #{file}"`
|
28
|
-
end
|
29
|
-
|
30
|
-
def self.wipe_repos
|
31
|
-
FileUtils.rm_rf(base_project_dir) if File.directory?(base_project_dir)
|
32
|
-
end
|
33
|
-
end
|
10
|
+
require 'fileutils'
|
11
|
+
require 'giternal_helper'
|
34
12
|
|
35
13
|
Spec::Runner.configuration.before(:each) do
|
36
|
-
|
14
|
+
GiternalHelper.wipe_repos
|
37
15
|
end
|
38
16
|
|
39
17
|
Spec::Runner.configuration.after(:each) do
|
40
|
-
|
18
|
+
GiternalHelper.wipe_repos
|
41
19
|
end
|
data/tasks/cucumber.rake
ADDED
@@ -0,0 +1,17 @@
|
|
1
|
+
begin
|
2
|
+
require 'cucumber/rake/task'
|
3
|
+
|
4
|
+
Cucumber::Rake::Task.new do |t|
|
5
|
+
t.cucumber_opts = "--format pretty"
|
6
|
+
end
|
7
|
+
|
8
|
+
rescue LoadError
|
9
|
+
at_exit do
|
10
|
+
puts <<-EOS
|
11
|
+
|
12
|
+
**********************************************************
|
13
|
+
To use cucumber for testing you must install cucumber gem:
|
14
|
+
http://github.com/aslakhellesoy/cucumber/tree/master
|
15
|
+
EOS
|
16
|
+
end
|
17
|
+
end
|
data/tasks/rspec.rake
CHANGED
@@ -1,21 +1,19 @@
|
|
1
|
-
begin
|
2
|
-
require 'spec'
|
3
|
-
rescue LoadError
|
4
|
-
require 'rubygems'
|
5
|
-
require 'spec'
|
6
|
-
end
|
7
1
|
begin
|
8
2
|
require 'spec/rake/spectask'
|
3
|
+
|
4
|
+
desc "Run the spec suite"
|
5
|
+
Spec::Rake::SpecTask.new do |t|
|
6
|
+
t.spec_opts = ['--options', "spec/spec.opts"]
|
7
|
+
t.spec_files = FileList['spec/**/*_spec.rb']
|
8
|
+
end
|
9
|
+
|
9
10
|
rescue LoadError
|
10
|
-
|
11
|
+
at_exit do
|
12
|
+
puts <<-EOS
|
13
|
+
|
14
|
+
****************************************************
|
11
15
|
To use rspec for testing you must install rspec gem:
|
12
16
|
gem install rspec
|
13
17
|
EOS
|
14
|
-
|
15
|
-
end
|
16
|
-
|
17
|
-
desc "Run the specs under spec/models"
|
18
|
-
Spec::Rake::SpecTask.new do |t|
|
19
|
-
t.spec_opts = ['--options', "spec/spec.opts"]
|
20
|
-
t.spec_files = FileList['spec/**/*_spec.rb']
|
18
|
+
end
|
21
19
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: giternal
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Pat Maddox
|
@@ -9,19 +9,9 @@ autorequire:
|
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
11
|
|
12
|
-
date: 2008-
|
12
|
+
date: 2008-12-03 00:00:00 -08:00
|
13
13
|
default_executable:
|
14
14
|
dependencies:
|
15
|
-
- !ruby/object:Gem::Dependency
|
16
|
-
name: sake
|
17
|
-
type: :runtime
|
18
|
-
version_requirement:
|
19
|
-
version_requirements: !ruby/object:Gem::Requirement
|
20
|
-
requirements:
|
21
|
-
- - ">="
|
22
|
-
- !ruby/object:Gem::Version
|
23
|
-
version: "1.0"
|
24
|
-
version:
|
25
15
|
- !ruby/object:Gem::Dependency
|
26
16
|
name: hoe
|
27
17
|
type: :development
|
@@ -30,37 +20,41 @@ dependencies:
|
|
30
20
|
requirements:
|
31
21
|
- - ">="
|
32
22
|
- !ruby/object:Gem::Version
|
33
|
-
version: 1.
|
23
|
+
version: 1.8.1
|
34
24
|
version:
|
35
25
|
description: description of gem
|
36
26
|
email:
|
37
27
|
- pat.maddox@gmail.com
|
38
|
-
executables:
|
39
|
-
|
28
|
+
executables:
|
29
|
+
- giternal
|
40
30
|
extensions: []
|
41
31
|
|
42
32
|
extra_rdoc_files:
|
43
33
|
- History.txt
|
44
34
|
- License.txt
|
45
35
|
- Manifest.txt
|
46
|
-
- PostInstall.txt
|
47
36
|
- README.txt
|
48
37
|
- website/index.txt
|
49
38
|
files:
|
39
|
+
- .emacs-project
|
50
40
|
- History.txt
|
51
41
|
- License.txt
|
52
42
|
- Manifest.txt
|
53
|
-
- PostInstall.txt
|
54
43
|
- README.txt
|
55
44
|
- Rakefile
|
45
|
+
- bin/giternal
|
56
46
|
- config/hoe.rb
|
57
47
|
- config/requirements.rb
|
48
|
+
- features/checking_out_externals.feature
|
49
|
+
- features/freeze_externals.feature
|
50
|
+
- features/steps/repository_steps.rb
|
51
|
+
- features/unfreeze_externals.feature
|
52
|
+
- giternal_helper.rb
|
58
53
|
- lib/giternal.rb
|
59
54
|
- lib/giternal/app.rb
|
60
55
|
- lib/giternal/repository.rb
|
61
56
|
- lib/giternal/version.rb
|
62
57
|
- lib/giternal/yaml_config.rb
|
63
|
-
- lib/tasks/giternal.rake
|
64
58
|
- script/console
|
65
59
|
- script/destroy
|
66
60
|
- script/generate
|
@@ -71,6 +65,7 @@ files:
|
|
71
65
|
- spec/giternal/yaml_config_spec.rb
|
72
66
|
- spec/spec.opts
|
73
67
|
- spec/spec_helper.rb
|
68
|
+
- tasks/cucumber.rake
|
74
69
|
- tasks/deployment.rake
|
75
70
|
- tasks/environment.rake
|
76
71
|
- tasks/rspec.rake
|
@@ -82,15 +77,7 @@ files:
|
|
82
77
|
- website/template.html.erb
|
83
78
|
has_rdoc: true
|
84
79
|
homepage: http://giternal.rubyforge.org
|
85
|
-
post_install_message:
|
86
|
-
** See README.txt **
|
87
|
-
|
88
|
-
** Run the following command **
|
89
|
-
sudo sake -i 'http://giternal.rubyforge.org/git?p=giternal.git;a=blob_plain;f=lib/tasks/giternal.rake;hb=HEAD'
|
90
|
-
|
91
|
-
For more information on giternal, see http://giternal.rubyforge.org
|
92
|
-
|
93
|
-
|
80
|
+
post_install_message: ""
|
94
81
|
rdoc_options:
|
95
82
|
- --main
|
96
83
|
- README.txt
|
@@ -111,7 +98,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
111
98
|
requirements: []
|
112
99
|
|
113
100
|
rubyforge_project: giternal
|
114
|
-
rubygems_version: 1.
|
101
|
+
rubygems_version: 1.3.1
|
115
102
|
signing_key:
|
116
103
|
specification_version: 2
|
117
104
|
summary: description of gem
|
data/PostInstall.txt
DELETED