1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
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
118
|
module Git
class Status
include Enumerable
@base = nil
@files = nil
def initialize(base)
@base = base
construct_status
end
def changed
@files.select { |k, f| f.type == 'M' }
end
def added
@files.select { |k, f| f.type == 'A' }
end
def deleted
@files.select { |k, f| f.type == 'D' }
end
def untracked
@files.select { |k, f| f.untracked }
end
def pretty
out = ''
self.each do |file|
out << file.path
out << "\n\tsha(r) " + file.sha_repo.to_s + ' ' + file.mode_repo.to_s
out << "\n\tsha(i) " + file.sha_index.to_s + ' ' + file.mode_index.to_s
out << "\n\ttype " + file.type.to_s
out << "\n\tstage " + file.stage.to_s
out << "\n\tuntrac " + file.untracked.to_s
out << "\n"
end
out << "\n"
out
end
# enumerable method
def [](file)
@files[file]
end
def each
@files.each do |k, file|
yield file
end
end
class StatusFile
attr_accessor :path, :type, :stage, :untracked
attr_accessor :mode_index, :mode_repo
attr_accessor :sha_index, :sha_repo
@base = nil
def initialize(base, hash)
@base = base
@path = hash[:path]
@type = hash[:type]
@stage = hash[:stage]
@mode_index = hash[:mode_index]
@mode_repo = hash[:mode_repo]
@sha_index = hash[:sha_index]
@sha_repo = hash[:sha_repo]
@untracked = hash[:untracked]
end
def blob(type = :index)
if type == :repo
@base.object(@sha_repo)
else
@base.object(@sha_index) rescue @base.object(@sha_repo)
end
end
end
private
def construct_status
@files = @base.lib.ls_files
# find untracked in working dir
Dir.chdir(@base.dir.path) do
Dir.glob('**/*') do |file|
if !@files[file]
@files[file] = {:path => file, :untracked => true} if !File.directory?(file)
end
end
end
# find modified in tree
@base.lib.diff_files.each do |path, data|
@files[path] ? @files[path].merge!(data) : @files[path] = data
end
# find added but not committed - new files
@base.lib.diff_index('HEAD').each do |path, data|
@files[path] ? @files[path].merge!(data) : @files[path] = data
end
@files.each do |k, file_hash|
@files[k] = StatusFile.new(@base, file_hash)
end
end
end
end
|