gitlab_git 1.4.1 → 2.0.0.beta

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: d590d7ff3fab5e14714b50c3834566f326ef20af
4
- data.tar.gz: 40e19943e01067a42f9ef8ba906a1e7b618d146c
3
+ metadata.gz: 721ce63ea203619c49c42fd796634d7076ebad3b
4
+ data.tar.gz: 3d7ac5846bc15878beddfedb4bc8378048359d43
5
5
  SHA512:
6
- metadata.gz: 0e589b34aea8ebb6397ba01b6367313b4a5725be1990dd86f5cee2077e9476969a34d239651452797035431397a646d56a1b90ba02a527273570769ebd0c34ef
7
- data.tar.gz: 8a7707289c1bdc7feadaaa8a9cba4aefefd8bcec7b8dc1212725495fd697893fe405583eeb644317ce7622101992c485ff01bf20a90978a8015942ea2da1dd1b
6
+ metadata.gz: 216f0f37fa7f9b38ce2bf9710ed9773210af4128e6f874124f0c5e26865fcf9739ef8d38cddea671c05c195fe7021dd4287a1d8f2511f8618400539e1833c799
7
+ data.tar.gz: 4df9626fbf0a5c1c18d603d64bc93fa7a998dccddaac7ae424461bbf36fc11b0f9e73f7817f6beb456cb43fcb89e2d124da2d1fe439e00a08f5676adf146235f
@@ -1,7 +1,6 @@
1
1
  module Gitlab
2
2
  module Git
3
3
  class Blame
4
-
5
4
  attr_accessor :repository, :sha, :path
6
5
 
7
6
  def initialize(repository, sha, path)
@@ -9,7 +8,7 @@ module Gitlab
9
8
  end
10
9
 
11
10
  def each
12
- raw_blame = Grit::Blob.blame(repository.repo, sha, path)
11
+ raw_blame = Grit::Blob.blame(repository.raw, sha, path)
13
12
 
14
13
  raw_blame.each do |commit, lines|
15
14
  next unless commit
@@ -13,6 +13,89 @@ module Gitlab
13
13
  ]
14
14
  attr_accessor *SERIALIZE_KEYS
15
15
 
16
+ class << self
17
+ # Get commits collection
18
+ #
19
+ # Ex.
20
+ # Commit.where(
21
+ # repo: repo,
22
+ # ref: 'master',
23
+ # path: 'app/models',
24
+ # limit: 10,
25
+ # offset: 5,
26
+ # )
27
+ #
28
+ def where(options)
29
+ repo = options.delete(:repo)
30
+ raise 'Gitlab::Git::Repository is required' unless repo.respond_to?(:log)
31
+
32
+ repo.log(options).map { |c| decorate(c) }
33
+ end
34
+
35
+ # Get single commit
36
+ #
37
+ # Ex.
38
+ # Commit.find(repo, '29eda46b')
39
+ #
40
+ # Commit.find(repo, 'master')
41
+ #
42
+ def find(repo, commit_id = nil)
43
+ # Find repo.tags first,
44
+ # because if commit_id is "tag name",
45
+ # repo.commit(commit_id) returns wrong commit sha
46
+ # that is git tag object sha.
47
+ tag = repo.tags.find {|tag| tag.name == commit_id} if commit_id
48
+
49
+ commit = if tag
50
+ tag.commit
51
+ else
52
+ repo.log(ref: commit_id).first
53
+ end
54
+
55
+ decorate(commit) if commit
56
+ end
57
+
58
+ # Get last commit for HEAD
59
+ #
60
+ # Ex.
61
+ # Commit.last(repo)
62
+ #
63
+ def last(repo)
64
+ find(repo, nil)
65
+ end
66
+
67
+ # Get last commit for specified path and ref
68
+ #
69
+ # Ex.
70
+ # Commit.last_for_path(repo, '29eda46b', 'app/models')
71
+ #
72
+ # Commit.last_for_path(repo, 'master', 'Gemfile')
73
+ #
74
+ def last_for_path(repo, ref, path = nil)
75
+ where(
76
+ repo: repo,
77
+ ref: ref,
78
+ path: path,
79
+ limit: 1
80
+ ).first
81
+ end
82
+
83
+ # Get commits between two refs
84
+ #
85
+ # Ex.
86
+ # Commit.between('29eda46b', 'master')
87
+ #
88
+ def between(repo, from, to)
89
+ repo.commits_between(from, to).map do |commit|
90
+ decorate(commit)
91
+ end
92
+ end
93
+
94
+ def decorate(commit, ref = nil)
95
+ Gitlab::Git::Commit.new(commit, ref)
96
+ end
97
+ end
98
+
16
99
  def initialize(raw_commit, head = nil)
17
100
  raise "Nil as raw commit passed" unless raw_commit
18
101
 
@@ -14,6 +14,21 @@ module Gitlab
14
14
  # Stats properties
15
15
  attr_accessor :new_file, :renamed_file, :deleted_file
16
16
 
17
+ class << self
18
+ def between(repo, from, to)
19
+ # Only show what is new in the source branch compared to the target branch, not the other way around.
20
+ # The linex below with merge_base is equivalent to diff with three dots (git diff branch1...branch2)
21
+ # From the git documentation: "git diff A...B" is equivalent to "git diff $(git-merge-base A B) B"
22
+ common_commit = repo.merge_base_commit(from, to)
23
+
24
+ repo.diff(common_commit, from).map do |diff|
25
+ Gitlab::Git::Diff.new(diff)
26
+ end
27
+ rescue Grit::Git::GitTimeout
28
+ [Gitlab::Git::Diff::BROKEN_DIFF]
29
+ end
30
+ end
31
+
17
32
  def initialize(raw_diff)
18
33
  raise "Nil as raw diff passed" unless raw_diff
19
34
 
@@ -10,7 +10,8 @@ module Gitlab
10
10
  end
11
11
 
12
12
  def log
13
- args = ['--format=%aN%x0a%ad', '--date=short', '--shortstat', '--no-merges']
13
+ # Limit log to 8k commits to avoid timeout for huge projects
14
+ args = ['--format=%aN%x0a%aE%x0a%ad', '--date=short', '--shortstat', '--no-merges', '--max-count=8000']
14
15
  repo.git.run(nil, 'log', nil, {}, args)
15
16
  rescue Grit::Git::GitTimeout
16
17
  nil
@@ -2,31 +2,23 @@ module Gitlab
2
2
  module Git
3
3
  class LogParser
4
4
  # Parses the log file into a collection of commits
5
- # Data model: {author, date, additions, deletions}
6
- def self.parse_log log_from_git
5
+ # Data model:
6
+ # {author_name, author_email, date, additions, deletions}
7
+ def self.parse_log(log_from_git)
7
8
  log = log_from_git.split("\n")
8
-
9
- i = 0
10
9
  collection = []
11
- entry = {}
12
10
 
13
- while i <= log.size do
14
- pos = i % 4
15
- case pos
16
- when 0
17
- unless i == 0
18
- collection.push(entry)
19
- entry = {}
20
- end
21
- entry[:author] = log[i].to_s
22
- when 1
23
- entry[:date] = log[i].to_s
24
- when 3
25
- changes = log[i].split(",")
26
- entry[:additions] = changes[1].to_i unless changes[1].nil?
27
- entry[:deletions] = changes[2].to_i unless changes[2].nil?
28
- end
29
- i += 1
11
+ log.each_slice(5) do |slice|
12
+ entry = {}
13
+ entry[:author_name] = slice[0]
14
+ entry[:author_email] = slice[1]
15
+ entry[:date] = slice[2]
16
+
17
+ changes = slice[4].split(",")
18
+ entry[:additions] = changes[1].to_i unless changes[1].nil?
19
+ entry[:deletions] = changes[2].to_i unless changes[2].nil?
20
+
21
+ collection.push(entry)
30
22
  end
31
23
 
32
24
  collection
@@ -1,4 +1,4 @@
1
- # Gitlab::Git::Gitlab::Git::Commit is a wrapper around native Grit::Repository object
1
+ # Gitlab::Git::Commit is a wrapper around native Grit::Repository object
2
2
  # We dont want to use grit objects inside app/
3
3
  # It helps us easily migrate to rugged in future
4
4
  module Gitlab
@@ -19,22 +19,21 @@ module Gitlab
19
19
  #
20
20
  attr_accessor :path_with_namespace
21
21
 
22
- # Grit repo object
23
- attr_accessor :repo
24
-
25
22
  # Default branch in the repository
26
23
  attr_accessor :root_ref
27
24
 
25
+ # Grit repo object
26
+ attr_reader :raw
27
+
28
+ # compatibility
29
+ alias_method :repo, :raw
30
+
28
31
  def initialize(path_with_namespace, root_ref = 'master')
29
32
  @root_ref = root_ref || "master"
30
33
  @path_with_namespace = path_with_namespace
31
34
 
32
35
  # Init grit repo object
33
- repo
34
- end
35
-
36
- def raw
37
- repo
36
+ raw
38
37
  end
39
38
 
40
39
  def path_to_repo
@@ -45,59 +44,12 @@ module Gitlab
45
44
  self.class.repos_path
46
45
  end
47
46
 
48
- def repo
49
- @repo ||= Grit::Repo.new(path_to_repo)
47
+ def raw
48
+ @raw ||= Grit::Repo.new(path_to_repo)
50
49
  rescue Grit::NoSuchPathError
51
50
  raise NoRepository.new('no repository for such path')
52
51
  end
53
52
 
54
- def commit(commit_id = nil)
55
- commit = if commit_id
56
- # Find repo.refs first,
57
- # because if commit_id is "tag name",
58
- # repo.commit(commit_id) returns wrong commit sha
59
- # that is git tag object sha.
60
- ref = repo.refs.find {|r| r.name == commit_id}
61
- if ref
62
- ref.commit
63
- else
64
- repo.commit(commit_id)
65
- end
66
- else
67
- repo.commits(root_ref).first
68
- end
69
-
70
- decorate_commit(commit) if commit
71
- end
72
-
73
- def commits_with_refs(n = 20)
74
- commits = repo.branches.map { |ref| decorate_commit(ref.commit, ref) }
75
-
76
- commits.sort! do |x, y|
77
- y.committed_date <=> x.committed_date
78
- end
79
-
80
- commits[0..n]
81
- end
82
-
83
- def commits(ref, path = nil, limit = nil, offset = nil)
84
- if path && path != ''
85
- repo.log(ref, path, max_count: limit, skip: offset, follow: true)
86
- elsif limit && offset
87
- repo.commits(ref, limit.to_i, offset.to_i)
88
- else
89
- repo.commits(ref)
90
- end.map{ |c| decorate_commit(c) }
91
- end
92
-
93
- def commits_between(from, to)
94
- repo.commits_between(from, to).map { |c| decorate_commit(c) }
95
- end
96
-
97
- def last_commit_for(ref, path = nil)
98
- commits(ref, path, 1).first
99
- end
100
-
101
53
  # Returns an Array of branch names
102
54
  # sorted by name ASC
103
55
  def branch_names
@@ -106,7 +58,7 @@ module Gitlab
106
58
 
107
59
  # Returns an Array of Branches
108
60
  def branches
109
- repo.branches.sort_by(&:name)
61
+ raw.branches.sort_by(&:name)
110
62
  end
111
63
 
112
64
  # Returns an Array of tag names
@@ -116,7 +68,7 @@ module Gitlab
116
68
 
117
69
  # Returns an Array of Tags
118
70
  def tags
119
- repo.tags.sort_by(&:name).reverse
71
+ raw.tags.sort_by(&:name).reverse
120
72
  end
121
73
 
122
74
  # Returns an Array of branch and tag names
@@ -125,7 +77,7 @@ module Gitlab
125
77
  end
126
78
 
127
79
  def heads
128
- @heads ||= repo.heads.sort_by(&:name)
80
+ @heads ||= raw.heads.sort_by(&:name)
129
81
  end
130
82
 
131
83
  def tree(fcommit, path = nil)
@@ -135,7 +87,7 @@ module Gitlab
135
87
  end
136
88
 
137
89
  def has_commits?
138
- !!commit
90
+ !!Gitlab::Git::Commit.last(self)
139
91
  rescue Grit::NoSuchPathError
140
92
  false
141
93
  end
@@ -167,7 +119,7 @@ module Gitlab
167
119
  #
168
120
  def archive_repo(ref, storage_path)
169
121
  ref = ref || self.root_ref
170
- commit = self.commit(ref)
122
+ commit = Gitlab::Git::Commit.find(self, ref)
171
123
  return nil unless commit
172
124
 
173
125
  # Build file path
@@ -180,7 +132,7 @@ module Gitlab
180
132
  # Create file if not exists
181
133
  unless File.exists?(file_path)
182
134
  FileUtils.mkdir_p File.dirname(file_path)
183
- file = self.repo.archive_to_file(ref, prefix, file_path)
135
+ file = self.raw.archive_to_file(ref, prefix, file_path)
184
136
  end
185
137
 
186
138
  file_path
@@ -192,33 +144,60 @@ module Gitlab
192
144
  (size.to_f / 1024).round(2)
193
145
  end
194
146
 
195
- def diffs_between(source_branch, target_branch)
196
- # Only show what is new in the source branch compared to the target branch, not the other way around.
197
- # The linex below with merge_base is equivalent to diff with three dots (git diff branch1...branch2)
198
- # From the git documentation: "git diff A...B" is equivalent to "git diff $(git-merge-base A B) B"
199
- common_commit = repo.git.native(:merge_base, {}, [target_branch, source_branch]).strip
200
- repo.diff(common_commit, source_branch).map { |diff| Gitlab::Git::Diff.new(diff) }
201
-
202
- rescue Grit::Git::GitTimeout
203
- [Gitlab::Git::Diff::BROKEN_DIFF]
204
- end
205
-
206
147
  def search_files(query, ref = nil)
207
148
  if ref.nil? || ref == ""
208
149
  ref = root_ref
209
150
  end
210
151
 
211
- greps = repo.grep(query, 3, ref)
152
+ greps = raw.grep(query, 3, ref)
212
153
 
213
154
  greps.map do |grep|
214
155
  Gitlab::Git::BlobSnippet.new(ref, grep.content, grep.startline, grep.filename)
215
156
  end
216
157
  end
217
158
 
218
- protected
159
+ # Delegate log to Grit method
160
+ #
161
+ # Usage.
162
+ # repo.log(
163
+ # ref: 'master',
164
+ # path: 'app/models',
165
+ # limit: 10,
166
+ # offset: 5,
167
+ # )
168
+ #
169
+ def log(options)
170
+ default_options = {
171
+ limit: 10,
172
+ offset: 0,
173
+ path: nil,
174
+ ref: root_ref,
175
+ follow: false
176
+ }
177
+
178
+ options = default_options.merge(options)
179
+
180
+ raw.log(
181
+ options[:ref] || root_ref,
182
+ options[:path],
183
+ max_count: options[:limit].to_i,
184
+ skip: options[:offset].to_i,
185
+ follow: options[:follow]
186
+ )
187
+ end
188
+
189
+ # Delegate commits_between to Grit method
190
+ #
191
+ def commits_between(from, to)
192
+ raw.commits_between(from, to)
193
+ end
194
+
195
+ def merge_base_commit(from, to)
196
+ raw.git.native(:merge_base, {}, [to, from]).strip
197
+ end
219
198
 
220
- def decorate_commit(commit, ref = nil)
221
- Gitlab::Git::Commit.new(commit, ref)
199
+ def diff(from, to)
200
+ raw.diff(from, to)
222
201
  end
223
202
  end
224
203
  end
@@ -9,7 +9,7 @@ module Gitlab
9
9
  @path = nil if !@path || @path == ''
10
10
 
11
11
  # Load tree from repository
12
- @commit = @repository.commit(@sha)
12
+ @commit = Gitlab::Git::Commit.find(@repository, @sha)
13
13
  @raw_tree = @repository.tree(@commit, @path)
14
14
  end
15
15
 
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gitlab_git
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.4.1
4
+ version: 2.0.0.beta
5
5
  platform: ruby
6
6
  authors:
7
7
  - Dmitriy Zaporozhets
@@ -86,9 +86,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
86
86
  version: '0'
87
87
  required_rubygems_version: !ruby/object:Gem::Requirement
88
88
  requirements:
89
- - - '>='
89
+ - - '>'
90
90
  - !ruby/object:Gem::Version
91
- version: '0'
91
+ version: 1.3.1
92
92
  requirements: []
93
93
  rubyforge_project:
94
94
  rubygems_version: 2.0.3