Библиотека для загрязнения и установки ожиданий на HTTP -запросах в Ruby.
Застревание HTTP -запросов на LIB LIB LIB LOW HTTP (не нужно изменять тесты при изменении библиотеки HTTP)
Установка и проверка ожиданий на HTTP -запросах
Соответствующие запросы на основе метода, URI, заголовков и тела
Умное сопоставление одного и того же URI в разных представлениях (также кодированных и некодированных формах)
Умное сопоставление одних и тех же заголовков в разных представлениях.
Поддержка Test :: Unit
Поддержка RSPEC
Поддержка министров
Async :: http :: client
Обочиной (в настоящее время только бордюр :: Easy)
EM-HTTP-Request
Эшон
Httpclient
Http Gem (также известный как http.rb)
httpx
Мантинор
Net :: http и другие библиотеки на основе net :: http, например:
Httparty
Отдых клиент
Покровитель
Typhoeus (в настоящее время только Typhoeus :: hydra)
МРТ 2.6
МРТ 2.7
МРТ 3.0
МРТ 3.1
МРТ 3.2
МРТ 3.3
Jruby
Gem установить WebMock
или альтернативно:
# Добавить в свой GemfileGroup: тест do Gem "WebMock" End
git clone http://github.com/bblimke/webmock.gitcd webmock Установка граблей
WebMock 2.x несколько изменился с версии 1.x. Изменения перечислены в Changelog.md
Создайте features/support/webmock.rb
со следующим содержанием:
требуется 'webmock/cucumber'
Добавьте следующий код в test/test_helper
:
Требовать 'webmock/minitest'
Добавьте следующий код в spec/spec_helper
:
требуется 'webmock/rspec'
Добавьте следующий код для test/test_helper.rb
требуется 'webmock/test_unit'
Вы также можете использовать WebMock за пределами тестовой структуры:
Требовать 'webmock'include webmock :: apiwebmock.enable!
stub_request (: any, "www.example.com") net :: http.get ("www.example.com", "/") # ===> Успех
stub_request (: post, "www.example.com"). с (Body: "ABC", заголовки: {'content-length' => 3}) uri = uri.parse ("http://www.example.com/") req = net :: http :: post. new (uri.path) req ['' content-guide '] = 3res = net :: http.start (uri.host, uri.port) do | http | http.request (req, "abc") end # ===> Успех
stub_request (: post, "www.example.com"). с (body:/world $/, заголовки: {"content-type" =>/image/.+/}). to_return (Body: "abc") uri = uri.parse ('http://www.example.com/') req = net :: http :: post.new (uri.path) req ['content-type' ] = 'Image/png'res = net :: http.start (uri.host, uri.port) do | http | http.request (req, 'hello world') end # ===> Успех
stub_request (: post, "www.example.com"). с (body: {data: {a: '1', b: 'five'}}) restclient.post ('www.example.com', "data [a] = 1 & data [b] = пять", content_type: 'application/xwww-form-urlencoded') # ===> successRestclient.post ('www.example.com', '{"data": {"a": "1", "b": "пять"}}', content_type: 'application /json') # ===> successRestClient.post ('www.example.com', '<data a = "1" b = "пять" />', content_type: 'application/xml') # ===> Успех
stub_request (: post, "www.example.com"). с (body: hash_including ({data: {a: '1', b: 'five'}})) restclient.post ('www.example.com', "data [a] = 1 & data [b] = пять & x = 1 ",: content_type => 'application/x-www-form-urlencoded') # ===> Успех
stub_request (: any, "www.example.com"). с (заголовки: {'header-name' => 'header-value'}) uri = uri.parse ('http://www.example.com/') req = net :: http :: opt.new ( uri.path) req ['header-name'] = 'header-value'res = net :: http.start (uri.host, uri.port) do | http | http.request (req, 'abc') end # ===> Успех
stub_request (: get, 'www.example.com'). с (заголовки: {'Accept' => ['image/jpeg', 'image/png']}) req = net :: http :: get.new ("/") req ['accept'] = ['' Image/png '] req.add_field (' Accept ',' image/jpeg ') net :: http.start ("www.example.com") {| http | http.request (req)} # ===> Успех
stub_request (: post, "www.example.com"). С {| запрос | request.body == "abc"} restclient.post ('www.example.com', 'abc') # ===> Успех
stub_request (: get, "www.example.com"). с (basic_auth: ['user', 'pass'])# или# stub_request (: get, "www.example.com").# с (заголовки: {'Authorization' => "basic #{base64.strict_encode64 ('user: pass'). Chomp}"}) net :: http.start ('www.example.com') do | http | req = net :: http :: get.new ('/') req.basic_auth 'user', 'pass' http.request (req) end # ===> Успех
stub_request(:get, "user:[email protected]")
не соответствует запросу с учетными данными, представленными в заголовке авторизации.stub_request (: get, "user: [email protected]") restclient.get ('user: [email protected]') # ===> Успех
stub_request (: any,/example/)net::http.get('www.example.com ','/') # ===> Успех
stub_request (: any, -> (uri) {true})
uri_template = addressable :: template.new "www.example.com/beers/"stub_request(: line, uri_template) net :: http.get ('www.example.com', '/webmock/') # = = ==> Успех
uri_template = Addressable :: template.new "www.example.com/thing/{ whid ).json <?x,y,ZE Пример.com ', '/Thing/5.json?x=1&y=2&z=3&anyparam=4') # ===> Успех
stub_request (: get, "www.example.com"). С (Query: {"a" => ["b", "c"]}) restclient.get ("http://www.example.com// ? a [] = b & a [] = c ") # ===> Успех
stub_request (: get, "www.example.com"). с (query: hash_including ({"a" => ["b", "c"]})) restclient.get ("http://www.example.com/?a®=b&a®=c&x= 1 ") # ===> Успех
stub_request (: get, "www.example.com"). с (Query: hash_excluding ({"a" => "b"})) restclient.get ("http://www.example.com/?a=b") # ===> failurerestclient.get ("http : //www.example.com/? a = c ") # ===> Успех
stub_request (: any, "www.example.com"). to_return (Body: "ABC", Статус: 200, заголовки: {'content-length' => 3}) net :: http.get ("www.example.com", '/') # ===> " ABC "
Установите соответствующий тип контента для httparty's parsed_response
.
Stub_Request (: any, "www.example.com"). TO_Return Body: '{}', заголовки: {content_type: 'Application/json'}
File.open ('/tmp/response_body.txt', 'w') {| f | f.puts 'abc'} stub_request (: any, "www.example.com"). to_return (body: file.new ('/tmp/response_body.txt'), status: 200) net :: http.get ('www.example.com', '/') # ===> "abcn"
stub_request (: any, "www.example.com"). to_return_json (body: {foo: "bar"}) net :: http.get ('www.example.com', '/') # ===> "{" foo ":" bar "}"
stub_request (: any, "www.example.com"). to_return (Состояние: [500, "Ошибка внутреннего сервера"]) req = net :: http :: get.new ("/") net :: http.start ("www.example.com") {| http | http.request (req)}. Сообщение # ===> «Ошибка внутреннего сервера»
curl -is
curl -is www.example.com > /tmp/example_curl_-is_output.txt
raw_response_file = file.new ("/tmp/example_curl_-is_output.txt")
из файла
stub_request (: get, "www.example.com"). to_return (raw_response_file)
или строка
stub_request (: get, "www.example.com"). TO_Return (raw_response_file.read)
stub_request (: any, 'www.example.net'). to_return {| Запрос | {body: request.body}} restclient.post ('www.example.net', 'abc') # ===> "abcn"
stub_request (: any, 'www.example.net'). to_return (lambda {| запрос | {body: request.body}}) restclient.post ('www.example.net', 'abc') # ===> "abcn"
curl -is
curl -is www.example.com > /tmp/www.example.com.txt
stub_request (: get, "www.example.com"). to_return (lambda {| request | file.new ("/tmp/#{request.uri.host.to_s} .txt")})
stub_request (: any, 'www.example.net'). to_return (body: lambda {| запрос | request.body}) restclient.post ('www.example.net', 'abc') # ===> "abcn"
класс myrackapp def self.call (env) [200, {}, ["hello"]]] endendStub_request (: get, "www.example.com"). to_rack (myrackapp) restclient.post ('www.example.com') # ===> "Привет"
stub_request (: any, 'www.example.net'). to_raise (standarderror) restclient.post ('www.example.net', 'abc') # ===> standarderror
stub_request (: any, 'www.example.net'). to_raise (standarderror.new ("Некоторая ошибка"))))
stub_request (: any, 'www.example.net'). to_raise ("Некоторая ошибка")
stub_request (: any, 'www.example.net'). to_timeoutrestclient.post ('www.example.net', 'abc') # ===> restClient :: requestTimeout
stub_request (: get, "www.example.com"). to_return ({body: "abc"}, {body: "def"}) net :: http.get ('www.example.com', '/') # ===> "abcn" net :: http. get ('www.example.com', '/') # ===> "defn" #after. /') # ===> "defn"
to_return()
, to_raise()
или to_timeout
объявленияstub_request (: get, "www.example.com"). to_return ({body: "abc"}). Затем. #Then () - просто синтаксический сахар to_return ({body: "def"}). Затем. to_raise (myexception) net :: http.get ('www.example.com', '/') # ===> "abcn" net :: http.get ('www.example.com', '/') # ===> "defn" net :: http.get ('www.example.com', '/') # ===> MyException поднято
stub_request (: get, "www.example.com"). to_return ({body: "abc"}). times (2) .then. to_return ({body: "def"}) net :: http.get ('www.example.com', '/') # ===> "abcn" net :: http.get ('www.example.com ','/') # ===> "abcn" net :: http.get (' www.example.com ','/') # ===> "defn"
stub_get = stub_request (: get, "www.example.com") remove_request_stub (stub_get)
Webmock.ally_net_connect! Stub_request (: any, "www.example.com"). To_return (body: "abc") net :: http.get ('www.example.com', '/') # ===> "abc" net :: http.get ('www.something.com', '/') # ===> /.+something.+/webmock.disable_net_connect com ','/') # ===> Неудача
Webmock.disable_net_connect! (Allocalhost: true) net :: http.get ('www.something.com', '/') # ===> failurenet :: http.get ('localhost: 9887', '/') # ===> разрешен. Может, селену?
Разрешенные запросы могут быть указаны несколькими способами.
С помощью String
указанной имени хоста:
Webmock.disable_net_connect! (Разрешить: 'www.example.org') restclient.get ('www.something.com', '/') # ===> failurerestclient.get ('www.example.org', '/ ') # ===> outdrestClient.get (' www.example.org:8080 ','/') # ===>
С помощью String
указанной имени хоста и порта:
Webmock.disable_net_connect! (Разрешить: 'www.example.org:8080')restclient.get(''www.something.com', '/') # ===> failurerestclient.get ('www.example.org', '/') # ===> failurerStestClient.get ('www.example.org:8080', '/') # ===> разрешен
С Regexp
соответствующей URI:
Webmock.disable_net_connect! (Allow: %r {Ample.org/foo}) restclient.get ('www.example.org', '/foo/bar') # ===> AldRestClient.get ('sample.org' , '/foo') # ===> outdrestClient.get ('sample.org', '/bar') # ===> Отказ
С объектом, который отвечает на #call
, получая объект URI
и возвращая логическое:
denylist = ['google.com', 'facebook.com', 'apple.com'] Alth_sites = lambda {| uri | denylist.none? {| Сайт | uri.host.include? (site)}} webmock.disable_net_connect! (Alling: Alling_sites) restClient.get ('www.example.org', '/') # ===> AldRestClient.get ('www.facebook. com ','/') # ===> failurerStestClient.get (' Apple.com ','/') # ===> Отказ
С Array
любого из вышеперечисленного:
Webmock.disable_net_connect! (Разрешить: [ Lambda {| Uri | uri.host.length % 2 == 0}, /Пример.org/, 'bbc.co.uk',]) restclient.get ('www.example.org', '/') # ===> outdrestclient.get ('bbc.co.uk', '/') # == => AldRestClient.get ('bbc.com', '/') # ===> outdrestClient.get ('www.bbc.com', '/') # ===> Отказ
Протокол HTTP имеет 3 шага: подключение, запрос и ответ (или 4 с закрытием). Большинство клиентских библиотек Ruby HTTP рассматривают Connect как часть шага запроса, за исключением Net::HTTP
, который позволяет открывать подключение к серверу отдельно с запросом, используя Net::HTTP.start
.
WebMock API также была разработана с помощью Connect, являющейся частью шага запроса, и это позволяет только загрязнять запросы, а не подключения. Когда называется Net::HTTP.start
, WebMock еще не знает, загрязнен ли запрос или нет. WebMock по умолчанию задерживает подключение до тех пор, пока запрос не будет обращен, поэтому, когда нет запроса, Net::HTTP.start
ничего не делает. Это означает, что WebMock по умолчанию ломает поведение Net :: HTTP!
Для обхода в эту проблему предлагается WebMock :net_http_connect_on_start
опция, которая может быть передана в WebMock.allow_net_connect!
и WebMock.disable_net_connect!
Методы, т.е.
Webmock.allay_net_connect! (Net_http_connect_on_start: true)
Это заставляет WebMock Net :: HTTP -адаптер всегда подключаться к Net::HTTP.start
. На момент создания соединения пока нет информации о запросе или URL, поэтому WebMock не может решить, стоит ли загнать запрос или нет, и все соединения разрешены. Для включения подключений только к определенному домену (например, ваш тестовый сервер) Использование:
Webmock.allay_net_connect! (Net_http_connect_on_start: "www.example.com")
Требовать 'webmock/test_unit'stub_request (: any, "www.example.com") uri = uri.parse (' http://www.example.com/ ') req = net :: http :: op.new ( uri.path) req ['' content-length '] = 3res = net :: http.start (uri.host, uri.port) do | http | http.request (req, 'abc') endassert_request: post, "http://www.example.com", Заголовки: {'content-kindy' => 3}, body: "abc", Время: 1 # ===> SucksAssert_not_requested: get, "http://www.something.com" # ===> ucksAssert_request (: post "http://www.example.com", раз: 1) {| req | req.body == "ABC"}
Webmock.allow_net_connect! Net :: http.get ('www.example.com', '/') # ===> ucksAssert_request: get, "http://www.example.com" # ===> Успех
stub_get = stub_request (: get, "www.example.com") stub_post = stub_request (: post, "www.example.com") net :: http.get ('www.example.com', '/') assert_requested (stub_get) assert_not_requested (stub_post)
WebMock
Этот стиль позаимствован у Факеве-матчера
требуется 'webmock/rspec'expect (webmock). с (body: "abc", заголовки: {'content-length' => 3}). DablyExpect (webMock) .not_to hak_requested (: get, "www.something.com"). Ожидайте (webmock). Опубликуйте, "www.example.com"). с {| req | req.body == "abc"}# Обратите внимание, что блок с `do ... end` вместо кудрявых кронштейнов не будет работать!# Почему? Смотрите этот комментарий https://github.com/bblimke/webmock/issues/174#issuecomment-34908908expect(webmock).to hake_request (: get, "www.example.com"). с (Query: {"a" => ["b", "c"]}) ожидайте (webmock) .to hak_request (: get, "www.example.com"). с (Query: hash_including ({"a" => ["b", "c"]})) ожидайте (webmock) .to hak_request (: get, "www.example.com"). с (body: {"a" => ["b", "c"]}, заголовки: {'content-type' => 'application/json'})
a_request
Ожидайте (a_request (: post, "www.example.com"). с (body: "abc", заголовки: {'content-guide' => 3})). haf_been_made.onceexpect (a_request (: post, "www.something.com")). habe_been_made.times (3) ждать (a_request (: post, www.something.com ")). (: post, "www.something.com")). haf_been_made.at_least_times (3) way (a_request (: post, "www.something.com")). ) Ожидайте (a_Request (: any, "www.example.com")). not_to haf_been_madeexpect (a_request (: post, "www.example.com"). С {| req | req.body == "abc"}) Полем haf_been_madeexpect (a_request (: get, "www.example.com"). С (Query: {"a" => ["b", "c"]})). HASE_BEEN_MADEEXPECT (a_request (: get, "www.example.com"). с (query: hash_including ({"a" => ["b", "c"]}))). Hak_been_madeexpect (a_request (: post, "www.example.com"). с (body: {"a" => ["b", "c"]}, заголовки: {'content-type' => 'application/json'})). haf_been_made
stub = stub_request (: get, "www.example.com")# ... сделайте запросы ... ожидайте (stub).
Если вы хотите сбросить все текущие заглушки и историю запросов, используйте WebMock.reset!
stub_request (: any, "www.example.com") net :: http.get ('www.example.com', '/') # ===> uscebmock.reset! net :: http.get ('www .example.com ','/') # ===> failureAressert_not_request: get, "www.example.com" # ===> Успех
Если вы хотите сбросить только счетчики выполненных запросов, используйте WebMock.reset_executed_requests!
Stub = stub_Request (: get, "www.example.com") stub2 = stub_request (: get, "www.example2.com") net :: http.get ('www.example.com', '/') net :: http.get ('www.example.com', '/')net::http.get('www.example2.com', '/'') expect(stub).t (stub2) .to haf_been_request.times (1) webmock.reset_executed_requests! ожидается (stub) .not_to haf_been_requestexpect (stub2) .not_to hak_been_requested
# Отключить WebMock (все адаптеры) webmock.disable!# Отключить WebMock для всех LIBS, кроме NET :: httpwebmock.disable! (Кроме: [: net_http])# включить webmock (все адаптеры) webmock.enable! кроме Patronwebmock.enable! (кроме: [: patron])
Выполненный запрос соответствует загрязненному запросу, если он проходит по критериям:
Когда запрос URI соответствует загрязнению строки URI, шаблона regexp или шаблона URI RFC 6570
И метод запроса такой же, как и загрязненный метод запроса или загрязненный метод запроса: любой
И корпус запроса такой же, как и загрязненный корпус запроса или загрязненный корпус запроса не указан
И заголовки запросов, загрязненные заголовки запросов, или загрязненные заголовки запросов соответствуют подмножеству заголовков запросов, или загрязненные заголовки запросов не указаны
И совпадения запроса, предоставленные блоки или блокировки, не предоставлены
Всегда будет применен последний объявленный заглушка. Запрос будет применен, т.е.
Stub_Request (: get, "www.example.com"). TO_Return (Body: "ABC") Stub_Request (: get, "www.example.com"). TO_Return (Body: "def") net :: http.get ('www.example.com', '/') # ====> "def"
WebMock будет соответствовать всем различным представлениям одного и того же URI.
Т.е. все следующие представления URI равны:
"www.example.com" "www.example.com/" "www.example.com:80" "www.example.com:80/" "http://www.example.com" "http: // www.example.com/"http://www.example.com:80"http://www.example.com:80/ ""
Следующие URI с пользователем также равны для WebMock
"A B: [email protected]" "a b: [email protected]/" "a b: [email protected]: 80" "a b: [email protected]: 80/" "http: // a b: [email protected]" "http: // a b: [email protected]/" "http: // a b: [email protected]: 80" "http : // a b: [email protected]: 80/"" A%20b: [email protected] "" A%20b: [email protected]/"" A%20b: Pass@ www.example.com:80""t%20b:[email protected]:80/"http://a%20b:[email protected]""http://a%20B: [email protected]/ "" http: // a%20b: [email protected]: 80 "" http: // a%20b: [email protected]: 80/"
или это
"www.example.com/my path/? a = my param & b = c" "www.example.com/my%20path/?a=my%20param&b=c" "www.example.com:80/my path/ ? a = my param & b = c "" www.example.com:80/my%20path/?a=my%20param&b=c "" http://www.example.com/my path/? a = my param & b = b = b = b = b = b = b = b = b = b = b = b = b = b = b = b C "" http://www.example.com/my%20path/?a=my%20Param&b=c "" http://www.example.com:80/my path/? a = my param & b = c " "http://www.example.com:80/my%20path/?a=my%20param&b=c"
Если вы предоставите Regexp для соответствия URI, WebMock попытается сопоставить его с каждой действительной формой одного и того же URL.
Т.е. /my path/
будет соответствовать www.example.com/my%20path
, потому что он эквивалентен www.example.com/my path
Если вы используете Addersable :: Template для сопоставления, то WebMock отложит правила сопоставления с адресами, которые соответствуют RFC 6570.
Если вы используете какой -либо из методов WebMock для сопоставления параметров запросов, то адресуемые будут использоваться для соответствия базовому URI, а WebMock будет соответствовать параметрам запросов. Если вы этого не сделаете, то WebMock позволит Addersable соответствовать полному URI.
WebMock будет соответствовать заголовкам запросов против загрязненных заголовков запросов в следующих ситуациях:
Загрязненный запрос указан, и заголовки запроса такие же, как и загрязненные заголовки
{ 'Header1' => 'Value1', 'Header2' => 'Value2' }
{ 'Header1' => 'Value1', 'Header2' => 'Value2' }
Загрязненный запрос имеет указанные заголовки, а загрязненные заголовки запросов являются подмножеством заголовков запроса
{ 'Header1' => 'Value1' }
{ 'Header1' => 'Value1', 'Header2' => 'Value2' }
Заправленный запрос не имеет заголовков
nil
{ 'Header1' => 'Value1', 'Header2' => 'Value2' }
WebMock нормализует заголовки и обработки всех форм одинаковых заголовков, что и равные: т.е. Следующие два набора заголовков равны:
{ "Header1" => "value1", content_length: 123, X_CuStOm_hEAder: :value }
{ header1: "value1", "Content-Length" => 123, "x-cuSTOM-HeAder" => "value" }
Чтобы записать реальные HTTP -взаимодействия вашего приложения и воспроизвести их позже в тестах, вы можете использовать видеомагнитофон с WebMock.
Webmock.after_request do | request_signature, ответ | был сделан «запрос #{request_signature}, и #{ответ} был возвращен» End
Webmock.after_request (кроме: [: patron], Real_requests_only: true) do | req_signature, ответ | был сделан «Запрос #{req_signature}, и #{ответ} был возвращен» End
Пожалуйста, отправьте их здесь http://github.com/bblimke/webmock/issues
Вы можете внести свой вклад, выделив проблемы, которые могут включать воспроизведение отчетов об ошибках или запрашивать жизненно важную информацию, такую как номера версий или инструкции по воспроизведению. Если вы хотите начать решать проблемы, один простой способ начать - подписаться на WebMock на кодетерс.
Если у вас есть какие-либо предложения о том, как улучшить WebMock, отправьте электронное письмо в список рассылки Groups.google.com/group/webmock-users
Меня особенно интересует, как DSL можно улучшить.
Чтобы работать над WebMock, вам сначала нужно расколоть и клонировать репо. Пожалуйста, сделайте любую работу над выделенным филиалом и повторно против Мастера, прежде чем отправлять запрос на привлечение.
Первоначальные строки этого проекта были написаны во время New Bamboo Hack Day благодаря моему коллегу Bambinos за все замечательные предложения!
Люди, которые представили патчи и новые функции или предложенные улучшения. Большое спасибо этим людям:
Бен Пилот
Марк Эванс
Иван Вега
Piotr Usewicz
Ник Плант
Ник Кэванто
Diego E. "Flameeyes" pettenò
Нильс Меершшерт
Мак Эрнхардт
Арвикко
Серхио Гил
Джеффри Джонс
Текин Сулиман
Том Уорд
Надим Битар
Мирон Марстон
Сэм Филлипс
Хосе Ангел Кортинас
Разич
Стив Тук
Натаниэль Библер
Мартин Лафран
Манесс Алрубаи
Чарльз Ли
Райан Бигг
Пит Хиггинс
Ганс де Граафф
Аластер Брунтон
Сэм Стоукс
Юджин Болшаков
Джеймс Конрой-Финн
Сальвадор Фуэнтес -младший
Алекс Ротенберг
Эйдан Фельдман
Стив Халл
Джей Адкиссон
Зак Деннис
Никита Федьяшев
Лин Джен-Шин
Дэвид Йу
Андреас Гарнс
Роман Штерензон
Крис МакГрат
Стивен Селис
Юджин Пименов
Альберт Ллоп
Кристофер Пикет
Таммер Салех
Николас Фуше
Джо Ван Дайк
Марк Абрамов
Фрэнк Шумахер
ДИМИТРИ ДЕНИССЕНКО
Марнен Лайбоу-Козер
Evgeniy Dolzhenko
Ник Recobra
Джордан Элвер
Джо Караюсуф
Пол Кортенс
Югё
аиндустриции
Эрик Ээстрих
Эрванлр
Бен Блейтинг
Джон Лейтон
Райан Шлезингер
Жюльен Бойер
Кевин Гловач
Ганс Хассельберг
Эндрю Франция
Джонатан Хайман
Рекс Фэн
Павел Форкерт
Jordi Massaguer PLA
Джейк Бенилов
Том Бове
Мокевнин Кирилл
Алекс Грант
Лукас Доммен
Бастиен Ваухер
JOOST BAAIJ
Джоэл Чиппиндейл
Мурахаши Санемат Кеничи
Тим Курверс
Илья Вассилевский
Готвальт
Лейф Бладт
Алекс Томлинс
Mitsutaka Mimura
Томи Кайра
Даниэль Ван Хозель
Ян Асафф
Ян Лесперанс
Мэтью Хоран
Дмитрий Гутов
Флориан Дюш
Мануэль Мейрер
Брайан Д. Бернс
Райли Стронг
Тамир Дуберштейн
Стефано Улиари
Алекс Ступаков
Карен Ван
Мэтт Берк
Джон Роу
Алекси В. Запаров
Правин Аримбратодиил
Бо Динес
Мэтью Конвей
Роб Олсон
Макс Линкольн
Олег Гритсенко
Хван-Джун Чой
Шибата Хироши
Калеб Томпсон
Тео Халберг
Пабло Джайрала
Insoo Buzz Jung
Карлос Алонсо Перес
Трлорз
Александр Симонов
Торбьерн Германсе
Марк Лоренц
Tjsousa
Тасос Статопулос
Дэн Бюеттнер
Свен Ридель
Марк Лоренц
Dávid Kovács
Fishermand46
Фрэнки Валь
Чоюн
Саймон Рассел
Стив Митчелл
Маттиас Путман
Захари Анкер
Эммануэль Самбо
Рамон Таяг
Йоханнес Шлумбергер
Siôn le Roux
Мэтт Палмер
Чжао Вэнь
Krzysztof rygielski
Magne Land
Юривм
Майк Кнеппер
Чарльз Пенс
Алексей Запаров
Пабло Брасеро
Седрик Пимента
Михиэль Карнебек
Алекс Кестнер
Манфред Стиенстра
Тим Диггинс
Габриэль Чейни
Крис Григо
Тайки Оно
Джонатан Шац
Хосе Луис Гонорто
Аарон Кромер
Павел Юрашек
Джейк стоит
Гейб Мартин-Демпеси
Майкл Гроссер
Алексей Маридашвили
Вилль Лаутанала
Коичи Ито
Джордан Харбанд
Tarmo Tänav
Джо Марти
Крис Томсон
Vít ondruch
Джордж Ульмер
Кристоф Кениг
Чунг-Йи Чи
Olexandr Hoshylyk
Джанко Мароньич
Пэт Аллан
Рик Сонг
Нарузе, Юи
ПИОТР БОНИЕКИ
Олиа Креммида
Михал Матьяс
Мэтт Бриктсон
Кенни Ортманн
Redbar0n
Лукас Поконни
Аркадий Тетельман
Казато Сугимото
Олле Джонссон
Павел Розицки
ГЕРЕМИЯ ТАГЛИАЛАТЕЛА
Коичи Сасада
Юсуке Эндох
Серый пекарь
СКОРОКХЕН ООГОНГ
Павел Валена
Адам Соколника
Джефф Фелхнер
Эйк отправить
Клаудио Поли
CSABA APAGYI
Фредерик Чеунг
Фабио Д. Батиста
Андрия Янко
y-yagi
Рафаэль Франса
Джордж Клэгхорн
Алекс Джунжер
Ориен Мэдвик
Андрей Сидоров
Марко Коста
Райан Дэвис
Брандур
Сэмюэль Уильямс
Патрик Рагнарссон
Алекс Куманс
Веса Лааксо
Джон Хоторн
Guppy0356
Тило Руше
Эндрю Стунтц
Лукас Уезу
Бруно Сутик
Райан Керр
Адам Харвуд
Бен Коши
Джесси Боуэс
Марек Каштелник
CE07C3
Джун Цзян
Олексии Ковирин
Мэтт Ларрас
Тони Шнайдер
Никлас Хёс
Джоанна Хартманн
Алекс Вондрак
Будет составить
Эдуардо Эрнандес
ojab
Джорджио Гамбино
Тиммимитрия
Майкл Фэрли
Рэй Зейн
Go Sueyoshi
Седрик Сохрауэр
Акира Мацуда
Марк Спанглер
Хенрик Них
Йоанн Лекуйер
Лукас Арно
Марк Рохлофф
Inkstak
Юки Иноуэ
Брэндон Уивер
Джош Николс
Рикардо Триндада
Мрака
Джеймс Браун
Казухиро Нишияма
Этиенн Барри
Мэтт Браун
Виктор Маслов
Gio Lodi
Райан Брукс
Джейкоб Фраутски
Кристиан Шмидт
Родриго Аргумедо
Для полного списка участников вы можете посетить страницу участников.
Спасибо, FakeWeb! Эта библиотека была вдохновлена FakeWeb. Я импортировал некоторые решения из этого проекта в WebMock. Я также скопировал код, т.е. net: http -адаптер. К сожалению, архитектура FakeWeb не позволила мне легко расширить ее с помощью необходимых мне функций. Я также предпочел некоторые вещи, чтобы работать по -другому, то есть запрашивая приоритет.
Copyright (C) 2009-2010 Bartosz Blimke. Смотрите лицензию для деталей.