ohloh_scm 4.0.4 → 5.0.0
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.
- checksums.yaml +4 -4
- data/.rubocop.yml +14 -3
- data/.ruby-version +1 -1
- data/Dockerfile +8 -8
- data/Gemfile +1 -1
- data/Gemfile.lock +48 -33
- data/lib/ohloh_scm/activity.rb +1 -1
- data/lib/ohloh_scm/bzr/activity.rb +12 -12
- data/lib/ohloh_scm/bzr/validation.rb +1 -1
- data/lib/ohloh_scm/commit.rb +2 -4
- data/lib/ohloh_scm/core.rb +2 -1
- data/lib/ohloh_scm/cvs/activity.rb +74 -60
- data/lib/ohloh_scm/cvs/scm.rb +12 -12
- data/lib/ohloh_scm/cvs/status.rb +1 -1
- data/lib/ohloh_scm/cvs/validation.rb +5 -5
- data/lib/ohloh_scm/diff.rb +1 -1
- data/lib/ohloh_scm/factory.rb +7 -1
- data/lib/ohloh_scm/git/activity.rb +111 -55
- data/lib/ohloh_scm/git/scm.rb +6 -8
- data/lib/ohloh_scm/git/status.rb +1 -1
- data/lib/ohloh_scm/git/validation.rb +1 -1
- data/lib/ohloh_scm/git_svn/activity.rb +5 -5
- data/lib/ohloh_scm/git_svn/scm.rb +5 -5
- data/lib/ohloh_scm/hg/activity.rb +13 -13
- data/lib/ohloh_scm/hg/scm.rb +3 -3
- data/lib/ohloh_scm/hg/validation.rb +1 -1
- data/lib/ohloh_scm/parser/branch_number.rb +7 -6
- data/lib/ohloh_scm/parser/bzr_xml_parser.rb +15 -15
- data/lib/ohloh_scm/parser/cvs_parser.rb +7 -6
- data/lib/ohloh_scm/parser/git_parser.rb +18 -15
- data/lib/ohloh_scm/parser/hg_parser.rb +8 -6
- data/lib/ohloh_scm/parser/svn_parser.rb +7 -6
- data/lib/ohloh_scm/py_bridge/hg_client.rb +1 -1
- data/lib/ohloh_scm/svn/activity.rb +17 -18
- data/lib/ohloh_scm/svn/scm.rb +4 -6
- data/lib/ohloh_scm/svn/validation.rb +2 -2
- data/lib/ohloh_scm/system.rb +1 -1
- data/lib/ohloh_scm/validation.rb +4 -6
- data/lib/ohloh_scm/version.rb +1 -1
- data/ohloh_scm.gemspec +5 -5
- data/security.md +30 -0
- data/spec/.rubocop.yml +2 -5
- data/spec/benchmarks/process_spawn_benchmark.rb +1 -1
- data/spec/helpers/assert_scm_attr_helper.rb +4 -4
- data/spec/helpers/generic_helper.rb +2 -2
- data/spec/helpers/repository_helper.rb +1 -1
- data/spec/ohloh_scm/activity_spec.rb +2 -2
- data/spec/ohloh_scm/bzr/activity_spec.rb +60 -60
- data/spec/ohloh_scm/bzr/validation_spec.rb +1 -1
- data/spec/ohloh_scm/cvs/activity_spec.rb +20 -21
- data/spec/ohloh_scm/cvs/scm_spec.rb +36 -36
- data/spec/ohloh_scm/cvs/validation_spec.rb +4 -4
- data/spec/ohloh_scm/factory_spec.rb +2 -2
- data/spec/ohloh_scm/git/activity_spec.rb +111 -110
- data/spec/ohloh_scm/git/scm_spec.rb +11 -11
- data/spec/ohloh_scm/git/status_spec.rb +3 -3
- data/spec/ohloh_scm/git/validation_spec.rb +7 -7
- data/spec/ohloh_scm/git_svn/activity_spec.rb +14 -14
- data/spec/ohloh_scm/git_svn/scm_spec.rb +1 -1
- data/spec/ohloh_scm/hg/activity_spec.rb +99 -99
- data/spec/ohloh_scm/hg/scm_spec.rb +5 -5
- data/spec/ohloh_scm/hg/validation_spec.rb +1 -1
- data/spec/ohloh_scm/parser/array_writer_spec.rb +7 -7
- data/spec/ohloh_scm/parser/branch_number_spec.rb +3 -3
- data/spec/ohloh_scm/parser/cvs_parser_spec.rb +31 -31
- data/spec/ohloh_scm/parser/git_parser_spec.rb +29 -32
- data/spec/ohloh_scm/parser/hg_parser_spec.rb +60 -60
- data/spec/ohloh_scm/svn/activity_spec.rb +11 -12
- data/spec/ohloh_scm/svn/scm_spec.rb +24 -24
- data/spec/ohloh_scm/svn/validation_spec.rb +6 -6
- data/spec/ohloh_scm/svn_parser_spec.rb +29 -29
- data/spec/ohloh_scm/system_spec.rb +5 -5
- data/spec/ohloh_scm/version_spec.rb +1 -1
- data/spec/string_encoder_spec.rb +4 -4
- metadata +8 -81
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 0517dea873b5829d942367af3ec07ec0497b405d30a757791cfed1778a281cd8
|
4
|
+
data.tar.gz: fb5146be6537fa90b3fe611f37a48b34614768a4c5d52223ca72b83c1dbef717
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 93001e6affa4f9e2ae96767d6a23d29527f74f76d64b01c015f0ddb7689d187b6d62857f33c8961a316823cb283838e1ee65fab472102b9d0ef601d457b68d0c
|
7
|
+
data.tar.gz: a6fe592ecaf5e5d848d12684dbbd50b35a7657c22579932c0dc08c0613f9d6369ce314df730cbebd591e56c2ddba7bfbab63887981f9fe1a706812d6de9107fa
|
data/.rubocop.yml
CHANGED
@@ -1,12 +1,14 @@
|
|
1
1
|
require: rubocop-performance
|
2
2
|
|
3
3
|
AllCops:
|
4
|
-
TargetRubyVersion:
|
4
|
+
TargetRubyVersion: 3.0
|
5
|
+
NewCops: enable
|
6
|
+
SuggestExtensions: false
|
5
7
|
|
6
|
-
|
8
|
+
Layout/LineLength:
|
7
9
|
Max: 99
|
8
10
|
|
9
|
-
Documentation:
|
11
|
+
Style/Documentation:
|
10
12
|
Enabled: false
|
11
13
|
|
12
14
|
Style/RegexpLiteral:
|
@@ -14,3 +16,12 @@ Style/RegexpLiteral:
|
|
14
16
|
|
15
17
|
Metrics/ClassLength:
|
16
18
|
Enabled: false
|
19
|
+
|
20
|
+
Lint/MissingSuper:
|
21
|
+
Enabled: false
|
22
|
+
|
23
|
+
Style/OptionalBooleanParameter:
|
24
|
+
Enabled: false
|
25
|
+
|
26
|
+
Metrics/AbcSize:
|
27
|
+
Enabled: true
|
data/.ruby-version
CHANGED
@@ -1 +1 @@
|
|
1
|
-
|
1
|
+
3.1.7
|
data/Dockerfile
CHANGED
@@ -1,11 +1,11 @@
|
|
1
1
|
FROM ubuntu:22.04
|
2
|
-
|
2
|
+
LABEL maintainer="OpenHub <info@openhub.net>"
|
3
3
|
|
4
|
-
ENV HOME
|
5
|
-
ENV LC_ALL
|
6
|
-
ENV APP_HOME
|
7
|
-
ENV DEBIAN_FRONTEND
|
8
|
-
ENV PATH
|
4
|
+
ENV HOME=/home
|
5
|
+
ENV LC_ALL=en_US.UTF-8
|
6
|
+
ENV APP_HOME=$HOME/app/ohloh_scm
|
7
|
+
ENV DEBIAN_FRONTEND=noninteractive
|
8
|
+
ENV PATH=$HOME/.rbenv/shims:$HOME/.rbenv/bin:$HOME/.rbenv/plugins/ruby-build/bin:$PATH
|
9
9
|
|
10
10
|
RUN apt-get update
|
11
11
|
RUN apt-get install -y build-essential software-properties-common locales ragel \
|
@@ -23,7 +23,7 @@ RUN cd $HOME \
|
|
23
23
|
&& echo 'eval "$(rbenv init -)"' >> $HOME/.bashrc \
|
24
24
|
&& echo 'gem: --no-rdoc --no-ri' >> $HOME/.gemrc \
|
25
25
|
&& echo 'export PATH="$HOME/.rbenv/shims:$HOME/.rbenv/bin:/home/.rbenv/plugins/ruby-build/bin:$PATH"' >> $HOME/.bash_profile \
|
26
|
-
&& rbenv install
|
26
|
+
&& rbenv install 3.1.7 && rbenv global 3.1.7
|
27
27
|
|
28
28
|
RUN git config --global --add safe.directory '*'
|
29
29
|
|
@@ -41,7 +41,7 @@ RUN ln -s /usr/bin/cvs /usr/bin/cvsnt
|
|
41
41
|
# Run bundle install before copying source to keep this step cached.
|
42
42
|
RUN mkdir -p $APP_HOME
|
43
43
|
COPY Gemfile* $APP_HOME/
|
44
|
-
RUN gem install rake bundler:
|
44
|
+
RUN gem install rake bundler:2.6.9 \
|
45
45
|
&& bundle config --global silence_root_warning 1 \
|
46
46
|
&& cd $APP_HOME && bundle install
|
47
47
|
|
data/Gemfile
CHANGED
data/Gemfile.lock
CHANGED
@@ -1,41 +1,56 @@
|
|
1
1
|
GEM
|
2
2
|
remote: https://rubygems.org/
|
3
3
|
specs:
|
4
|
-
ast (2.4.
|
5
|
-
byebug (
|
6
|
-
docile (1.
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
mini_portile2 (2.
|
11
|
-
minitest (5.
|
12
|
-
mocha (
|
13
|
-
|
14
|
-
nokogiri (1.
|
15
|
-
mini_portile2 (~> 2.
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
4
|
+
ast (2.4.3)
|
5
|
+
byebug (12.0.0)
|
6
|
+
docile (1.4.1)
|
7
|
+
json (2.12.2)
|
8
|
+
language_server-protocol (3.17.0.5)
|
9
|
+
lint_roller (1.1.0)
|
10
|
+
mini_portile2 (2.8.9)
|
11
|
+
minitest (5.25.5)
|
12
|
+
mocha (2.7.1)
|
13
|
+
ruby2_keywords (>= 0.0.5)
|
14
|
+
nokogiri (1.18.8)
|
15
|
+
mini_portile2 (~> 2.8.2)
|
16
|
+
racc (~> 1.4)
|
17
|
+
parallel (1.27.0)
|
18
|
+
parser (3.3.8.0)
|
19
|
+
ast (~> 2.4.1)
|
20
|
+
racc
|
21
|
+
prism (1.4.0)
|
22
|
+
racc (1.8.1)
|
23
|
+
rainbow (3.1.1)
|
24
|
+
rake (13.2.1)
|
25
|
+
regexp_parser (2.10.0)
|
26
|
+
rubocop (1.75.8)
|
27
|
+
json (~> 2.3)
|
28
|
+
language_server-protocol (~> 3.17.0.2)
|
29
|
+
lint_roller (~> 1.1.0)
|
24
30
|
parallel (~> 1.10)
|
25
|
-
parser (>=
|
26
|
-
psych (>= 3.1.0)
|
31
|
+
parser (>= 3.3.0.2)
|
27
32
|
rainbow (>= 2.2.2, < 4.0)
|
33
|
+
regexp_parser (>= 2.9.3, < 3.0)
|
34
|
+
rubocop-ast (>= 1.44.0, < 2.0)
|
28
35
|
ruby-progressbar (~> 1.7)
|
29
|
-
unicode-display_width (>=
|
30
|
-
rubocop-
|
31
|
-
|
32
|
-
|
33
|
-
|
36
|
+
unicode-display_width (>= 2.4.0, < 4.0)
|
37
|
+
rubocop-ast (1.44.1)
|
38
|
+
parser (>= 3.3.7.2)
|
39
|
+
prism (~> 1.4)
|
40
|
+
rubocop-performance (1.10.2)
|
41
|
+
rubocop (>= 0.90.0, < 2.0)
|
42
|
+
rubocop-ast (>= 0.4.0)
|
43
|
+
ruby-progressbar (1.13.0)
|
44
|
+
ruby2_keywords (0.0.5)
|
45
|
+
simplecov (0.22.0)
|
34
46
|
docile (~> 1.1)
|
35
|
-
|
36
|
-
|
37
|
-
simplecov-html (0.
|
38
|
-
|
47
|
+
simplecov-html (~> 0.11)
|
48
|
+
simplecov_json_formatter (~> 0.1)
|
49
|
+
simplecov-html (0.13.1)
|
50
|
+
simplecov_json_formatter (0.1.4)
|
51
|
+
unicode-display_width (3.1.4)
|
52
|
+
unicode-emoji (~> 4.0, >= 4.0.4)
|
53
|
+
unicode-emoji (4.0.4)
|
39
54
|
|
40
55
|
PLATFORMS
|
41
56
|
ruby
|
@@ -46,9 +61,9 @@ DEPENDENCIES
|
|
46
61
|
mocha
|
47
62
|
nokogiri
|
48
63
|
rake
|
49
|
-
rubocop (
|
64
|
+
rubocop (>= 1.12.0)
|
50
65
|
rubocop-performance
|
51
66
|
simplecov
|
52
67
|
|
53
68
|
BUNDLED WITH
|
54
|
-
|
69
|
+
2.6.9
|
data/lib/ohloh_scm/activity.rb
CHANGED
@@ -29,7 +29,7 @@ module OhlohScm
|
|
29
29
|
# Unlike other SCMs, Bzr doesn't simply place the contents into dest_dir.
|
30
30
|
# It actually *creates* dest_dir. Since it should already exist at this point,
|
31
31
|
# first we have to delete it.
|
32
|
-
|
32
|
+
FileUtils.rm_f(dest_dir)
|
33
33
|
|
34
34
|
run "cd '#{url}' && bzr export --format=dir -r #{to_rev_param(token)} '#{dest_dir}'"
|
35
35
|
end
|
@@ -45,7 +45,7 @@ module OhlohScm
|
|
45
45
|
a = OhlohScm::BzrXmlParser.parse(log)
|
46
46
|
|
47
47
|
if after && (i = a.index { |commit| commit.token == after })
|
48
|
-
a[(i + 1)
|
48
|
+
a[(i + 1)..]
|
49
49
|
else
|
50
50
|
a
|
51
51
|
end
|
@@ -74,8 +74,8 @@ module OhlohScm
|
|
74
74
|
end
|
75
75
|
|
76
76
|
def head_token
|
77
|
-
run("bzr log --limit 1 --show-id #{url} 2> /dev/null"\
|
78
|
-
"
|
77
|
+
run("bzr log --limit 1 --show-id #{url} 2> /dev/null " \
|
78
|
+
"| grep ^revision-id | cut -f2 -d' '").strip
|
79
79
|
end
|
80
80
|
|
81
81
|
def head
|
@@ -136,24 +136,24 @@ module OhlohScm
|
|
136
136
|
# +after+. However, bzr doesn't work that way; it returns
|
137
137
|
# everything after and INCLUDING +after+. Therefore, consumers
|
138
138
|
# of this file should check for and reject the duplicate commit.
|
139
|
-
def safe_open_log_file(opts = {})
|
139
|
+
def safe_open_log_file(opts = {}, &block)
|
140
140
|
return '' if opts[:after] && opts[:after] == head_token
|
141
141
|
|
142
|
-
open_log_file(opts)
|
142
|
+
open_log_file(opts, &block)
|
143
143
|
end
|
144
144
|
|
145
|
-
def open_log_file(opts = {})
|
145
|
+
def open_log_file(opts = {}, &block)
|
146
146
|
cmd = "#{rev_list_command(opts)} -v > #{log_filename}"
|
147
147
|
run cmd
|
148
|
-
File.open(log_filename, 'r')
|
148
|
+
File.open(log_filename, 'r', &block)
|
149
149
|
ensure
|
150
|
-
|
150
|
+
FileUtils.rm_f(log_filename)
|
151
151
|
end
|
152
152
|
|
153
153
|
# Ohloh tracks only files, not directories. This function removes directories
|
154
154
|
# from the commit diffs.
|
155
155
|
def remove_directories(commit)
|
156
|
-
commit.diffs.delete_if { |d| d.path[-1
|
156
|
+
commit.diffs.delete_if { |d| d.path[-1..] == '/' }
|
157
157
|
commit
|
158
158
|
end
|
159
159
|
|
@@ -164,11 +164,11 @@ module OhlohScm
|
|
164
164
|
# Bzr doesn't like it when the filename includes a colon
|
165
165
|
# Also, fix the case where the filename includes a single quote
|
166
166
|
def escape(path)
|
167
|
-
path.gsub(
|
167
|
+
path.gsub(':') { |c| "\\#{c}" }.gsub("'", "''")
|
168
168
|
end
|
169
169
|
|
170
170
|
def tag_strings
|
171
|
-
run("cd '#{url}' && bzr tags").split(
|
171
|
+
run("cd '#{url}' && bzr tags").split("\n")
|
172
172
|
end
|
173
173
|
|
174
174
|
def time_string(rev)
|
data/lib/ohloh_scm/commit.rb
CHANGED
@@ -24,9 +24,7 @@ module OhlohScm
|
|
24
24
|
attr_accessor :author_name, :author_email, :author_date,
|
25
25
|
:committer_name, :committer_email, :committer_date
|
26
26
|
|
27
|
-
attr_accessor :message
|
28
|
-
|
29
|
-
attr_accessor :diffs
|
27
|
+
attr_accessor :message, :diffs
|
30
28
|
|
31
29
|
# The token is used to uniquely identify a commit, and can be any type of
|
32
30
|
# adapter-specific data.
|
@@ -46,7 +44,7 @@ module OhlohScm
|
|
46
44
|
attr_accessor :directories
|
47
45
|
|
48
46
|
def initialize(params = {})
|
49
|
-
params.each { |k, v| send(k
|
47
|
+
params.each { |k, v| send("#{k}=", v) if respond_to?("#{k}=") }
|
50
48
|
end
|
51
49
|
end
|
52
50
|
end
|
data/lib/ohloh_scm/core.rb
CHANGED
@@ -11,9 +11,10 @@ module OhlohScm
|
|
11
11
|
def initialize(scm_type, url, branch_name, username, password)
|
12
12
|
scm_opts = { core: self, url: url, branch_name: branch_name,
|
13
13
|
username: username, password: password }
|
14
|
+
|
14
15
|
scm_class_name = scm_type.to_s.camelize
|
15
16
|
|
16
|
-
@scm = OhlohScm.const_get(scm_class_name)::Scm.new(scm_opts)
|
17
|
+
@scm = OhlohScm.const_get(scm_class_name)::Scm.new(**scm_opts)
|
17
18
|
@activity = OhlohScm.const_get(scm_class_name)::Activity.new(self)
|
18
19
|
@status = OhlohScm.const_get(scm_class_name)::Status.new(self)
|
19
20
|
@validation = OhlohScm.const_get(scm_class_name)::Validation.new(self)
|
@@ -5,79 +5,95 @@ module OhlohScm
|
|
5
5
|
class Activity < OhlohScm::Activity
|
6
6
|
def tags
|
7
7
|
cmd = "cvs -Q -d #{url} rlog -h #{scm.branch_name} | awk -F\"[.:]\" '/^\\t/&&$(NF-1)!=0'"
|
8
|
-
|
9
|
-
tag_strings.map do |tag_string|
|
8
|
+
run(cmd).split("\n").map do |tag_string|
|
10
9
|
tag_name, version = tag_string.split(':')
|
11
10
|
[tag_name.delete("\t"), version.strip]
|
12
11
|
end
|
13
12
|
end
|
14
13
|
|
15
|
-
# rubocop:disable Metrics/AbcSize, Metrics/MethodLength
|
16
14
|
def commits(opts = {})
|
17
|
-
|
18
|
-
|
15
|
+
result = fetch_commits(opts)
|
16
|
+
# Nothing found; we're done here. || We requested everything, so just return everything.
|
17
|
+
return result if result.empty? || opts[:after].to_s.empty?
|
19
18
|
|
20
|
-
|
21
|
-
|
22
|
-
end
|
19
|
+
filter_commits(result, opts[:after])
|
20
|
+
end
|
23
21
|
|
24
|
-
|
25
|
-
|
22
|
+
def export_tag(dest_dir, tag_name = 'HEAD')
|
23
|
+
run "cvsnt -d #{url} export -d'#{dest_dir}' -r #{tag_name} '#{scm.branch_name}'"
|
24
|
+
end
|
26
25
|
|
27
|
-
|
28
|
-
|
26
|
+
# using :ext (ssh) protocol might trigger ssh to confirm accepting the host's
|
27
|
+
# ssh key. This causes the UI to hang asking for manual confirmation. To avoid
|
28
|
+
# this we pre-populate the ~/.ssh/known_hosts file with the host's key.
|
29
|
+
def ensure_host_key
|
30
|
+
return if protocol != :ext
|
29
31
|
|
30
|
-
|
31
|
-
|
32
|
+
ensure_key_file = "#{File.dirname(__FILE__)}/../../../../bin/ensure_key"
|
33
|
+
cmd = "#{ensure_key_file} '#{host}'"
|
34
|
+
run_with_err(cmd)
|
35
|
+
end
|
32
36
|
|
33
|
-
|
34
|
-
|
35
|
-
|
37
|
+
private
|
38
|
+
|
39
|
+
def fetch_commits(opts)
|
40
|
+
OhlohScm::CvsParser.parse(open_log_file(opts)).tap do |result|
|
41
|
+
# Git converter needs a backpointer to the scm for each commit
|
42
|
+
result.each { |c| c.scm = scm }
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
def filter_commits(commits, after)
|
47
|
+
return commits if first_commit_newer?(commits, after)
|
36
48
|
|
37
49
|
# Walk the list of commits to find the first new one, throwing away all of the old ones.
|
38
50
|
|
39
51
|
# I want to string-compare timestamps without converting to dates objects.
|
40
52
|
# Some CVS servers print dates as 2006/01/02 03:04:05, others as 2006-01-02 03:04:05.
|
41
53
|
# To work around this, we'll build a regex that matches either date format.
|
42
|
-
|
54
|
+
timestamp_regex = create_timestamp_regex(after)
|
55
|
+
match_index = find_match_index(commits, timestamp_regex)
|
43
56
|
|
44
|
-
|
45
|
-
|
46
|
-
return [] if i == result.size - 1 # There aren't any new commits.
|
57
|
+
extract_new_commits(commits, match_index)
|
58
|
+
end
|
47
59
|
|
48
|
-
|
49
|
-
|
60
|
+
def first_commit_newer?(commits, after)
|
61
|
+
# We must now remove any duplicates caused by timestamp fudge factors,
|
62
|
+
# and only return commits with timestamp > after.
|
50
63
|
|
51
|
-
#
|
52
|
-
#
|
53
|
-
|
54
|
-
# Often this means that the *last* time we ran commits(), there was some kind of
|
55
|
-
# undetected problem (CVS was in an intermediate state?) so the list of timestamps we
|
56
|
-
# calculated last time does not match the list of timestamps we calculated this time.
|
57
|
-
#
|
58
|
-
# There's no work around for this condition here in the code, but there are some things
|
59
|
-
# you can try manually to fix the problem. Typically, you can try throwing way the
|
60
|
-
# commit associated with 'after' and fetching it again (git reset --hard HEAD^).
|
61
|
-
raise "token '#{after}' not found in rlog."
|
64
|
+
# If the first commit is newer than after,
|
65
|
+
# then the whole list is new and we can simply return.
|
66
|
+
parse_time(commits.first.token) > parse_time(after)
|
62
67
|
end
|
63
|
-
# rubocop:enable Metrics/AbcSize, Metrics/MethodLength
|
64
68
|
|
65
|
-
def
|
66
|
-
|
69
|
+
def create_timestamp_regex(timestamp)
|
70
|
+
Regexp.new(timestamp.gsub(/[\/-]/, '.'))
|
67
71
|
end
|
68
72
|
|
69
|
-
|
70
|
-
|
71
|
-
# this we pre-populate the ~/.ssh/known_hosts file with the host's key.
|
72
|
-
def ensure_host_key
|
73
|
-
return if protocol != :ext
|
74
|
-
|
75
|
-
ensure_key_file = File.dirname(__FILE__) + '/../../../../bin/ensure_key'
|
76
|
-
cmd = "#{ensure_key_file} '#{host}'"
|
77
|
-
run_with_err(cmd)
|
73
|
+
def find_match_index(commits, timestamp_regex)
|
74
|
+
commits.index { |commit| commit.token&.match?(timestamp_regex) }
|
78
75
|
end
|
79
76
|
|
80
|
-
|
77
|
+
def extract_new_commits(commits, match_index)
|
78
|
+
case match_index
|
79
|
+
when nil
|
80
|
+
# Something bad is going on: 'after' does not match any timestamp in the rlog.
|
81
|
+
# This is very rare, but it can happen.
|
82
|
+
#
|
83
|
+
# Often this means that the *last* time we ran commits(), there was some kind of
|
84
|
+
# undetected problem (CVS was in an intermediate state?) so the list of timestamps we
|
85
|
+
# calculated last time does not match the list of timestamps we calculated this time.
|
86
|
+
#
|
87
|
+
# There's no work around for this condition here in the code, but there are some things
|
88
|
+
# you can try manually to fix the problem. Typically, you can try throwing way the
|
89
|
+
# commit associated with 'after' and fetching it again (git reset --hard HEAD^).
|
90
|
+
raise 'token not found in rlog.'
|
91
|
+
when commits.size - 1
|
92
|
+
[]
|
93
|
+
else
|
94
|
+
commits[match_index + 1..]
|
95
|
+
end
|
96
|
+
end
|
81
97
|
|
82
98
|
# Gets the rlog of the repository and saves it in a temporary file.
|
83
99
|
# If you pass a timestamp token, then only commits after the timestamp will be returned.
|
@@ -91,29 +107,27 @@ module OhlohScm
|
|
91
107
|
# This means that the returned log might actually contain a few revisions
|
92
108
|
# that predate the requested time.
|
93
109
|
# That's better than missing revisions completely! Just be sure to check for duplicates.
|
94
|
-
|
95
|
-
def open_log_file(opts = {})
|
110
|
+
def open_log_file(opts = {}, &block)
|
96
111
|
ensure_host_key
|
97
112
|
status.lock?
|
98
|
-
run "cvsnt -d #{url} rlog #{opt_branch} #{opt_time(opts[:after])} '#{scm.branch_name}'"\
|
99
|
-
|
100
|
-
File.open(rlog_filename, 'r')
|
113
|
+
run "cvsnt -d #{url} rlog #{opt_branch} #{opt_time(opts[:after])} '#{scm.branch_name}' " \
|
114
|
+
"| #{string_encoder_path} > #{rlog_filename}"
|
115
|
+
File.open(rlog_filename, 'r', &block)
|
101
116
|
ensure
|
102
|
-
|
117
|
+
FileUtils.rm_f(rlog_filename)
|
103
118
|
end
|
104
|
-
# rubocop:enable Metrics/AbcSize
|
105
119
|
|
106
120
|
def opt_time(after = nil)
|
107
121
|
return '' unless after
|
108
122
|
|
109
123
|
most_recent_time = parse_time(after) - 10
|
110
|
-
# rubocop:disable
|
124
|
+
# rubocop:disable Layout/LineLength
|
111
125
|
" -d '#{most_recent_time.strftime('%Y-%m-%d %H:%M:%S')}Z<#{Time.now.utc.strftime('%Y-%m-%d %H:%M:%S')}Z' "
|
112
|
-
# rubocop:enable
|
126
|
+
# rubocop:enable Layout/LineLength
|
113
127
|
end
|
114
128
|
|
115
129
|
def rlog_filename
|
116
|
-
File.join(temp_folder, (url + scm.branch_name.to_s).gsub(/\W/, '')
|
130
|
+
File.join(temp_folder, "#{(url + scm.branch_name.to_s).gsub(/\W/, '')}.rlog")
|
117
131
|
end
|
118
132
|
|
119
133
|
# Converts a CVS time string to a Ruby Time object
|
@@ -128,9 +142,9 @@ module OhlohScm
|
|
128
142
|
# returns the host this adapter is connecting to
|
129
143
|
def host
|
130
144
|
@host ||= begin
|
131
|
-
|
132
|
-
|
133
|
-
|
145
|
+
url =~ /@([^:]*):/
|
146
|
+
Regexp.last_match(1)
|
147
|
+
end
|
134
148
|
end
|
135
149
|
|
136
150
|
# returns the protocol this adapter connects with
|
data/lib/ohloh_scm/cvs/scm.rb
CHANGED
@@ -9,9 +9,14 @@ module OhlohScm
|
|
9
9
|
opt_d = rev.token ? "-D'#{rev.token}Z'" : ''
|
10
10
|
|
11
11
|
activity.ensure_host_key
|
12
|
-
if File.exist?(local_directory
|
12
|
+
if File.exist?("#{local_directory}/CVS/Root")
|
13
13
|
# We already have a local enlistment, so do a quick update.
|
14
|
-
if
|
14
|
+
if rev.directories.empty?
|
15
|
+
# Brute force: get all updates
|
16
|
+
logger.warn("Revision #{rev.token} did not contain any directories.
|
17
|
+
Using brute force update of entire module.")
|
18
|
+
run "cd #{local_directory} && cvsnt update -d -R -C #{opt_d}"
|
19
|
+
else
|
15
20
|
build_ordered_directory_list(rev.directories).each do |d|
|
16
21
|
if d.empty?
|
17
22
|
run "cd #{local_directory} && cvsnt update -d -l -C #{opt_d} ."
|
@@ -19,18 +24,13 @@ module OhlohScm
|
|
19
24
|
run "cd #{local_directory} && cvsnt update -d -l -C #{opt_d} '#{d}'"
|
20
25
|
end
|
21
26
|
end
|
22
|
-
else
|
23
|
-
# Brute force: get all updates
|
24
|
-
logger.warn("Revision #{rev.token} did not contain any directories.
|
25
|
-
Using brute force update of entire module.")
|
26
|
-
run "cd #{local_directory} && cvsnt update -d -R -C #{opt_d}"
|
27
27
|
end
|
28
28
|
else
|
29
29
|
# We do not have a local enlistment, so do a slow checkout to create one.
|
30
30
|
# Silly cvsnt won't accept an absolute path.
|
31
31
|
# We'll have to play some games and cd to the parent directory.
|
32
32
|
parent_path, checkout_dir = File.split(local_directory)
|
33
|
-
FileUtils.mkdir_p(parent_path)
|
33
|
+
FileUtils.mkdir_p(parent_path)
|
34
34
|
run "cd #{parent_path} &&
|
35
35
|
cvsnt -d #{url} checkout #{opt_d} -A -d'#{checkout_dir}' '#{branch_name}'"
|
36
36
|
end
|
@@ -66,7 +66,7 @@ module OhlohScm
|
|
66
66
|
# using cvs modules that are only a single directory deep when testing.
|
67
67
|
# We'll check if the url begins with '/' to detect an integration test,
|
68
68
|
# then return an empty string (ie, the default root directory) if so.
|
69
|
-
return [''] if url
|
69
|
+
return [''] if /^\//.match?(url)
|
70
70
|
|
71
71
|
list = []
|
72
72
|
directories = directories.collect { |a| trim_directory(a.to_s).to_s }
|
@@ -105,7 +105,7 @@ module OhlohScm
|
|
105
105
|
# For example, if url = ':pserver:anonymous:@moodle.cvs.sourceforge.net:/cvsroot/moodle'
|
106
106
|
# and module = 'contrib', then the directory prefix = '/cvsroot/moodle/contrib/'
|
107
107
|
# If not remote, just leave the directory name as-is
|
108
|
-
root ? dir[root.length
|
108
|
+
root ? dir[root.length..] : dir
|
109
109
|
end
|
110
110
|
|
111
111
|
def root
|
@@ -126,7 +126,7 @@ module OhlohScm
|
|
126
126
|
# found in the :pserver: url is assigned to both.
|
127
127
|
def sync_pserver_username_password
|
128
128
|
# Do nothing unless pserver connection string is well-formed.
|
129
|
-
return unless url =~ /:pserver:([\w
|
129
|
+
return unless url =~ /:pserver:([\w\-_]*)(:([\w\-_]*))?@(.*)$/
|
130
130
|
|
131
131
|
pserver_username = Regexp.last_match(1)
|
132
132
|
pserver_password = Regexp.last_match(3)
|
@@ -140,7 +140,7 @@ module OhlohScm
|
|
140
140
|
|
141
141
|
# Based on the URL, take a guess about which forge this code is hosted on.
|
142
142
|
def guess_forge
|
143
|
-
return unless url =~ /.*(pserver|ext).*@(([
|
143
|
+
return unless url =~ /.*(pserver|ext).*@(([^.]+\.)?(cvs|dev)\.)?([^:]+):\//i
|
144
144
|
|
145
145
|
Regexp.last_match(5).downcase
|
146
146
|
end
|
data/lib/ohloh_scm/cvs/status.rb
CHANGED
@@ -7,7 +7,7 @@ module OhlohScm
|
|
7
7
|
run "timeout 2m cvsnt -q -d #{scm.url} rlog '#{scm.branch_name}'"
|
8
8
|
false
|
9
9
|
rescue StandardError => e
|
10
|
-
raise 'CVS lock has been found' if
|
10
|
+
raise 'CVS lock has been found' if /waiting for.*lock in/.match?(e.message)
|
11
11
|
end
|
12
12
|
end
|
13
13
|
end
|
@@ -17,16 +17,16 @@ module OhlohScm
|
|
17
17
|
def branch_name_errors
|
18
18
|
if scm.branch_name.to_s.empty?
|
19
19
|
[:branch_name, "The branch name can't be blank."]
|
20
|
-
elsif scm.branch_name.length >
|
21
|
-
[:branch_name, 'The branch name must not be longer than
|
22
|
-
elsif !scm.branch_name.match?(/^[\w
|
20
|
+
elsif scm.branch_name.length > 200
|
21
|
+
[:branch_name, 'The branch name must not be longer than 200 characters.']
|
22
|
+
elsif !scm.branch_name.match?(/^[\w\-+.\/\ ]+$/)
|
23
23
|
[:branch_name, "The branch name may contain only letters,
|
24
24
|
numbers, spaces, and the special characters '_', '-', '+', '/', and '.'"]
|
25
25
|
end
|
26
26
|
end
|
27
27
|
|
28
28
|
def public_url_regex
|
29
|
-
/^:(pserver|ext):[\w
|
29
|
+
/^:(pserver|ext):[\w\-+_]*(:[\w\-+_]*)?@[\w\-+.]+:[0-9]*\/[\w\-+.\/]*$/
|
30
30
|
end
|
31
31
|
|
32
32
|
# Returns an array of file and directory names from the remote server.
|
@@ -56,7 +56,7 @@ module OhlohScm
|
|
56
56
|
files = []
|
57
57
|
output.each_line do |s|
|
58
58
|
s.strip!
|
59
|
-
s = Regexp.last_match(1)
|
59
|
+
s = "#{Regexp.last_match(1)}/" if s =~ /^D\/(.*)\/\/\/\/$/
|
60
60
|
s = Regexp.last_match(1) if s =~ /^\/(.*)\/.*\/.*\/.*\/$/
|
61
61
|
next if s == 'CVSROOT/'
|
62
62
|
|
data/lib/ohloh_scm/diff.rb
CHANGED
@@ -34,7 +34,7 @@ module OhlohScm
|
|
34
34
|
attr_accessor :from_path, :from_revision
|
35
35
|
|
36
36
|
def initialize(params = {})
|
37
|
-
params.each { |k, v| send(k
|
37
|
+
params.each { |k, v| send("#{k}=", v) if respond_to?("#{k}=") }
|
38
38
|
end
|
39
39
|
|
40
40
|
# eql?() and hash() are implemented so that [].uniq() will work on an array of Diffs.
|