georgi-git_store 0.2.4 → 0.3

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.
@@ -3,7 +3,7 @@ require 'grit'
3
3
  require 'benchmark'
4
4
  require 'fileutils'
5
5
 
6
- REPO = File.expand_path(File.dirname(__FILE__) + '/repo')
6
+ REPO = '/tmp/git-store'
7
7
 
8
8
  FileUtils.rm_rf REPO
9
9
  FileUtils.mkpath REPO
@@ -21,7 +21,7 @@ Benchmark.bm 20 do |x|
21
21
  store.transaction { store['aa'] = rand.to_s }
22
22
  end
23
23
  x.report 'load 1000 objects' do
24
- GitStore.new('.')
24
+ GitStore.new('.').values { |v| v }
25
25
  end
26
26
  x.report 'load 1000 with grit' do
27
27
  Grit::Repo.new('.').tree.contents.each { |e| e.data }
@@ -0,0 +1,82 @@
1
+ require "#{File.dirname(__FILE__)}/../lib/git_store"
2
+ require 'pp'
3
+
4
+ describe GitStore::Commit do
5
+
6
+ REPO = '/tmp/git_store_test'
7
+
8
+ attr_reader :store
9
+
10
+ before(:each) do
11
+ FileUtils.rm_rf REPO
12
+ Dir.mkdir REPO
13
+ Dir.chdir REPO
14
+ `git init`
15
+ @store = GitStore.new(REPO)
16
+ end
17
+
18
+ it "should dump in right format" do
19
+ time = Time.now
20
+ timestamp = "#{ time.to_i } #{ time.to_s.split[4] }"
21
+
22
+ commit = GitStore::Commit.new(nil)
23
+ commit.tree = @store.root.id
24
+ commit.author = "hanni #{timestamp}"
25
+ commit.committer = "hanni #{timestamp}"
26
+ commit.message = "This is a message"
27
+
28
+ commit.dump.should == "tree #{@store.root.id}
29
+ author hanni #{timestamp}
30
+ committer hanni #{timestamp}
31
+
32
+ This is a message"
33
+ end
34
+
35
+ it "should be readable by git binary" do
36
+ time = Time.local(2009, 4, 20)
37
+ author = store.user_info("hans <hans@email.de>", time)
38
+
39
+ store['a'] = "Yay"
40
+ commit = store.commit("Commit Message", author, author)
41
+
42
+ IO.popen("git log") do |io|
43
+ io.gets.should == "commit #{commit.id}\n"
44
+ io.gets.should == "Author: hans <hans@email.de>\n"
45
+ io.gets.should == "Date: Mon Apr 20 00:00:00 2009 +0200\n"
46
+ io.gets.should == "\n"
47
+ io.gets.should == " Commit Message\n"
48
+ end
49
+ end
50
+
51
+ it "should diff 2 commits" do
52
+ store['x'] = 'a'
53
+ store['y'] = "
54
+ First Line.
55
+ Second Line.
56
+ Last Line.
57
+ "
58
+ a = store.commit
59
+
60
+ store.delete('x')
61
+ store['y'] = "
62
+ First Line.
63
+ Last Line.
64
+ Another Line.
65
+ "
66
+ store['z'] = 'c'
67
+
68
+ b = store.commit
69
+
70
+ diff = b.diff(a)
71
+
72
+ diff[0].a_path.should == 'x'
73
+ diff[0].deleted_file.should be_true
74
+
75
+ diff[1].a_path.should == 'y'
76
+ diff[1].diff.should == "--- a/y\n+++ b/y\n@@ -1,4 +1,4 @@\n \n First Line.\n-Second Line.\n Last Line.\n+Another Line."
77
+
78
+ diff[2].a_path.should == 'z'
79
+ diff[2].new_file.should be_true
80
+ end
81
+
82
+ end
@@ -1,210 +1,239 @@
1
1
  require "#{File.dirname(__FILE__)}/../lib/git_store"
2
+ require "#{File.dirname(__FILE__)}/helper"
3
+ require 'pp'
2
4
 
3
5
  describe GitStore do
4
6
 
5
- #REPO = File.expand_path(File.dirname(__FILE__) + '/repo')
6
7
  REPO = '/tmp/git_store_test'
7
8
 
9
+ attr_reader :store
10
+
8
11
  before(:each) do
9
12
  FileUtils.rm_rf REPO
10
13
  Dir.mkdir REPO
11
14
  Dir.chdir REPO
12
- end
13
-
14
- def store
15
- @store
15
+
16
+ `git init`
17
+ @store = GitStore.new(REPO)
16
18
  end
17
19
 
18
20
  def file(file, data)
19
21
  FileUtils.mkpath(File.dirname(file))
20
22
  open(file, 'w') { |io| io << data }
21
- if @use_git
22
- `git add #{file}`
23
- `git commit -m 'added #{file}'`
24
- File.unlink(file)
25
- end
23
+
24
+ `git add #{file}`
25
+ `git commit -m 'added #{file}'`
26
+ File.unlink(file)
27
+ end
28
+
29
+ it 'should fail to initialize without a valid git repository' do
30
+ lambda {
31
+ GitStore.new('/')
32
+ }.should raise_error(ArgumentError)
26
33
  end
27
34
 
28
- shared_examples_for 'all stores' do
29
- it 'should find modified entries' do
30
- store['a'] = 'Hello'
35
+ it 'should find modified entries' do
36
+ store['a'] = 'Hello'
31
37
 
32
- store.root.should be_modified
33
- store.root.table['a'].should be_modified
38
+ store.root.should be_modified
34
39
 
35
- store.commit
40
+ store.commit
41
+
42
+ store.root.should_not be_modified
36
43
 
37
- store['a'] = 'Bello'
44
+ store['a'] = 'Bello'
38
45
 
39
- store.root.table['a'].should be_modified
40
- end
46
+ store.root.should be_modified
47
+ end
41
48
 
42
- it 'should load a repo' do
43
- file 'a', 'Hello'
44
- file 'b', 'World'
45
-
46
- store.load
49
+ it 'should load a repo' do
50
+ file 'a', 'Hello'
51
+ file 'b', 'World'
52
+
53
+ store.load
47
54
 
48
- store['a'].should == 'Hello'
49
- store['b'].should == 'World'
50
- end
55
+ store['a'].should == 'Hello'
56
+ store['b'].should == 'World'
57
+ end
51
58
 
52
- it 'should load folders' do
53
- file 'x/a', 'Hello'
54
- file 'y/b', 'World'
59
+ it 'should load folders' do
60
+ file 'x/a', 'Hello'
61
+ file 'y/b', 'World'
55
62
 
56
- store.load
57
- store['x'].should be_kind_of(GitStore::Tree)
58
- store['y'].should be_kind_of(GitStore::Tree)
63
+ store.load
64
+ store['x'].should be_kind_of(GitStore::Tree)
65
+ store['y'].should be_kind_of(GitStore::Tree)
59
66
 
60
- store['x']['a'].should == 'Hello'
61
- store['y']['b'].should == 'World'
62
- end
67
+ store['x']['a'].should == 'Hello'
68
+ store['y']['b'].should == 'World'
69
+ end
63
70
 
64
- it 'should load yaml' do
65
- file 'x/a.yml', '[1, 2, 3, 4]'
71
+ it 'should load yaml' do
72
+ file 'x/a.yml', '[1, 2, 3, 4]'
66
73
 
67
- store.load
74
+ store.load
68
75
 
69
- store['x']['a.yml'].should == [1,2,3,4]
70
- store['x']['a.yml'] = [1,2,3,4,5]
71
- end
76
+ store['x']['a.yml'].should == [1,2,3,4]
77
+ store['x']['a.yml'] = [1,2,3,4,5]
78
+ end
79
+
80
+ it 'should save yaml' do
81
+ store['x/a.yml'] = [1,2,3,4,5]
82
+ store['x/a.yml'].should == [1,2,3,4,5]
83
+ end
72
84
 
73
- it 'should resolve paths' do
74
- file 'x/a', 'Hello'
75
- file 'y/b', 'World'
85
+ it 'should detect modification' do
86
+ store.transaction do
87
+ store['x/a'] = 'a'
88
+ end
76
89
 
77
- store.load
90
+ store.load
78
91
 
79
- store['x/a'].should == 'Hello'
80
- store['y/b'].should == 'World'
81
-
82
- store['y/b'] = 'Now this'
92
+ store['x/a'].should == 'a'
83
93
 
84
- store['y']['b'].should == 'Now this'
94
+ store.transaction do
95
+ store['x/a'] = 'b'
96
+ store['x'].should be_modified
97
+ store.root.should be_modified
85
98
  end
86
99
 
87
- it 'should create new trees' do
88
- store['new/tree'] = 'This tree'
89
- store['this', 'tree'] = 'Another'
90
- store['new/tree'].should == 'This tree'
91
- store['this/tree'].should == 'Another'
92
- end
100
+ store.load
93
101
 
94
- it 'should delete entries' do
95
- store['a'] = 'Hello'
96
- store.delete('a')
97
-
98
- store['a'].should be_nil
99
- end
102
+ store['x/a'].should == 'b'
100
103
  end
101
104
 
102
- describe 'with Git' do
103
- before(:each) do
104
- `git init`
105
- @use_git = true
106
- @store = GitStore.new(REPO)
107
- end
105
+ it 'should resolve paths' do
106
+ file 'x/a', 'Hello'
107
+ file 'y/b', 'World'
108
+
109
+ store.load
110
+
111
+ store['x/a'].should == 'Hello'
112
+ store['y/b'].should == 'World'
108
113
 
109
- it_should_behave_like 'all stores'
114
+ store['y/b'] = 'Now this'
110
115
 
111
- it 'should have a head commit' do
112
- file 'a', 'Hello'
116
+ store['y']['b'].should == 'Now this'
117
+ end
113
118
 
114
- store.read_head.should_not be_nil
115
- File.should be_exist(store.object_path(store.read_head))
116
- end
119
+ it 'should create new trees' do
120
+ store['new/tree'] = 'This tree'
121
+ store['new/tree'].should == 'This tree'
122
+ end
117
123
 
118
- it 'should detect changes' do
119
- file 'a', 'Hello'
124
+ it 'should delete entries' do
125
+ store['a'] = 'Hello'
126
+ store.delete('a')
127
+
128
+ store['a'].should be_nil
129
+ end
120
130
 
121
- store.should be_changed
122
- end
131
+ it 'should have a head commit' do
132
+ file 'a', 'Hello'
123
133
 
124
- it 'should rollback a transaction' do
125
- file 'a/b', 'Hello'
126
- file 'c/d', 'World'
134
+ store.load
135
+ store.head.should_not be_nil
136
+ end
127
137
 
128
- begin
129
- store.transaction do
130
- store['a/b'] = 'Changed'
131
- store['x/a'] = 'Added'
132
- raise
133
- end
134
- rescue
135
- end
138
+ it 'should detect changes' do
139
+ file 'a', 'Hello'
136
140
 
137
- store['a/b'].should == 'Hello'
138
- store['c/d'].should == 'World'
139
- store['x/a'].should be_nil
140
- end
141
+ store.should be_changed
142
+ end
141
143
 
142
- it 'should commit a transaction' do
143
- file 'a/b', 'Hello'
144
- file 'c/d', 'World'
144
+ it 'should rollback a transaction' do
145
+ file 'a/b', 'Hello'
146
+ file 'c/d', 'World'
145
147
 
148
+ begin
146
149
  store.transaction do
147
150
  store['a/b'] = 'Changed'
148
151
  store['x/a'] = 'Added'
152
+ raise
149
153
  end
154
+ rescue
155
+ end
150
156
 
151
- store.load
152
-
153
- store['a/b'].should == 'Changed'
154
- store['c/d'].should == 'World'
155
- store['x/a'].should == 'Added'
157
+ store['a/b'].should == 'Hello'
158
+ store['c/d'].should == 'World'
159
+ store['x/a'].should be_nil
160
+ end
161
+
162
+ it 'should commit a transaction' do
163
+ file 'a/b', 'Hello'
164
+ file 'c/d', 'World'
165
+
166
+ store.transaction do
167
+ store['a/b'] = 'Changed'
168
+ store['x/a'] = 'Added'
156
169
  end
157
170
 
158
- it 'should allow only one transaction' do
159
- file 'a/b', 'Hello'
171
+ a = git_ls_tree(store['a'].id)
172
+ x = git_ls_tree(store['x'].id)
160
173
 
161
- ready = false
174
+ a.should == [["100644", "blob", "b653cf27cef08de46da49a11fa5016421e9e3b32", "b"]]
175
+ x.should == [["100644", "blob", "87d2b203800386b1cc8735a7d540a33e246357fa", "a"]]
162
176
 
163
- store.transaction do
164
- Thread.start do
165
- store.transaction do
166
- store['a/b'] = 'Changed by second thread'
167
- end
168
- ready = true
169
- end
170
- store['a/b'] = 'Changed'
171
- end
172
-
173
- sleep 0.01 until ready
177
+ git_show(a[0][2]).should == 'Changed'
178
+ git_show(x[0][2]).should == 'Added'
179
+ end
180
+
181
+ it "should save blobs" do
182
+ store['a'] = 'a'
183
+ store['b'] = 'b'
184
+ store['c'] = 'c'
174
185
 
175
- store.load
176
-
177
- store['a/b'].should == 'Changed by second thread'
178
- end
186
+ store.commit
179
187
 
180
- it 'should commit added files' do
181
- store.load
182
- store['c'] = 'Hello'
183
- store['d'] = 'World'
184
- store.commit
188
+ a = store.id_for('blob', 'a')
189
+ b = store.id_for('blob', 'b')
190
+ c = store.id_for('blob', 'c')
185
191
 
186
- `git checkout`
192
+ git_show(a).should == 'a'
193
+ git_show(b).should == 'b'
194
+ git_show(c).should == 'c'
195
+ end
187
196
 
188
- File.should be_exist('c')
189
- File.should be_exist('d')
197
+ it 'should allow only one transaction' do
198
+ file 'a/b', 'Hello'
190
199
 
191
- File.read('c').should == 'Hello'
192
- File.read('d').should == 'World'
193
- end
194
- end
200
+ ready = false
195
201
 
196
- describe 'without Git' do
197
- before(:each) do
198
- @use_git = false
199
- @store = GitStore::FileStore.new(REPO)
202
+ store.transaction do
203
+ Thread.start do
204
+ store.transaction do
205
+ store['a/b'] = 'Changed by second thread'
206
+ end
207
+ ready = true
208
+ end
209
+ store['a/b'] = 'Changed'
200
210
  end
201
211
 
202
- it_should_behave_like 'all stores'
212
+ sleep 0.01 until ready
213
+
214
+ store.load
215
+
216
+ store['a/b'].should == 'Changed by second thread'
217
+ end
218
+
219
+ it 'should find all objects' do
220
+ store.load
221
+ store['c'] = 'Hello'
222
+ store['d'] = 'World'
223
+ store.commit
224
+
225
+ store.to_a.should == [['c', 'Hello'], ['d', 'World']]
203
226
  end
204
227
 
205
- it 'should fail to initialize without a valid git repository' do
206
- lambda {
207
- GitStore.new(REPO)
208
- }.should raise_error(ArgumentError)
228
+ it "should load commits" do
229
+ store['a'] = 'a'
230
+ store.commit 'added a'
231
+
232
+ store['b'] = 'b'
233
+ store.commit 'added b'
234
+
235
+ store.commits[0].message.should == 'added b'
236
+ store.commits[1].message.should == 'added a'
209
237
  end
238
+
210
239
  end