public
Rubygem
Description: Ruby/Git is a Ruby library that can be used to create, read and manipulate Git repositories by wrapping system calls to the git binary.
Homepage: http://jointheconversation.org/rubygit/
Clone URL: git://github.com/schacon/ruby-git.git
Search Repo:
Add the possibility to read blob contents in chunks via IO#popen
siebertm (author)
Fri May 09 08:22:31 -0700 2008
schacon (committer)
Mon May 12 17:30:13 -0700 2008
commit  7df710fdb2e9b6376b3201ac6dee9ea6524f6e5f
tree    fc170fe0e81f1ca4e3ca3056544429b30de28af9
parent  ae106e2a3569e5ea874852c613ed060d8e232109
...
166
167
168
169
170
 
 
171
172
173
...
596
597
598
599
 
600
601
602
603
604
605
606
 
607
608
609
610
 
611
612
 
613
614
615
...
626
627
628
 
 
 
 
 
 
 
 
629
630
...
166
167
168
 
 
169
170
171
172
173
...
596
597
598
 
599
600
601
602
603
604
605
 
606
607
608
609
 
610
611
 
612
613
614
615
...
626
627
628
629
630
631
632
633
634
635
636
637
638
0
@@ -166,8 +166,8 @@ module Git
0
       end
0
     end
0
     
0
- def object_contents(sha)
0
- command('cat-file', ['-p', sha])
0
+ def object_contents(sha, &block)
0
+ command('cat-file', ['-p', sha], &block)
0
     end
0
 
0
     def ls_tree(sha)
0
@@ -596,20 +596,20 @@ module Git
0
       command(cmd, opts, chdir).split("\n")
0
     end
0
     
0
- def command(cmd, opts = [], chdir = true)
0
+ def command(cmd, opts = [], chdir = true, &block)
0
       ENV['GIT_DIR'] = @git_dir if (@git_dir != ENV['GIT_DIR'])
0
       ENV['GIT_INDEX_FILE'] = @git_index_file if (@git_index_file != ENV['GIT_INDEX_FILE'])
0
       ENV['GIT_WORK_TREE'] = @git_work_dir if (@git_work_dir != ENV['GIT_WORK_TREE'])
0
       path = @git_work_dir || @git_dir || @path
0
 
0
       opts = opts.to_a.join(' ')
0
- git_cmd = "git #{cmd} #{opts}"
0
+ git_cmd = "git #{cmd} #{opts} 2>&1"
0
 
0
       out = nil
0
       if chdir && (Dir.getwd != path)
0
- Dir.chdir(path) { out = `#{git_cmd} 2>&1`.chomp }
0
+ Dir.chdir(path) { out = run_command(git_cmd, &block) }
0
       else
0
- out = `#{git_cmd} 2>&1`.chomp
0
+ out = run_command(git_cmd, &block)
0
       end
0
       
0
       if @logger
0
@@ -626,5 +626,13 @@ module Git
0
       out
0
     end
0
     
0
+ def run_command(git_cmd, &block)
0
+ if block_given?
0
+ IO.popen(git_cmd, &block)
0
+ else
0
+ `#{git_cmd}`.chomp
0
+ end
0
+ end
0
+
0
   end
0
 end
...
28
29
30
31
32
33
 
 
 
 
 
 
 
 
 
 
 
34
35
36
...
28
29
30
 
 
 
31
32
33
34
35
36
37
38
39
40
41
42
43
44
0
@@ -28,9 +28,17 @@ module Git
0
         @size || @size = @base.lib.object_size(@objectish)
0
       end
0
       
0
- # caches the contents of this call in memory
0
- def contents
0
- @contents || @contents = @base.lib.object_contents(@objectish)
0
+ # get the object's contents
0
+ # if no block is given, the contents are cached in memory and returned as a string
0
+ # if a block is given, it yields an IO object (via IO::popen) which could be used to
0
+ # read a large file in chunks. use this for large files so that they are not held
0
+ # in memory
0
+ def contents(&block)
0
+ if block_given?
0
+ @base.lib.object_contents(@objectish, &block)
0
+ else
0
+ @contents || @contents = @base.lib.object_contents(@objectish)
0
+ end
0
       end
0
       
0
       def contents_array
...
85
86
87
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
88
89
90
...
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
0
@@ -85,6 +85,33 @@ class TestLib < Test::Unit::TestCase
0
     assert_equal(blob, @lib.object_contents('v2.5:example.txt')) #blob
0
     
0
   end
0
+
0
+ def test_object_contents_with_block
0
+ commit = "tree 94c827875e2cadb8bc8d4cdd900f19aa9e8634c7\n"
0
+ commit += "parent 546bec6f8872efa41d5d97a369f669165ecda0de\n"
0
+ commit += "author scott Chacon <schacon@agadorsparticus.corp.reactrix.com> 1194561188 -0800\n"
0
+ commit += "committer scott Chacon <schacon@agadorsparticus.corp.reactrix.com> 1194561188 -0800\n"
0
+ commit += "\ntest"
0
+
0
+ @lib.object_contents('1cc8667014381') do |f|
0
+ assert_equal(commit, f.read.chomp)
0
+ end
0
+
0
+ # commit
0
+
0
+ tree = "040000 tree 6b790ddc5eab30f18cabdd0513e8f8dac0d2d3ed\tex_dir\n"
0
+ tree += "100644 blob 3aac4b445017a8fc07502670ec2dbf744213dd48\texample.txt"
0
+
0
+ @lib.object_contents('1cc8667014381^{tree}') do |f|
0
+ assert_equal(tree, f.read.chomp) #tree
0
+ end
0
+
0
+ blob = "1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n2"
0
+
0
+ @lib.object_contents('v2.5:example.txt') do |f|
0
+ assert_equal(blob, f.read.chomp) #blob
0
+ end
0
+ end
0
 
0
   # returns Git::Branch object array
0
   def test_branches_all
...
102
103
104
 
 
 
 
 
 
 
 
 
105
106
107
...
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
0
@@ -102,6 +102,15 @@ class TestObject < Test::Unit::TestCase
0
     o = @git.gblob('v2.6:example.txt')
0
     assert_equal('replace with new text', o.contents)
0
     assert_equal('replace with new text', o.contents) # this should be cached
0
+
0
+ # make sure the block is called
0
+ block_called = false
0
+ o.contents do |f|
0
+ block_called = true
0
+ assert_equal('replace with new text', f.read.chomp)
0
+ end
0
+
0
+ assert(block_called)
0
   end
0
   
0
   def test_revparse

Comments

    No one has commented yet.