proxy_tester 0.0.1 → 0.0.2
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.
- data/Gemfile +2 -0
- data/Gemfile.lock +18 -1
- data/README.md +88 -4
- data/bin/proxy_tester +11 -0
- data/config.yaml +0 -0
- data/features/.keep +0 -0
- data/features/add_test_case.feature +41 -0
- data/features/step_definitions.rb +30 -0
- data/features/support/debugging.rb +3 -0
- data/features/support/env.rb +12 -0
- data/features/support/environment.rb +22 -0
- data/features/support/filesystem.rb +19 -0
- data/lib/proxy_tester.rb +11 -1
- data/lib/proxy_tester/actions/add_test_case.rb +40 -0
- data/lib/proxy_tester/actions/clear_environment.rb +21 -0
- data/lib/proxy_tester/actions/fetch_urls.rb +94 -0
- data/lib/proxy_tester/actions/handle_error.rb +10 -6
- data/lib/proxy_tester/capybara_proxy.rb +1 -1
- data/lib/proxy_tester/cli/main.rb +10 -3
- data/lib/proxy_tester/cli/test.rb +79 -0
- data/lib/proxy_tester/config.rb +1 -1
- data/lib/proxy_tester/error_handler.rb +16 -7
- data/lib/proxy_tester/error_messages.rb +45 -3
- data/lib/proxy_tester/exceptions.rb +31 -2
- data/lib/proxy_tester/git_repository.rb +6 -7
- data/lib/proxy_tester/http_proxy.rb +48 -0
- data/lib/proxy_tester/locales/en.yml +18 -0
- data/lib/proxy_tester/main.rb +1 -1
- data/lib/proxy_tester/models/user.rb +2 -2
- data/lib/proxy_tester/remote_repository.rb +55 -0
- data/lib/proxy_tester/reporters/fetch_urls.rb +34 -0
- data/lib/proxy_tester/version.rb +2 -1
- data/proxy_tester.gemspec +2 -0
- data/script/ci +4 -0
- data/script/test_web +5 -2
- data/spec/actions/add_test_case_spec.rb +81 -0
- data/spec/actions/fetch_urls_spec.rb +52 -0
- data/spec/actions/handle_error_spec.rb +1 -1
- data/spec/capybara_proxy_spec.rb +1 -1
- data/spec/git_repository_spec.rb +22 -0
- data/spec/http_proxy_spec.rb +47 -0
- data/spec/remote_repository_spec.rb +103 -0
- data/spec/reporters/fetch_urls_spec.rb +58 -0
- data/spec/support/filesystem.rb +2 -0
- data/spec/support/reporting.rb +6 -0
- data/spec/user_spec.rb +10 -2
- metadata +66 -5
- data/lib/proxy_tester/actions/clone_repository.rb +0 -39
- data/spec/actions/clone_repository_spec.rb +0 -83
@@ -29,13 +29,6 @@ module ProxyTester
|
|
29
29
|
def self.clone(source, destination, options = {})
|
30
30
|
bare = options.fetch(:bare, false)
|
31
31
|
|
32
|
-
source = Addressable::URI.heuristic_parse(::File.expand_path(source))
|
33
|
-
if source.scheme.blank?
|
34
|
-
source.scheme = 'file'
|
35
|
-
source.authority = ''
|
36
|
-
end
|
37
|
-
source = source.to_s
|
38
|
-
|
39
32
|
destination = ::File.expand_path(destination)
|
40
33
|
|
41
34
|
if bare
|
@@ -45,6 +38,12 @@ module ProxyTester
|
|
45
38
|
end
|
46
39
|
|
47
40
|
new(destination)
|
41
|
+
rescue Rugged::NetworkError
|
42
|
+
raise Exceptions::RepositoryDoesNotExist, JSON.dump(repository: source)
|
43
|
+
rescue Rugged::OSError
|
44
|
+
raise Exceptions::RepositoryDoesNotExist, JSON.dump(repository: source)
|
45
|
+
rescue Rugged::RepositoryError
|
46
|
+
raise Exceptions::RepositoryInvalid, JSON.dump(repository: source)
|
48
47
|
end
|
49
48
|
|
50
49
|
def add_content(path, content = '', mode = 0100644, commit_info = default_commit_info)
|
@@ -0,0 +1,48 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
module ProxyTester
|
3
|
+
class HttpProxy
|
4
|
+
|
5
|
+
private
|
6
|
+
|
7
|
+
attr_reader :user
|
8
|
+
|
9
|
+
public
|
10
|
+
|
11
|
+
attr_reader :host, :port
|
12
|
+
|
13
|
+
def initialize(connection_string)
|
14
|
+
match = connection_string_pattern.match(connection_string) || {}
|
15
|
+
|
16
|
+
raise Exceptions::ProxyConnectionStringInvalid, JSON.dump(connection_string: connection_string) if match[:host].blank?
|
17
|
+
raise Exceptions::ProxyConnectionStringInvalid, JSON.dump(connection_string: connection_string) if match[:port].blank?
|
18
|
+
|
19
|
+
@host = match[:host]
|
20
|
+
@port = match[:port]
|
21
|
+
end
|
22
|
+
|
23
|
+
def use_user(user)
|
24
|
+
@user = user
|
25
|
+
end
|
26
|
+
|
27
|
+
def to_string(options = {})
|
28
|
+
result = []
|
29
|
+
result << 'http://'
|
30
|
+
|
31
|
+
if user and options[:cleartext] == true
|
32
|
+
result << "#{user.name}:#{user.password}@"
|
33
|
+
elsif user
|
34
|
+
result << "#{user.name}:#{'*' * 4}@" if user
|
35
|
+
end
|
36
|
+
|
37
|
+
result << "#{host}:#{port}"
|
38
|
+
|
39
|
+
result.join
|
40
|
+
end
|
41
|
+
|
42
|
+
private
|
43
|
+
|
44
|
+
def connection_string_pattern
|
45
|
+
/(?<host>[[:alnum:]._-]+):(?<port>\d+{1,5})/
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
@@ -37,6 +37,24 @@ en:
|
|
37
37
|
invalid_proxy_type:
|
38
38
|
summary: Invalid proxy type...
|
39
39
|
details: 'Sorry, but I cannot fullfill your request. You provided an invalid proxy type "%{type}". Allowed values are ":none", ":http" or ":socks5".'
|
40
|
+
invalid_proxy_connection_string:
|
41
|
+
summary: Invalid Proxy Connection String...
|
42
|
+
details: 'Sorry, but I cannot fullfill your request. You provided an invalid proxy connection string "%{string}". It needs to be something like "proxy:port".'
|
43
|
+
unreachable_proxy:
|
44
|
+
summary: Unreachable Proxy...
|
45
|
+
details: 'Sorry, but I cannot fullfill your request. I was not able to contact the given proxy "%{host}" on port "%{port}". Maybe it is an invalid hostname?'
|
46
|
+
unexisting_repository:
|
47
|
+
summary: Repository Does Not Exist...
|
48
|
+
details: 'Sorry, but I cannot fullfill your request. The path "%{repository}" you provided does not exist.'
|
49
|
+
invalid_repository:
|
50
|
+
summary: Invalid Repository...
|
51
|
+
details: 'Sorry, but I cannot fullfill your request. The path "%{repository}" you provided is not a repository of a supported type (git).'
|
52
|
+
sigint:
|
53
|
+
summary: Program Execution Interrupted...
|
54
|
+
details: You've chosen to interrupt the program execution.
|
55
|
+
sigterm:
|
56
|
+
summary: Program Execution Aborted...
|
57
|
+
details: I received a SIGTERM. Aborting program execution.
|
40
58
|
views:
|
41
59
|
application:
|
42
60
|
title: Proxy Tester
|
data/lib/proxy_tester/main.rb
CHANGED
@@ -0,0 +1,55 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
module ProxyTester
|
3
|
+
class RemoteRepository
|
4
|
+
|
5
|
+
private
|
6
|
+
|
7
|
+
attr_reader :repository
|
8
|
+
|
9
|
+
public
|
10
|
+
|
11
|
+
# Create Remote Repository
|
12
|
+
def initialize(repository)
|
13
|
+
@repository = parse(repository)
|
14
|
+
end
|
15
|
+
|
16
|
+
# source path of repository
|
17
|
+
#
|
18
|
+
# @return [String]
|
19
|
+
# base path to repository
|
20
|
+
#
|
21
|
+
# @example
|
22
|
+
# http://githost/repo.git => repo
|
23
|
+
# user@host:/githost/repo.git => repo
|
24
|
+
def base
|
25
|
+
::File.basename(repository.path, '.*')
|
26
|
+
end
|
27
|
+
|
28
|
+
# source path of repository
|
29
|
+
#
|
30
|
+
# @return [String]
|
31
|
+
# path to repository
|
32
|
+
def source
|
33
|
+
repository.to_s
|
34
|
+
end
|
35
|
+
|
36
|
+
private
|
37
|
+
|
38
|
+
def parse(repo_string)
|
39
|
+
repo_string = ::File.expand_path(repo_string) if repo_string =~ %r{^(?:[^/@]+/)*[^/]+$}
|
40
|
+
|
41
|
+
repo = Addressable::URI.heuristic_parse(repo_string)
|
42
|
+
|
43
|
+
if repo.scheme.blank?
|
44
|
+
repo.scheme = 'file'
|
45
|
+
repo.authority = ''
|
46
|
+
repo.path = repo_string
|
47
|
+
elsif repo.scheme == 'ssh'
|
48
|
+
repo.host = repo.host + ':'
|
49
|
+
end
|
50
|
+
|
51
|
+
repo
|
52
|
+
end
|
53
|
+
|
54
|
+
end
|
55
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
module ProxyTester
|
3
|
+
module Reporters
|
4
|
+
class FetchUrls
|
5
|
+
|
6
|
+
private
|
7
|
+
|
8
|
+
attr_reader :output
|
9
|
+
|
10
|
+
public
|
11
|
+
|
12
|
+
def initialize(output = $stdout)
|
13
|
+
@output = output
|
14
|
+
end
|
15
|
+
|
16
|
+
def header
|
17
|
+
puts 'Results of run'
|
18
|
+
end
|
19
|
+
|
20
|
+
def data(d)
|
21
|
+
output.printf "%-10s: %s\n", 'proxy', d[:proxy]
|
22
|
+
output.printf "%-10s: %s\n", 'url', d[:url]
|
23
|
+
output.printf "%-10s: %s\n", 'status', d[:status]
|
24
|
+
|
25
|
+
output.printf "%-10s:\n", 'headers'
|
26
|
+
|
27
|
+
d[:headers].each do |h,v|
|
28
|
+
output.printf " %-20s: %s\n", h, v
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
end
|
data/lib/proxy_tester/version.rb
CHANGED
data/proxy_tester.gemspec
CHANGED
@@ -31,4 +31,6 @@ Gem::Specification.new do |spec|
|
|
31
31
|
spec.add_runtime_dependency 'poltergeist'
|
32
32
|
spec.add_runtime_dependency 'proxy_pac_rb', '~>0.2.5'
|
33
33
|
spec.add_runtime_dependency 'therubyracer'
|
34
|
+
spec.add_runtime_dependency 'excon'
|
35
|
+
spec.add_runtime_dependency 'highline'
|
34
36
|
end
|
data/script/ci
CHANGED
data/script/test_web
CHANGED
@@ -0,0 +1,81 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require 'spec_helper'
|
3
|
+
|
4
|
+
describe Actions::AddTestCase do
|
5
|
+
let(:remote_repository_path) { File.join(working_directory, 'git_repo.git') }
|
6
|
+
|
7
|
+
context '#initialize' do
|
8
|
+
it 'requires a source and a destination' do
|
9
|
+
repo = GitRepository.create(remote_repository_path)
|
10
|
+
repo.add_content('file.txt', 'asdf1')
|
11
|
+
|
12
|
+
remote_repository = double('RemoteRepository')
|
13
|
+
allow(remote_repository).to receive(:source).and_return("file://#{remote_repository_path}")
|
14
|
+
|
15
|
+
expect {
|
16
|
+
Actions::AddTestCase.new(remote_repository, working_directory)
|
17
|
+
}.not_to raise_error
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
context '#run' do
|
22
|
+
it 'runs the action' do
|
23
|
+
repo = GitRepository.create(remote_repository_path)
|
24
|
+
repo.add_content('file.txt', 'asdf1')
|
25
|
+
|
26
|
+
remote_repository = double('RemoteRepository')
|
27
|
+
allow(remote_repository).to receive(:to_string).and_return("file://#{remote_repository_path}")
|
28
|
+
allow(remote_repository).to receive(:source).and_return("file://#{remote_repository_path}")
|
29
|
+
allow(remote_repository).to receive(:base).and_return(::File.basename(remote_repository_path, '.git'))
|
30
|
+
|
31
|
+
action = Actions::AddTestCase.new(remote_repository, working_directory)
|
32
|
+
silence(:stderr) do
|
33
|
+
action.run
|
34
|
+
end
|
35
|
+
|
36
|
+
expect(path_exists?('git_repo')).to be_true
|
37
|
+
end
|
38
|
+
|
39
|
+
it 'respects existing path' do
|
40
|
+
repo = GitRepository.create(remote_repository_path)
|
41
|
+
repo.add_content('file.txt', 'asdf1')
|
42
|
+
|
43
|
+
remote_repository = double('RemoteRepository')
|
44
|
+
allow(remote_repository).to receive(:to_string).and_return("file://#{remote_repository_path}")
|
45
|
+
allow(remote_repository).to receive(:source).and_return("file://#{remote_repository_path}")
|
46
|
+
allow(remote_repository).to receive(:base).and_return(::File.basename(remote_repository_path, '.git'))
|
47
|
+
|
48
|
+
create_directory(::File.join(::File.basename(remote_repository_path, '.git'), '.git'))
|
49
|
+
|
50
|
+
action = Actions::AddTestCase.new(remote_repository, working_directory)
|
51
|
+
|
52
|
+
result = capture(:stderr) do
|
53
|
+
ProxyTester.ui_logger.level = :info
|
54
|
+
action.run
|
55
|
+
end
|
56
|
+
|
57
|
+
expect(result).to include('already')
|
58
|
+
end
|
59
|
+
|
60
|
+
it 'does remove existing path if forced to' do
|
61
|
+
repo = GitRepository.create(remote_repository_path)
|
62
|
+
repo.add_content('file.txt', 'asdf1')
|
63
|
+
|
64
|
+
remote_repository = double('RemoteRepository')
|
65
|
+
allow(remote_repository).to receive(:to_string).and_return("file://#{remote_repository_path}")
|
66
|
+
allow(remote_repository).to receive(:source).and_return("file://#{remote_repository_path}")
|
67
|
+
allow(remote_repository).to receive(:base).and_return(::File.basename(remote_repository_path, '.git'))
|
68
|
+
|
69
|
+
create_directory(::File.join(::File.basename(remote_repository_path, '.git'), '.git'))
|
70
|
+
|
71
|
+
action = Actions::AddTestCase.new(remote_repository, working_directory, force: true)
|
72
|
+
|
73
|
+
result = capture(:stderr) do
|
74
|
+
ProxyTester.ui_logger.level = :info
|
75
|
+
action.run
|
76
|
+
end
|
77
|
+
|
78
|
+
expect(result).to include('Add')
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
@@ -0,0 +1,52 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require 'spec_helper'
|
3
|
+
|
4
|
+
describe Actions::FetchUrls do
|
5
|
+
context '#initialize' do
|
6
|
+
it 'requires a set of options' do
|
7
|
+
proxy = double('HttpProxy')
|
8
|
+
reporter = double('reporter')
|
9
|
+
allow(reporter).to receive(:header)
|
10
|
+
|
11
|
+
options = {
|
12
|
+
proxy: proxy,
|
13
|
+
urls: ['http://localhost:4567/rspec/url_fetcher'],
|
14
|
+
timeout: 2,
|
15
|
+
count: 1,
|
16
|
+
concurrent: false,
|
17
|
+
output: StringIO.new,
|
18
|
+
reporter: reporter,
|
19
|
+
}
|
20
|
+
|
21
|
+
expect {
|
22
|
+
Actions::FetchUrls.new(options)
|
23
|
+
}.not_to raise_error
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
context '#run' do
|
28
|
+
it 'fetchs urls' do
|
29
|
+
proxy = double('HttpProxy')
|
30
|
+
allow(proxy).to receive(:to_string).and_return('http://localhost:3128')
|
31
|
+
|
32
|
+
reporter = double('reporter')
|
33
|
+
allow(reporter).to receive(:data)
|
34
|
+
allow(reporter).to receive(:header)
|
35
|
+
|
36
|
+
options = {
|
37
|
+
proxy: proxy,
|
38
|
+
urls: ['http://example.org'],
|
39
|
+
timeout: 2,
|
40
|
+
count: 2,
|
41
|
+
output: StringIO.new,
|
42
|
+
concurrent: false,
|
43
|
+
reporter: reporter,
|
44
|
+
}
|
45
|
+
|
46
|
+
fetcher = Actions::FetchUrls.new(options)
|
47
|
+
silence :stderr do
|
48
|
+
fetcher.run
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
data/spec/capybara_proxy_spec.rb
CHANGED
@@ -61,7 +61,7 @@ describe CapybaraProxy do
|
|
61
61
|
proxy.port = 3128
|
62
62
|
|
63
63
|
proxy.user = double('user')
|
64
|
-
allow(proxy.user).to receive(:to_string).and_return('user:password')
|
64
|
+
allow(proxy.user).to receive(:to_string).with(cleartext: true).and_return('user:password')
|
65
65
|
|
66
66
|
expect(proxy.as_phantomjs_arguments).to eq(
|
67
67
|
[
|
data/spec/git_repository_spec.rb
CHANGED
@@ -107,5 +107,27 @@ describe GitRepository do
|
|
107
107
|
|
108
108
|
expect(Rugged::Repository.new(clone_path).bare?).to be true
|
109
109
|
end
|
110
|
+
|
111
|
+
it 'raises error if repository does not exist' do
|
112
|
+
expect {
|
113
|
+
GitRepository.clone('asdf', 'asdf1')
|
114
|
+
}.to raise_error Exceptions::RepositoryDoesNotExist
|
115
|
+
end
|
116
|
+
|
117
|
+
it 'raises error if repository does not exist' do
|
118
|
+
expect {
|
119
|
+
GitRepository.clone('asdf.git', 'asdf1')
|
120
|
+
}.to raise_error Exceptions::RepositoryDoesNotExist
|
121
|
+
end
|
122
|
+
|
123
|
+
it 'raises error if repository is not a supported vcs repository' do
|
124
|
+
create_directory('invalid_repo')
|
125
|
+
|
126
|
+
expect {
|
127
|
+
in_working_directory do
|
128
|
+
GitRepository.clone('invalid_repo', 'asdf1')
|
129
|
+
end
|
130
|
+
}.to raise_error Exceptions::RepositoryInvalid
|
131
|
+
end
|
110
132
|
end
|
111
133
|
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require 'spec_helper'
|
3
|
+
|
4
|
+
describe HttpProxy do
|
5
|
+
context '#initialize' do
|
6
|
+
it 'requires a connection string' do
|
7
|
+
expect {
|
8
|
+
HttpProxy.new('localhost:8080')
|
9
|
+
}.not_to raise_error
|
10
|
+
end
|
11
|
+
|
12
|
+
it 'fails on invalid connection string' do
|
13
|
+
expect {
|
14
|
+
HttpProxy.new('gargabe:asdf')
|
15
|
+
}.to raise_error Exceptions::ProxyConnectionStringInvalid
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
context '#to_string' do
|
20
|
+
it 'generates a string' do
|
21
|
+
proxy = HttpProxy.new('localhost:8080')
|
22
|
+
expect(proxy.to_string).to eq('http://localhost:8080')
|
23
|
+
end
|
24
|
+
|
25
|
+
it 'uses a user and output no password' do
|
26
|
+
user = double('ProxyUser')
|
27
|
+
allow(user).to receive(:name).and_return('user')
|
28
|
+
expect(user).not_to receive(:password)
|
29
|
+
|
30
|
+
proxy = HttpProxy.new('localhost:8080')
|
31
|
+
proxy.use_user user
|
32
|
+
|
33
|
+
expect(proxy.to_string).to eq('http://user:****@localhost:8080')
|
34
|
+
end
|
35
|
+
|
36
|
+
it 'uses a user and output password on request' do
|
37
|
+
user = double('ProxyUser')
|
38
|
+
allow(user).to receive(:name).and_return('user')
|
39
|
+
allow(user).to receive(:password).and_return('password')
|
40
|
+
|
41
|
+
proxy = HttpProxy.new('localhost:8080')
|
42
|
+
proxy.use_user user
|
43
|
+
|
44
|
+
expect(proxy.to_string(cleartext: true)).to eq('http://user:password@localhost:8080')
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|