diff -Nru ruby-excon-0.33.0/changelog.txt ruby-excon-0.45.1/changelog.txt --- ruby-excon-0.33.0/changelog.txt 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/changelog.txt 2015-04-10 16:36:11.000000000 +0000 @@ -1,3 +1,181 @@ +0.45.1 03/27/2015 +================= + +fix scope for readline buffer, fixes dropped initial characters + +0.45.0 03/26/2015 +================= + +prefer default SSL config to ENV, when available +document instrumentor deviation from rails format +better error/warning around openssl 1.0.2 bug +fix nonblocking ssl connect to not have tight loop +also remove user/pass when following redirects + +0.44.4 03/04/2015 +================= + +update bundled certs +loosen travis versions, to get ~> type follow-the-leader behavior +fix syntax issue in ruby 2.2.1 + +0.44.3 02/24/2015 +================= + +don't pass body when following GET redirects +fix error rescue case to properly reference error object + +0.44.2 02/11/2015 +================= + +simplify data[:debug] logic +catch nonblock errors around readline + + +0.44.1 02/01/2015 +================= + +fix issue with frozen strings in user/pass + +0.44.0 01/30/2015 +================= + +re-implement timeout using IO.select +document custom URI parser usage +fix ruby 2.2 build +improved IPv6 support +Excon::Utils improvements +add 429 errors + +0.43.0 01/09/2015 +================= + +use basic error instead of nil as default for socket error +allow setup_proxy to accept uri +add disable_proxy and proxy: false to disable proxy settings + +0.42.1 12/04/2014 +================= + +update bundled certs +fix redirect follower to avoid erroneously setting basic auth + +0.42.0 12/02/2014 +================= + +fix stubbing section of README +follow redirect for all request methods +remove unhelpful link for excon.io +rescue/ignore illegal seek on rewind +add ssl_cert_store option +allow non-RSA ssl keys +attempt to rewind request_block when idempotent +add configurable thread safety for socket pool + + +0.41.0 11/05/2014 +================= + +add :ssl_verify_peer_host option for dev purposes +add #reason_phrase to response + +0.40.0 10/06/2014 +================= + +fix support for specifying ssl_ca_path +more consistent response_block/response.body behavior for mocks +add support for proxies running on unix domain sockets + +0.39.6 09/22/2014 +================= + +pretty print stub not found errors + +0.39.5 09/14/2014 +================= + +fix double delegation error +make client_key_pass valid connection key +cast headers to_s to fix historical symbol usage + +0.39.4 08/08/2014 +================= + +ensure Response#new uses case-insensitive headers +add client cert pass phrase support + +0.39.3 08/05/2014 +================= + +fix for nil and/or unknown proxy values + +0.39.2 08/04/2014 +================= + +respect both ca_file/ca_path when both present + +0.39.1 08/04/2014 +================= + +fix for ssl proxies + remote_ip stuff + +0.39.0 08/01/2014 +================= + +revert to a blocking readline, for performance +simplify status lookup +consolidate proxy code +store defaults as a constant +avoid setting nil user/pass vs just no setting keys +move idempotent warnings in to middleware +simplify validations +use constants in utils +group non-chunk response paring +optimize/simplify socket local lookup +simplify to pro-actively build downcased headers instead of lazily do so +add version to options (so it will appear in debug) +add OS/Ruby version info to options/version for debugging +more consistent output styling for errors +remove TE stuff to simplify +shorten timeout/sleep in streaming tests +remove transfer-encoding altogether if it only includes chunked +only rescue http status errors in relevant tests +use case-insensitive headers in stubs also + +0.38.0 07/09/2014 +================= + +avoid reading non-file bodies (mock related fix) +fixes to readme links +fix excon_debug to set debug_response +ensure both \r and \n are read when parsing headers + +0.37.0 06/09/2014 +================= + +fix chunked reading to avoid chop! on non-chunk endings +fixes for proxy usage + +0.36.0 06/04/2014 +================= + +fix to reconcile streaming changes for chunked encoding + +0.35.0 06/03/2014 +================= + +fix for responses with content_length + +0.34.0 05/29/2014 +================= + +add support for setting ssl_verify_callback +stream partial results imediately, when available +update rack/unicorn in tests to support streaming tests +skip streaming tests on jruby (as they depend on unicorn) +update travis tests to use newest rubinius +improve formatting/readibility of standard instrumentor output + 0.33.0 05/15/2014 ================= Binary files /tmp/3cHms6_ZgF/ruby-excon-0.33.0/checksums.yaml.gz and /tmp/l0UOecm96i/ruby-excon-0.45.1/checksums.yaml.gz differ diff -Nru ruby-excon-0.33.0/CONTRIBUTING.md ruby-excon-0.45.1/CONTRIBUTING.md --- ruby-excon-0.33.0/CONTRIBUTING.md 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/CONTRIBUTING.md 2015-04-10 16:36:11.000000000 +0000 @@ -5,19 +5,19 @@ ### Coding * Pick a task: - * Offer feedback on open [pull requests](https://github.com/geemus/excon/pulls). - * Review open [issues](https://github.com/geemus/excon/issues) for things to help on. - * [Create an issue](https://github.com/geemus/excon/issues/new) to start a discussion on additions or features. + * Offer feedback on open [pull requests](https://github.com/excon/excon/pulls). + * Review open [issues](https://github.com/excon/excon/issues) for things to help on. + * [Create an issue](https://github.com/excon/excon/issues/new) to start a discussion on additions or features. * Fork the project, add your changes and tests to cover them in a topic branch. -* Commit your changes and rebase against `geemus/excon` to ensure everything is up to date. -* [Submit a pull request](https://github.com/geemus/excon/compare/). +* Commit your changes and rebase against `excon/excon` to ensure everything is up to date. +* [Submit a pull request](https://github.com/excon/excon/compare/). ### Non-Coding -* Work for {twitter}[http://twitter.com]? I'd love to reclaim the unused {@excon}[http://twitter.com/excon] account! -* Offer feedback on open [issues](https://github.com/geemus/excon/issues). -* Write and help edit [documentation](https://github.com/geemus/excon.github.com). -* Translate [documentation](https://github.com/geemus/excon.github.com) in to other languages. +* Work for [twitter](http://twitter.com)? I'd love to reclaim the unused [@excon](http://twitter.com/excon) account! +* Offer feedback on open [issues](https://github.com/excon/excon/issues). +* Write and help edit [documentation](https://github.com/excon/excon.github.com). +* Translate [documentation](https://github.com/excon/excon.github.com) in to other languages. * Organize or volunteer at events. * [Donate](https://www.gittip.com/geemus/)! * Discuss other ideas for contribution with [geemus](mailto:geemus+excon@gmail.com). diff -Nru ruby-excon-0.33.0/CONTRIBUTORS.md ruby-excon-0.45.1/CONTRIBUTORS.md --- ruby-excon-0.33.0/CONTRIBUTORS.md 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/CONTRIBUTORS.md 2015-04-10 16:36:11.000000000 +0000 @@ -2,21 +2,27 @@ * Anshul Khandelwal * Ash Wilson * Ben Burkert +* Benedikt Böhm * Bo Jeanes * Brandur * Brian D. Burns * Brian Hartsock * Caio Chassot * Caius Durling +* Carl Hörberg * Carlos Sanchez * Claudio Poli +* Damien Mathieu * Dan Hensgen * Dan Peterson * Dan Prince * Dane Harrigan * Dave Myron * Dave Newton +* David Biehl +* David Biehl * Dimitrij Denissenko +* Dominik Richter * Eugene Howe * Evan Phoenix * Fabian Wiesel @@ -24,19 +30,24 @@ * Glenn Pratt * Graeme Nelson * Hakan Ensari +* Ian Neubert * Jacob Atzen * James Watling * Jeremy Hinegardner +* John Keiser * John Leach * Jonas Pfenniger * Jonathan Dance * Jonathan Dance * Jonathan Roes +* Joshua Gross * Joshua Mckinney * Joshua Napoli * Joshua Napoli +* Kensuke Nagae * Konstantin Shabanov * Kyle Rames +* Lewis Marshall * Lincoln Stoll * Louis Sobel * Mathias Meyer @@ -65,6 +76,7 @@ * Sean Cribbs * Sergio Rubio * Shai Rosenfeld +* Swanand Pagnis * Terry Howe * Thom Mahoney & Josh Lane * Thom May @@ -73,6 +85,7 @@ * Tom Maher * Tom Maher * Trym Skaar +* Tuomas Silen * Viven * Wesley Beary * Wesley Beary @@ -80,6 +93,7 @@ * Wesley Beary * Wesley Beary * chrisrhoden +* dickeyxxx * geemus (Wesley Beary) * geemus * ggoodale diff -Nru ruby-excon-0.33.0/data/cacert.pem ruby-excon-0.45.1/data/cacert.pem --- ruby-excon-0.33.0/data/cacert.pem 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/data/cacert.pem 2015-04-10 16:36:11.000000000 +0000 @@ -1,75 +1,23 @@ ## -## ca-bundle.crt -- Bundle of CA Root Certificates +## Bundle of CA Root Certificates ## -## Certificate data from Mozilla as of: Tue Jan 28 09:38:07 2014 +## Certificate data from Mozilla as of: Wed Feb 25 04:12:04 2015 ## ## This is a bundle of X.509 certificates of public Certificate Authorities ## (CA). These were automatically extracted from Mozilla's root certificates ## file (certdata.txt). This file can be found in the mozilla source tree: -## http://mxr.mozilla.org/mozilla-release/source/security/nss/lib/ckfw/builtins/certdata.txt?raw=1 +## http://hg.mozilla.org/releases/mozilla-release/raw-file/default/security/nss/lib/ckfw/builtins/certdata.txt ## ## It contains the certificates in PEM format and therefore ## can be directly used with curl / libcurl / php_curl, or with ## an Apache+mod_ssl webserver for SSL client authentication. ## Just configure this file as the SSLCACertificateFile. ## +## Conversion done with mk-ca-bundle.pl version 1.25. +## SHA1: f9bc9fa76145720d94124527f82a7185d921975e +## -GTE CyberTrust Global Root -========================== ------BEGIN CERTIFICATE----- -MIICWjCCAcMCAgGlMA0GCSqGSIb3DQEBBAUAMHUxCzAJBgNVBAYTAlVTMRgwFgYDVQQKEw9HVEUg -Q29ycG9yYXRpb24xJzAlBgNVBAsTHkdURSBDeWJlclRydXN0IFNvbHV0aW9ucywgSW5jLjEjMCEG -A1UEAxMaR1RFIEN5YmVyVHJ1c3QgR2xvYmFsIFJvb3QwHhcNOTgwODEzMDAyOTAwWhcNMTgwODEz -MjM1OTAwWjB1MQswCQYDVQQGEwJVUzEYMBYGA1UEChMPR1RFIENvcnBvcmF0aW9uMScwJQYDVQQL -Ex5HVEUgQ3liZXJUcnVzdCBTb2x1dGlvbnMsIEluYy4xIzAhBgNVBAMTGkdURSBDeWJlclRydXN0 -IEdsb2JhbCBSb290MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCVD6C28FCc6HrHiM3dFw4u -sJTQGz0O9pTAipTHBsiQl8i4ZBp6fmw8U+E3KHNgf7KXUwefU/ltWJTSr41tiGeA5u2ylc9yMcql -HHK6XALnZELn+aks1joNrI1CqiQBOeacPwGFVw1Yh0X404Wqk2kmhXBIgD8SFcd5tB8FLztimQID -AQABMA0GCSqGSIb3DQEBBAUAA4GBAG3rGwnpXtlR22ciYaQqPEh346B8pt5zohQDhT37qw4wxYMW -M4ETCJ57NE7fQMh017l93PR2VX2bY1QY6fDq81yx2YtCHrnAlU66+tXifPVoYb+O7AWXX1uw16OF -NMQkpw0PlZPvy5TYnh+dXIVtx6quTx8itc2VrbqnzPmrC3p/ ------END CERTIFICATE----- - -Thawte Server CA -================ ------BEGIN CERTIFICATE----- -MIIDEzCCAnygAwIBAgIBATANBgkqhkiG9w0BAQQFADCBxDELMAkGA1UEBhMCWkExFTATBgNVBAgT -DFdlc3Rlcm4gQ2FwZTESMBAGA1UEBxMJQ2FwZSBUb3duMR0wGwYDVQQKExRUaGF3dGUgQ29uc3Vs -dGluZyBjYzEoMCYGA1UECxMfQ2VydGlmaWNhdGlvbiBTZXJ2aWNlcyBEaXZpc2lvbjEZMBcGA1UE -AxMQVGhhd3RlIFNlcnZlciBDQTEmMCQGCSqGSIb3DQEJARYXc2VydmVyLWNlcnRzQHRoYXd0ZS5j -b20wHhcNOTYwODAxMDAwMDAwWhcNMjAxMjMxMjM1OTU5WjCBxDELMAkGA1UEBhMCWkExFTATBgNV -BAgTDFdlc3Rlcm4gQ2FwZTESMBAGA1UEBxMJQ2FwZSBUb3duMR0wGwYDVQQKExRUaGF3dGUgQ29u -c3VsdGluZyBjYzEoMCYGA1UECxMfQ2VydGlmaWNhdGlvbiBTZXJ2aWNlcyBEaXZpc2lvbjEZMBcG -A1UEAxMQVGhhd3RlIFNlcnZlciBDQTEmMCQGCSqGSIb3DQEJARYXc2VydmVyLWNlcnRzQHRoYXd0 -ZS5jb20wgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBANOkUG7I/1Zr5s9dtuoMaHVHoqrC2oQl -/Kj0R1HahbUgdJSGHg91yekIYfUGbTBuFRkC6VLAYttNmZ7iagxEOM3+vuNkCXDF/rFrKbYvScg7 -1CcEJRCXL+eQbcAoQpnXTEPew/UhbVSfXcNY4cDk2VuwuNy0e982OsK1ZiIS1ocNAgMBAAGjEzAR -MA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZIhvcNAQEEBQADgYEAB/pMaVz7lcxG7oWDTSEwjsrZqG9J -GubaUeNgcGyEYRGhGshIPllDfU+VPaGLtwtimHp1it2ITk6eQNuozDJ0uW8NxuOzRAvZim+aKZuZ -GCg70eNAKJpaPNW15yAbi8qkq43pUdniTCxZqdq5snUb9kLy78fyGPmJvKP/iiMucEc= ------END CERTIFICATE----- - -Thawte Premium Server CA -======================== ------BEGIN CERTIFICATE----- -MIIDJzCCApCgAwIBAgIBATANBgkqhkiG9w0BAQQFADCBzjELMAkGA1UEBhMCWkExFTATBgNVBAgT -DFdlc3Rlcm4gQ2FwZTESMBAGA1UEBxMJQ2FwZSBUb3duMR0wGwYDVQQKExRUaGF3dGUgQ29uc3Vs -dGluZyBjYzEoMCYGA1UECxMfQ2VydGlmaWNhdGlvbiBTZXJ2aWNlcyBEaXZpc2lvbjEhMB8GA1UE -AxMYVGhhd3RlIFByZW1pdW0gU2VydmVyIENBMSgwJgYJKoZIhvcNAQkBFhlwcmVtaXVtLXNlcnZl -ckB0aGF3dGUuY29tMB4XDTk2MDgwMTAwMDAwMFoXDTIwMTIzMTIzNTk1OVowgc4xCzAJBgNVBAYT -AlpBMRUwEwYDVQQIEwxXZXN0ZXJuIENhcGUxEjAQBgNVBAcTCUNhcGUgVG93bjEdMBsGA1UEChMU -VGhhd3RlIENvbnN1bHRpbmcgY2MxKDAmBgNVBAsTH0NlcnRpZmljYXRpb24gU2VydmljZXMgRGl2 -aXNpb24xITAfBgNVBAMTGFRoYXd0ZSBQcmVtaXVtIFNlcnZlciBDQTEoMCYGCSqGSIb3DQEJARYZ -cHJlbWl1bS1zZXJ2ZXJAdGhhd3RlLmNvbTCBnzANBgkqhkiG9w0BAQEFAAOBjQAwgYkCgYEA0jY2 -aovXwlue2oFBYo847kkEVdbQ7xwblRZH7xhINTpS9CtqBo87L+pW46+GjZ4X9560ZXUCTe/LCaIh -Udib0GfQug2SBhRz1JPLlyoAnFxODLz6FVL88kRu2hFKbgifLy3j+ao6hnO2RlNYyIkFvYMRuHM/ -qgeN9EJN50CdHDcCAwEAAaMTMBEwDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG9w0BAQQFAAOBgQAm -SCwWwlj66BZ0DKqqX1Q/8tfJeGBeXm43YyJ3Nn6yF8Q0ufUIhfzJATj/Tb7yFkJD57taRvvBxhEf -8UqwKEbJw8RCfbz6q1lu1bdRiBHjpIUZa4JMpAwSremkrj/xw0llmozFyD4lt5SZu5IycQfwhl7t -UCemDaYj+bvLpgcUQg== ------END CERTIFICATE----- - Equifax Secure CA ================= -----BEGIN CERTIFICATE----- @@ -90,41 +38,6 @@ 70+sB3c4 -----END CERTIFICATE----- -Verisign Class 3 Public Primary Certification Authority -======================================================= ------BEGIN CERTIFICATE----- -MIICPDCCAaUCEHC65B0Q2Sk0tjjKewPMur8wDQYJKoZIhvcNAQECBQAwXzELMAkGA1UEBhMCVVMx -FzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMTcwNQYDVQQLEy5DbGFzcyAzIFB1YmxpYyBQcmltYXJ5 -IENlcnRpZmljYXRpb24gQXV0aG9yaXR5MB4XDTk2MDEyOTAwMDAwMFoXDTI4MDgwMTIzNTk1OVow -XzELMAkGA1UEBhMCVVMxFzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMTcwNQYDVQQLEy5DbGFzcyAz -IFB1YmxpYyBQcmltYXJ5IENlcnRpZmljYXRpb24gQXV0aG9yaXR5MIGfMA0GCSqGSIb3DQEBAQUA -A4GNADCBiQKBgQDJXFme8huKARS0EN8EQNvjV69qRUCPhAwL0TPZ2RHP7gJYHyX3KqhEBarsAx94 -f56TuZoAqiN91qyFomNFx3InzPRMxnVx0jnvT0Lwdd8KkMaOIG+YD/isI19wKTakyYbnsZogy1Ol -hec9vn2a/iRFM9x2Fe0PonFkTGUugWhFpwIDAQABMA0GCSqGSIb3DQEBAgUAA4GBALtMEivPLCYA -TxQT3ab7/AoRhIzzKBxnki98tsX63/Dolbwdj2wsqFHMc9ikwFPwTtYmwHYBV4GSXiHx0bH/59Ah -WM1pF+NEHJwZRDmJXNycAA9WjQKZ7aKQRUzkuxCkPfAyAw7xzvjoyVGM5mKf5p/AfbdynMk2Omuf -Tqj/ZA1k ------END CERTIFICATE----- - -Verisign Class 3 Public Primary Certification Authority - G2 -============================================================ ------BEGIN CERTIFICATE----- -MIIDAjCCAmsCEH3Z/gfPqB63EHln+6eJNMYwDQYJKoZIhvcNAQEFBQAwgcExCzAJBgNVBAYTAlVT -MRcwFQYDVQQKEw5WZXJpU2lnbiwgSW5jLjE8MDoGA1UECxMzQ2xhc3MgMyBQdWJsaWMgUHJpbWFy -eSBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eSAtIEcyMTowOAYDVQQLEzEoYykgMTk5OCBWZXJpU2ln -biwgSW5jLiAtIEZvciBhdXRob3JpemVkIHVzZSBvbmx5MR8wHQYDVQQLExZWZXJpU2lnbiBUcnVz -dCBOZXR3b3JrMB4XDTk4MDUxODAwMDAwMFoXDTI4MDgwMTIzNTk1OVowgcExCzAJBgNVBAYTAlVT -MRcwFQYDVQQKEw5WZXJpU2lnbiwgSW5jLjE8MDoGA1UECxMzQ2xhc3MgMyBQdWJsaWMgUHJpbWFy -eSBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eSAtIEcyMTowOAYDVQQLEzEoYykgMTk5OCBWZXJpU2ln -biwgSW5jLiAtIEZvciBhdXRob3JpemVkIHVzZSBvbmx5MR8wHQYDVQQLExZWZXJpU2lnbiBUcnVz -dCBOZXR3b3JrMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDMXtERXVxp0KvTuWpMmR9ZmDCO -FoUgRm1HP9SFIIThbbP4pO0M8RcPO/mn+SXXwc+EY/J8Y8+iR/LGWzOOZEAEaMGAuWQcRXfH2G71 -lSk8UOg013gfqLptQ5GVj0VXXn7F+8qkBOvqlzdUMG+7AUcyM83cV5tkaWH4mx0ciU9cZwIDAQAB -MA0GCSqGSIb3DQEBBQUAA4GBAFFNzb5cy5gZnBWyATl4Lk0PZ3BwmcYQWpSkU01UbSuvDV1Ai2TT -1+7eVmGSX6bEHRBhNtMsJzzoKQm5EWR0zLVznxxIqbxhAe7iF6YM40AIOw7n60RzKprxaZLvcRTD -Oaxxp5EJb+RxBrO6WVcmeQD2+A2iMzAo1KpYoJ2daZH9 ------END CERTIFICATE----- - GlobalSign Root CA ================== -----BEGIN CERTIFICATE----- @@ -168,63 +81,6 @@ TBj0/VLZjmmx6BEP3ojY+x1J96relc8geMJgEtslQIxq/H5COEBkEveegeGTLg== -----END CERTIFICATE----- -ValiCert Class 1 VA -=================== ------BEGIN CERTIFICATE----- -MIIC5zCCAlACAQEwDQYJKoZIhvcNAQEFBQAwgbsxJDAiBgNVBAcTG1ZhbGlDZXJ0IFZhbGlkYXRp -b24gTmV0d29yazEXMBUGA1UEChMOVmFsaUNlcnQsIEluYy4xNTAzBgNVBAsTLFZhbGlDZXJ0IENs -YXNzIDEgUG9saWN5IFZhbGlkYXRpb24gQXV0aG9yaXR5MSEwHwYDVQQDExhodHRwOi8vd3d3LnZh -bGljZXJ0LmNvbS8xIDAeBgkqhkiG9w0BCQEWEWluZm9AdmFsaWNlcnQuY29tMB4XDTk5MDYyNTIy -MjM0OFoXDTE5MDYyNTIyMjM0OFowgbsxJDAiBgNVBAcTG1ZhbGlDZXJ0IFZhbGlkYXRpb24gTmV0 -d29yazEXMBUGA1UEChMOVmFsaUNlcnQsIEluYy4xNTAzBgNVBAsTLFZhbGlDZXJ0IENsYXNzIDEg -UG9saWN5IFZhbGlkYXRpb24gQXV0aG9yaXR5MSEwHwYDVQQDExhodHRwOi8vd3d3LnZhbGljZXJ0 -LmNvbS8xIDAeBgkqhkiG9w0BCQEWEWluZm9AdmFsaWNlcnQuY29tMIGfMA0GCSqGSIb3DQEBAQUA -A4GNADCBiQKBgQDYWYJ6ibiWuqYvaG9YLqdUHAZu9OqNSLwxlBfw8068srg1knaw0KWlAdcAAxIi -GQj4/xEjm84H9b9pGib+TunRf50sQB1ZaG6m+FiwnRqP0z/x3BkGgagO4DrdyFNFCQbmD3DD+kCm -DuJWBQ8YTfwggtFzVXSNdnKgHZ0dwN0/cQIDAQABMA0GCSqGSIb3DQEBBQUAA4GBAFBoPUn0LBwG -lN+VYH+Wexf+T3GtZMjdd9LvWVXoP+iOBSoh8gfStadS/pyxtuJbdxdA6nLWI8sogTLDAHkY7FkX -icnGah5xyf23dKUlRWnFSKsZ4UWKJWsZ7uW7EvV/96aNUcPwnXS3qT6gpf+2SQMT2iLM7XGCK5nP -Orf1LXLI ------END CERTIFICATE----- - -ValiCert Class 2 VA -=================== ------BEGIN CERTIFICATE----- -MIIC5zCCAlACAQEwDQYJKoZIhvcNAQEFBQAwgbsxJDAiBgNVBAcTG1ZhbGlDZXJ0IFZhbGlkYXRp -b24gTmV0d29yazEXMBUGA1UEChMOVmFsaUNlcnQsIEluYy4xNTAzBgNVBAsTLFZhbGlDZXJ0IENs -YXNzIDIgUG9saWN5IFZhbGlkYXRpb24gQXV0aG9yaXR5MSEwHwYDVQQDExhodHRwOi8vd3d3LnZh -bGljZXJ0LmNvbS8xIDAeBgkqhkiG9w0BCQEWEWluZm9AdmFsaWNlcnQuY29tMB4XDTk5MDYyNjAw -MTk1NFoXDTE5MDYyNjAwMTk1NFowgbsxJDAiBgNVBAcTG1ZhbGlDZXJ0IFZhbGlkYXRpb24gTmV0 -d29yazEXMBUGA1UEChMOVmFsaUNlcnQsIEluYy4xNTAzBgNVBAsTLFZhbGlDZXJ0IENsYXNzIDIg -UG9saWN5IFZhbGlkYXRpb24gQXV0aG9yaXR5MSEwHwYDVQQDExhodHRwOi8vd3d3LnZhbGljZXJ0 -LmNvbS8xIDAeBgkqhkiG9w0BCQEWEWluZm9AdmFsaWNlcnQuY29tMIGfMA0GCSqGSIb3DQEBAQUA -A4GNADCBiQKBgQDOOnHK5avIWZJV16vYdA757tn2VUdZZUcOBVXc65g2PFxTXdMwzzjsvUGJ7SVC -CSRrCl6zfN1SLUzm1NZ9WlmpZdRJEy0kTRxQb7XBhVQ7/nHk01xC+YDgkRoKWzk2Z/M/VXwbP7Rf -ZHM047QSv4dk+NoS/zcnwbNDu+97bi5p9wIDAQABMA0GCSqGSIb3DQEBBQUAA4GBADt/UG9vUJSZ -SWI4OB9L+KXIPqeCgfYrx+jFzug6EILLGACOTb2oWH+heQC1u+mNr0HZDzTuIYEZoDJJKPTEjlbV -UjP9UNV+mWwD5MlM/Mtsq2azSiGM5bUMMj4QssxsodyamEwCW/POuZ6lcg5Ktz885hZo+L7tdEy8 -W9ViH0Pd ------END CERTIFICATE----- - -RSA Root Certificate 1 -====================== ------BEGIN CERTIFICATE----- -MIIC5zCCAlACAQEwDQYJKoZIhvcNAQEFBQAwgbsxJDAiBgNVBAcTG1ZhbGlDZXJ0IFZhbGlkYXRp -b24gTmV0d29yazEXMBUGA1UEChMOVmFsaUNlcnQsIEluYy4xNTAzBgNVBAsTLFZhbGlDZXJ0IENs -YXNzIDMgUG9saWN5IFZhbGlkYXRpb24gQXV0aG9yaXR5MSEwHwYDVQQDExhodHRwOi8vd3d3LnZh -bGljZXJ0LmNvbS8xIDAeBgkqhkiG9w0BCQEWEWluZm9AdmFsaWNlcnQuY29tMB4XDTk5MDYyNjAw -MjIzM1oXDTE5MDYyNjAwMjIzM1owgbsxJDAiBgNVBAcTG1ZhbGlDZXJ0IFZhbGlkYXRpb24gTmV0 -d29yazEXMBUGA1UEChMOVmFsaUNlcnQsIEluYy4xNTAzBgNVBAsTLFZhbGlDZXJ0IENsYXNzIDMg -UG9saWN5IFZhbGlkYXRpb24gQXV0aG9yaXR5MSEwHwYDVQQDExhodHRwOi8vd3d3LnZhbGljZXJ0 -LmNvbS8xIDAeBgkqhkiG9w0BCQEWEWluZm9AdmFsaWNlcnQuY29tMIGfMA0GCSqGSIb3DQEBAQUA -A4GNADCBiQKBgQDjmFGWHOjVsQaBalfDcnWTq8+epvzzFlLWLU2fNUSoLgRNB0mKOCn1dzfnt6td -3zZxFJmP3MKS8edgkpfs2Ejcv8ECIMYkpChMMFp2bbFc893enhBxoYjHW5tBbcqwuI4V7q0zK89H -BFx1cQqYJJgpp0lZpd34t0NiYfPT4tBVPwIDAQABMA0GCSqGSIb3DQEBBQUAA4GBAFa7AliEZwgs -3x/be0kz9dNnnfS0ChCzycUs4pJqcXgn8nCDQtM+z6lU9PHYkhaM0QTLS6vJn0WuPIqpsHEzXcjF -V9+vqDWzf4mH6eglkrh/hXqu1rweN1gqZ8mRzyqBPu3GOd/APhmcGcwTTYJBtYze4D1gCCAPRX5r -on+jjBXu ------END CERTIFICATE----- - Verisign Class 3 Public Primary Certification Authority - G3 ============================================================ -----BEGIN CERTIFICATE----- @@ -273,33 +129,6 @@ UPMxxY8BqHTr9Xgn2uf3ZkPznoM+IKrDNWCRzg== -----END CERTIFICATE----- -Entrust.net Secure Server CA -============================ ------BEGIN CERTIFICATE----- -MIIE2DCCBEGgAwIBAgIEN0rSQzANBgkqhkiG9w0BAQUFADCBwzELMAkGA1UEBhMCVVMxFDASBgNV -BAoTC0VudHJ1c3QubmV0MTswOQYDVQQLEzJ3d3cuZW50cnVzdC5uZXQvQ1BTIGluY29ycC4gYnkg -cmVmLiAobGltaXRzIGxpYWIuKTElMCMGA1UECxMcKGMpIDE5OTkgRW50cnVzdC5uZXQgTGltaXRl -ZDE6MDgGA1UEAxMxRW50cnVzdC5uZXQgU2VjdXJlIFNlcnZlciBDZXJ0aWZpY2F0aW9uIEF1dGhv -cml0eTAeFw05OTA1MjUxNjA5NDBaFw0xOTA1MjUxNjM5NDBaMIHDMQswCQYDVQQGEwJVUzEUMBIG -A1UEChMLRW50cnVzdC5uZXQxOzA5BgNVBAsTMnd3dy5lbnRydXN0Lm5ldC9DUFMgaW5jb3JwLiBi -eSByZWYuIChsaW1pdHMgbGlhYi4pMSUwIwYDVQQLExwoYykgMTk5OSBFbnRydXN0Lm5ldCBMaW1p -dGVkMTowOAYDVQQDEzFFbnRydXN0Lm5ldCBTZWN1cmUgU2VydmVyIENlcnRpZmljYXRpb24gQXV0 -aG9yaXR5MIGdMA0GCSqGSIb3DQEBAQUAA4GLADCBhwKBgQDNKIM0VBuJ8w+vN5Ex/68xYMmo6LIQ -aO2f55M28Qpku0f1BBc/I0dNxScZgSYMVHINiC3ZH5oSn7yzcdOAGT9HZnuMNSjSuQrfJNqc1lB5 -gXpa0zf3wkrYKZImZNHkmGw6AIr1NJtl+O3jEP/9uElY3KDegjlrgbEWGWG5VLbmQwIBA6OCAdcw -ggHTMBEGCWCGSAGG+EIBAQQEAwIABzCCARkGA1UdHwSCARAwggEMMIHeoIHboIHYpIHVMIHSMQsw -CQYDVQQGEwJVUzEUMBIGA1UEChMLRW50cnVzdC5uZXQxOzA5BgNVBAsTMnd3dy5lbnRydXN0Lm5l -dC9DUFMgaW5jb3JwLiBieSByZWYuIChsaW1pdHMgbGlhYi4pMSUwIwYDVQQLExwoYykgMTk5OSBF -bnRydXN0Lm5ldCBMaW1pdGVkMTowOAYDVQQDEzFFbnRydXN0Lm5ldCBTZWN1cmUgU2VydmVyIENl -cnRpZmljYXRpb24gQXV0aG9yaXR5MQ0wCwYDVQQDEwRDUkwxMCmgJ6AlhiNodHRwOi8vd3d3LmVu -dHJ1c3QubmV0L0NSTC9uZXQxLmNybDArBgNVHRAEJDAigA8xOTk5MDUyNTE2MDk0MFqBDzIwMTkw -NTI1MTYwOTQwWjALBgNVHQ8EBAMCAQYwHwYDVR0jBBgwFoAU8BdiE1U9s/8KAGv7UISX8+1i0Bow -HQYDVR0OBBYEFPAXYhNVPbP/CgBr+1CEl/PtYtAaMAwGA1UdEwQFMAMBAf8wGQYJKoZIhvZ9B0EA -BAwwChsEVjQuMAMCBJAwDQYJKoZIhvcNAQEFBQADgYEAkNwwAvpkdMKnCqV8IY00F6j7Rw7/JXyN -Ewr75Ji174z4xRAN95K+8cPV1ZVqBLssziY2ZcgxxufuP+NXdYR6Ee9GTxj005i7qIcyunL2POI9 -n9cd2cNgQ4xYDiKWL2KjLB+6rQXvqzJ4h6BUcxm1XAX5Uj5tLUUL9wqT6u0G+bI= ------END CERTIFICATE----- - Entrust.net Premium 2048 Secure Server CA ========================================= -----BEGIN CERTIFICATE----- @@ -362,23 +191,6 @@ NMR1pHMc8Y3c7635s3a0kr/clRAevsvIO1qEYBlWlKlV -----END CERTIFICATE----- -Equifax Secure eBusiness CA 1 -============================= ------BEGIN CERTIFICATE----- -MIICgjCCAeugAwIBAgIBBDANBgkqhkiG9w0BAQQFADBTMQswCQYDVQQGEwJVUzEcMBoGA1UEChMT -RXF1aWZheCBTZWN1cmUgSW5jLjEmMCQGA1UEAxMdRXF1aWZheCBTZWN1cmUgZUJ1c2luZXNzIENB -LTEwHhcNOTkwNjIxMDQwMDAwWhcNMjAwNjIxMDQwMDAwWjBTMQswCQYDVQQGEwJVUzEcMBoGA1UE -ChMTRXF1aWZheCBTZWN1cmUgSW5jLjEmMCQGA1UEAxMdRXF1aWZheCBTZWN1cmUgZUJ1c2luZXNz -IENBLTEwgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBAM4vGbwXt3fek6lfWg0XTzQaDJj0ItlZ -1MRoRvC0NcWFAyDGr0WlIVFFQesWWDYyb+JQYmT5/VGcqiTZ9J2DKocKIdMSODRsjQBuWqDZQu4a -IZX5UkxVWsUPOE9G+m34LjXWHXzr4vCwdYDIqROsvojvOm6rXyo4YgKwEnv+j6YDAgMBAAGjZjBk -MBEGCWCGSAGG+EIBAQQEAwIABzAPBgNVHRMBAf8EBTADAQH/MB8GA1UdIwQYMBaAFEp4MlIR21kW -Nl7fwRQ2QGpHfEyhMB0GA1UdDgQWBBRKeDJSEdtZFjZe38EUNkBqR3xMoTANBgkqhkiG9w0BAQQF -AAOBgQB1W6ibAxHm6VZMzfmpTMANmvPMZWnmJXbMWbfWVMMdzZmsGd20hdXgPfxiIKeES1hl8eL5 -lSE/9dR+WB5Hh1Q+WKG1tfgq73HnvMP2sUlG4tega+VWeponmHxGYhTnyfxuAxJ5gDgdSIKN/Bf+ -KpYrtWKmpj29f5JZzVoqgrI3eQ== ------END CERTIFICATE----- - AddTrust Low-Value Services Root ================================ -----BEGIN CERTIFICATE----- @@ -624,59 +436,6 @@ X36vWkzaH6byHCx+rgIW0lbQL1dTR+iS -----END CERTIFICATE----- -America Online Root Certification Authority 1 -============================================= ------BEGIN CERTIFICATE----- -MIIDpDCCAoygAwIBAgIBATANBgkqhkiG9w0BAQUFADBjMQswCQYDVQQGEwJVUzEcMBoGA1UEChMT -QW1lcmljYSBPbmxpbmUgSW5jLjE2MDQGA1UEAxMtQW1lcmljYSBPbmxpbmUgUm9vdCBDZXJ0aWZp -Y2F0aW9uIEF1dGhvcml0eSAxMB4XDTAyMDUyODA2MDAwMFoXDTM3MTExOTIwNDMwMFowYzELMAkG -A1UEBhMCVVMxHDAaBgNVBAoTE0FtZXJpY2EgT25saW5lIEluYy4xNjA0BgNVBAMTLUFtZXJpY2Eg -T25saW5lIFJvb3QgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkgMTCCASIwDQYJKoZIhvcNAQEBBQAD -ggEPADCCAQoCggEBAKgv6KRpBgNHw+kqmP8ZonCaxlCyfqXfaE0bfA+2l2h9LaaLl+lkhsmj76CG -v2BlnEtUiMJIxUo5vxTjWVXlGbR0yLQFOVwWpeKVBeASrlmLojNoWBym1BW32J/X3HGrfpq/m44z -DyL9Hy7nBzbvYjnF3cu6JRQj3gzGPTzOggjmZj7aUTsWOqMFf6Dch9Wc/HKpoH145LcxVR5lu9Rh -sCFg7RAycsWSJR74kEoYeEfffjA3PlAb2xzTa5qGUwew76wGePiEmf4hjUyAtgyC9mZweRrTT6PP -8c9GsEsPPt2IYriMqQkoO3rHl+Ee5fSfwMCuJKDIodkP1nsmgmkyPacCAwEAAaNjMGEwDwYDVR0T -AQH/BAUwAwEB/zAdBgNVHQ4EFgQUAK3Zo/Z59m50qX8zPYEX10zPM94wHwYDVR0jBBgwFoAUAK3Z -o/Z59m50qX8zPYEX10zPM94wDgYDVR0PAQH/BAQDAgGGMA0GCSqGSIb3DQEBBQUAA4IBAQB8itEf -GDeC4Liwo+1WlchiYZwFos3CYiZhzRAW18y0ZTTQEYqtqKkFZu90821fnZmv9ov761KyBZiibyrF -VL0lvV+uyIbqRizBs73B6UlwGBaXCBOMIOAbLjpHyx7kADCVW/RFo8AasAFOq73AI25jP4BKxQft -3OJvx8Fi8eNy1gTIdGcL+oiroQHIb/AUr9KZzVGTfu0uOMe9zkZQPXLjeSWdm4grECDdpbgyn43g -Kd8hdIaC2y+CMMbHNYaz+ZZfRtsMRf3zUMNvxsNIrUam4SdHCh0Om7bCd39j8uB9Gr784N/Xx6ds -sPmuujz9dLQR6FgNgLzTqIA6me11zEZ7 ------END CERTIFICATE----- - -America Online Root Certification Authority 2 -============================================= ------BEGIN CERTIFICATE----- -MIIFpDCCA4ygAwIBAgIBATANBgkqhkiG9w0BAQUFADBjMQswCQYDVQQGEwJVUzEcMBoGA1UEChMT -QW1lcmljYSBPbmxpbmUgSW5jLjE2MDQGA1UEAxMtQW1lcmljYSBPbmxpbmUgUm9vdCBDZXJ0aWZp -Y2F0aW9uIEF1dGhvcml0eSAyMB4XDTAyMDUyODA2MDAwMFoXDTM3MDkyOTE0MDgwMFowYzELMAkG -A1UEBhMCVVMxHDAaBgNVBAoTE0FtZXJpY2EgT25saW5lIEluYy4xNjA0BgNVBAMTLUFtZXJpY2Eg -T25saW5lIFJvb3QgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkgMjCCAiIwDQYJKoZIhvcNAQEBBQAD -ggIPADCCAgoCggIBAMxBRR3pPU0Q9oyxQcngXssNt79Hc9PwVU3dxgz6sWYFas14tNwC206B89en -fHG8dWOgXeMHDEjsJcQDIPT/DjsS/5uN4cbVG7RtIuOx238hZK+GvFciKtZHgVdEglZTvYYUAQv8 -f3SkWq7xuhG1m1hagLQ3eAkzfDJHA1zEpYNI9FdWboE2JxhP7JsowtS013wMPgwr38oE18aO6lhO -qKSlGBxsRZijQdEt0sdtjRnxrXm3gT+9BoInLRBYBbV4Bbkv2wxrkJB+FFk4u5QkE+XRnRTf04JN -RvCAOVIyD+OEsnpD8l7eXz8d3eOyG6ChKiMDbi4BFYdcpnV1x5dhvt6G3NRI270qv0pV2uh9UPu0 -gBe4lL8BPeraunzgWGcXuVjgiIZGZ2ydEEdYMtA1fHkqkKJaEBEjNa0vzORKW6fIJ/KD3l67Xnfn -6KVuY8INXWHQjNJsWiEOyiijzirplcdIz5ZvHZIlyMbGwcEMBawmxNJ10uEqZ8A9W6Wa6897Gqid -FEXlD6CaZd4vKL3Ob5Rmg0gp2OpljK+T2WSfVVcmv2/LNzGZo2C7HK2JNDJiuEMhBnIMoVxtRsX6 -Kc8w3onccVvdtjc+31D1uAclJuW8tf48ArO3+L5DwYcRlJ4jbBeKuIonDFRH8KmzwICMoCfrHRnj -B453cMor9H124HhnAgMBAAGjYzBhMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFE1FwWg4u3Op -aaEg5+31IqEjFNeeMB8GA1UdIwQYMBaAFE1FwWg4u3OpaaEg5+31IqEjFNeeMA4GA1UdDwEB/wQE -AwIBhjANBgkqhkiG9w0BAQUFAAOCAgEAZ2sGuV9FOypLM7PmG2tZTiLMubekJcmnxPBUlgtk87FY -T15R/LKXeydlwuXK5w0MJXti4/qftIe3RUavg6WXSIylvfEWK5t2LHo1YGwRgJfMqZJS5ivmae2p -+DYtLHe/YUjRYwu5W1LtGLBDQiKmsXeu3mnFzcccobGlHBD7GL4acN3Bkku+KVqdPzW+5X1R+FXg -JXUjhx5c3LqdsKyzadsXg8n33gy8CNyRnqjQ1xU3c6U1uPx+xURABsPr+CKAXEfOAuMRn0T//Zoy -zH1kUQ7rVyZ2OuMeIjzCpjbdGe+n/BLzJsBZMYVMnNjP36TMzCmT/5RtdlwTCJfy7aULTd3oyWgO -ZtMADjMSW7yV5TKQqLPGbIOtd+6Lfn6xqavT4fG2wLHqiMDn05DpKJKUe2h7lyoKZy2FAjgQ5ANh -1NolNscIWC2hp1GvMApJ9aZphwctREZ2jirlmjvXGKL8nDgQzMY70rUXOm/9riW99XJZZLF0Kjhf -GEzfz3EEWjbUvy+ZnOjZurGV5gJLIaFb1cFPj65pbVPbAZO1XB4Y3WRayhgoPmMEEf0cjQAPuDff -Z4qdZqkCapH/E8ovXYO8h5Ns3CRRFgQlZvqz2cK6Kb6aSDiCmfS/O0oxGfm/jiEzFMpPVF/7zvuP -cX/9XhmgD0uRuMRUvAawRY8mkaKO/qk= ------END CERTIFICATE----- - Visa eCommerce Root =================== -----BEGIN CERTIFICATE----- @@ -953,30 +712,6 @@ iJf2fL1LuCAWZwWN4jvBcj+UlTfHXbme2JOhF4//DGYVwSR8MnwDHTuhWEUykw== -----END CERTIFICATE----- -TDC Internet Root CA -==================== ------BEGIN CERTIFICATE----- -MIIEKzCCAxOgAwIBAgIEOsylTDANBgkqhkiG9w0BAQUFADBDMQswCQYDVQQGEwJESzEVMBMGA1UE -ChMMVERDIEludGVybmV0MR0wGwYDVQQLExRUREMgSW50ZXJuZXQgUm9vdCBDQTAeFw0wMTA0MDUx -NjMzMTdaFw0yMTA0MDUxNzAzMTdaMEMxCzAJBgNVBAYTAkRLMRUwEwYDVQQKEwxUREMgSW50ZXJu -ZXQxHTAbBgNVBAsTFFREQyBJbnRlcm5ldCBSb290IENBMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8A -MIIBCgKCAQEAxLhAvJHVYx/XmaCLDEAedLdInUaMArLgJF/wGROnN4NrXceO+YQwzho7+vvOi20j -xsNuZp+Jpd/gQlBn+h9sHvTQBda/ytZO5GhgbEaqHF1j4QeGDmUApy6mcca8uYGoOn0a0vnRrEvL -znWv3Hv6gXPU/Lq9QYjUdLP5Xjg6PEOo0pVOd20TDJ2PeAG3WiAfAzc14izbSysseLlJ28TQx5yc -5IogCSEWVmb/Bexb4/DPqyQkXsN/cHoSxNK1EKC2IeGNeGlVRGn1ypYcNIUXJXfi9i8nmHj9eQY6 -otZaQ8H/7AQ77hPv01ha/5Lr7K7a8jcDR0G2l8ktCkEiu7vmpwIDAQABo4IBJTCCASEwEQYJYIZI -AYb4QgEBBAQDAgAHMGUGA1UdHwReMFwwWqBYoFakVDBSMQswCQYDVQQGEwJESzEVMBMGA1UEChMM -VERDIEludGVybmV0MR0wGwYDVQQLExRUREMgSW50ZXJuZXQgUm9vdCBDQTENMAsGA1UEAxMEQ1JM -MTArBgNVHRAEJDAigA8yMDAxMDQwNTE2MzMxN1qBDzIwMjEwNDA1MTcwMzE3WjALBgNVHQ8EBAMC -AQYwHwYDVR0jBBgwFoAUbGQBx/2FbazI2p5QCIUItTxWqFAwHQYDVR0OBBYEFGxkAcf9hW2syNqe -UAiFCLU8VqhQMAwGA1UdEwQFMAMBAf8wHQYJKoZIhvZ9B0EABBAwDhsIVjUuMDo0LjADAgSQMA0G -CSqGSIb3DQEBBQUAA4IBAQBOQ8zR3R0QGwZ/t6T609lN+yOfI1Rb5osvBCiLtSdtiaHsmGnc540m -gwV5dOy0uaOXwTUA/RXaOYE6lTGQ3pfphqiZdwzlWqCE/xIWrG64jcN7ksKsLtB9KOy282A4aW8+ -2ARVPp7MVdK6/rtHBNcK2RYKNCn1WBPVT8+PVkuzHu7TmHnaCB4Mb7j4Fifvwm899qNLPg7kbWzb -O0ESm70NRyN/PErQr8Cv9u8btRXE64PECV90i9kR+8JWsTz4cMo0jUNAE4z9mQNUecYu6oah9jrU -Cbz0vGbMPVjQV0kK7iXiQe4T+Zs4NNEA9X7nlB38aQNiuJkFBT1reBK9sG9l ------END CERTIFICATE----- - UTN DATACorp SGC Root CA ======================== -----BEGIN CERTIFICATE----- @@ -1117,64 +852,6 @@ 8CgHrTwXZoi1/baI -----END CERTIFICATE----- -NetLock Business (Class B) Root -=============================== ------BEGIN CERTIFICATE----- -MIIFSzCCBLSgAwIBAgIBaTANBgkqhkiG9w0BAQQFADCBmTELMAkGA1UEBhMCSFUxETAPBgNVBAcT -CEJ1ZGFwZXN0MScwJQYDVQQKEx5OZXRMb2NrIEhhbG96YXRiaXp0b25zYWdpIEtmdC4xGjAYBgNV -BAsTEVRhbnVzaXR2YW55a2lhZG9rMTIwMAYDVQQDEylOZXRMb2NrIFV6bGV0aSAoQ2xhc3MgQikg -VGFudXNpdHZhbnlraWFkbzAeFw05OTAyMjUxNDEwMjJaFw0xOTAyMjAxNDEwMjJaMIGZMQswCQYD -VQQGEwJIVTERMA8GA1UEBxMIQnVkYXBlc3QxJzAlBgNVBAoTHk5ldExvY2sgSGFsb3phdGJpenRv -bnNhZ2kgS2Z0LjEaMBgGA1UECxMRVGFudXNpdHZhbnlraWFkb2sxMjAwBgNVBAMTKU5ldExvY2sg -VXpsZXRpIChDbGFzcyBCKSBUYW51c2l0dmFueWtpYWRvMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCB -iQKBgQCx6gTsIKAjwo84YM/HRrPVG/77uZmeBNwcf4xKgZjupNTKihe5In+DCnVMm8Bp2GQ5o+2S -o/1bXHQawEfKOml2mrriRBf8TKPV/riXiK+IA4kfpPIEPsgHC+b5sy96YhQJRhTKZPWLgLViqNhr -1nGTLbO/CVRY7QbrqHvcQ7GhaQIDAQABo4ICnzCCApswEgYDVR0TAQH/BAgwBgEB/wIBBDAOBgNV -HQ8BAf8EBAMCAAYwEQYJYIZIAYb4QgEBBAQDAgAHMIICYAYJYIZIAYb4QgENBIICURaCAk1GSUdZ -RUxFTSEgRXplbiB0YW51c2l0dmFueSBhIE5ldExvY2sgS2Z0LiBBbHRhbGFub3MgU3pvbGdhbHRh -dGFzaSBGZWx0ZXRlbGVpYmVuIGxlaXJ0IGVsamFyYXNvayBhbGFwamFuIGtlc3p1bHQuIEEgaGl0 -ZWxlc2l0ZXMgZm9seWFtYXRhdCBhIE5ldExvY2sgS2Z0LiB0ZXJtZWtmZWxlbG9zc2VnLWJpenRv -c2l0YXNhIHZlZGkuIEEgZGlnaXRhbGlzIGFsYWlyYXMgZWxmb2dhZGFzYW5hayBmZWx0ZXRlbGUg -YXogZWxvaXJ0IGVsbGVub3J6ZXNpIGVsamFyYXMgbWVndGV0ZWxlLiBBeiBlbGphcmFzIGxlaXJh -c2EgbWVndGFsYWxoYXRvIGEgTmV0TG9jayBLZnQuIEludGVybmV0IGhvbmxhcGphbiBhIGh0dHBz -Oi8vd3d3Lm5ldGxvY2submV0L2RvY3MgY2ltZW4gdmFneSBrZXJoZXRvIGF6IGVsbGVub3J6ZXNA -bmV0bG9jay5uZXQgZS1tYWlsIGNpbWVuLiBJTVBPUlRBTlQhIFRoZSBpc3N1YW5jZSBhbmQgdGhl -IHVzZSBvZiB0aGlzIGNlcnRpZmljYXRlIGlzIHN1YmplY3QgdG8gdGhlIE5ldExvY2sgQ1BTIGF2 -YWlsYWJsZSBhdCBodHRwczovL3d3dy5uZXRsb2NrLm5ldC9kb2NzIG9yIGJ5IGUtbWFpbCBhdCBj -cHNAbmV0bG9jay5uZXQuMA0GCSqGSIb3DQEBBAUAA4GBAATbrowXr/gOkDFOzT4JwG06sPgzTEdM -43WIEJessDgVkcYplswhwG08pXTP2IKlOcNl40JwuyKQ433bNXbhoLXan3BukxowOR0w2y7jfLKR -stE3Kfq51hdcR0/jHTjrn9V7lagonhVK0dHQKwCXoOKSNitjrFgBazMpUIaD8QFI ------END CERTIFICATE----- - -NetLock Express (Class C) Root -============================== ------BEGIN CERTIFICATE----- -MIIFTzCCBLigAwIBAgIBaDANBgkqhkiG9w0BAQQFADCBmzELMAkGA1UEBhMCSFUxETAPBgNVBAcT -CEJ1ZGFwZXN0MScwJQYDVQQKEx5OZXRMb2NrIEhhbG96YXRiaXp0b25zYWdpIEtmdC4xGjAYBgNV -BAsTEVRhbnVzaXR2YW55a2lhZG9rMTQwMgYDVQQDEytOZXRMb2NrIEV4cHJlc3N6IChDbGFzcyBD -KSBUYW51c2l0dmFueWtpYWRvMB4XDTk5MDIyNTE0MDgxMVoXDTE5MDIyMDE0MDgxMVowgZsxCzAJ -BgNVBAYTAkhVMREwDwYDVQQHEwhCdWRhcGVzdDEnMCUGA1UEChMeTmV0TG9jayBIYWxvemF0Yml6 -dG9uc2FnaSBLZnQuMRowGAYDVQQLExFUYW51c2l0dmFueWtpYWRvazE0MDIGA1UEAxMrTmV0TG9j -ayBFeHByZXNzeiAoQ2xhc3MgQykgVGFudXNpdHZhbnlraWFkbzCBnzANBgkqhkiG9w0BAQEFAAOB -jQAwgYkCgYEA6+ywbGGKIyWvYCDj2Z/8kwvbXY2wobNAOoLO/XXgeDIDhlqGlZHtU/qdQPzm6N3Z -W3oDvV3zOwzDUXmbrVWg6dADEK8KuhRC2VImESLH0iDMgqSaqf64gXadarfSNnU+sYYJ9m5tfk63 -euyucYT2BDMIJTLrdKwWRMbkQJMdf60CAwEAAaOCAp8wggKbMBIGA1UdEwEB/wQIMAYBAf8CAQQw -DgYDVR0PAQH/BAQDAgAGMBEGCWCGSAGG+EIBAQQEAwIABzCCAmAGCWCGSAGG+EIBDQSCAlEWggJN -RklHWUVMRU0hIEV6ZW4gdGFudXNpdHZhbnkgYSBOZXRMb2NrIEtmdC4gQWx0YWxhbm9zIFN6b2xn -YWx0YXRhc2kgRmVsdGV0ZWxlaWJlbiBsZWlydCBlbGphcmFzb2sgYWxhcGphbiBrZXN6dWx0LiBB -IGhpdGVsZXNpdGVzIGZvbHlhbWF0YXQgYSBOZXRMb2NrIEtmdC4gdGVybWVrZmVsZWxvc3NlZy1i -aXp0b3NpdGFzYSB2ZWRpLiBBIGRpZ2l0YWxpcyBhbGFpcmFzIGVsZm9nYWRhc2FuYWsgZmVsdGV0 -ZWxlIGF6IGVsb2lydCBlbGxlbm9yemVzaSBlbGphcmFzIG1lZ3RldGVsZS4gQXogZWxqYXJhcyBs -ZWlyYXNhIG1lZ3RhbGFsaGF0byBhIE5ldExvY2sgS2Z0LiBJbnRlcm5ldCBob25sYXBqYW4gYSBo -dHRwczovL3d3dy5uZXRsb2NrLm5ldC9kb2NzIGNpbWVuIHZhZ3kga2VyaGV0byBheiBlbGxlbm9y -emVzQG5ldGxvY2submV0IGUtbWFpbCBjaW1lbi4gSU1QT1JUQU5UISBUaGUgaXNzdWFuY2UgYW5k -IHRoZSB1c2Ugb2YgdGhpcyBjZXJ0aWZpY2F0ZSBpcyBzdWJqZWN0IHRvIHRoZSBOZXRMb2NrIENQ -UyBhdmFpbGFibGUgYXQgaHR0cHM6Ly93d3cubmV0bG9jay5uZXQvZG9jcyBvciBieSBlLW1haWwg -YXQgY3BzQG5ldGxvY2submV0LjANBgkqhkiG9w0BAQQFAAOBgQAQrX/XDDKACtiG8XmYta3UzbM2 -xJZIwVzNmtkFLp++UOv0JhQQLdRmF/iewSf98e3ke0ugbLWrmldwpu2gpO0u9f38vf5NNwgMvOOW -gyL1SRt/Syu0VMGAfJlOHdCM7tCs5ZL6dVb+ZKATj7i4Fp1hBWeAyNDYpQcCNJgEjTME1A== ------END CERTIFICATE----- - XRamp Global CA Root ==================== -----BEGIN CERTIFICATE----- @@ -1318,31 +995,6 @@ +fwC00fmcc4QAu4njIT/rEUNE1yDMuAlpYYsfPQS -----END CERTIFICATE----- -Firmaprofesional Root CA -======================== ------BEGIN CERTIFICATE----- -MIIEVzCCAz+gAwIBAgIBATANBgkqhkiG9w0BAQUFADCBnTELMAkGA1UEBhMCRVMxIjAgBgNVBAcT -GUMvIE11bnRhbmVyIDI0NCBCYXJjZWxvbmExQjBABgNVBAMTOUF1dG9yaWRhZCBkZSBDZXJ0aWZp -Y2FjaW9uIEZpcm1hcHJvZmVzaW9uYWwgQ0lGIEE2MjYzNDA2ODEmMCQGCSqGSIb3DQEJARYXY2FA -ZmlybWFwcm9mZXNpb25hbC5jb20wHhcNMDExMDI0MjIwMDAwWhcNMTMxMDI0MjIwMDAwWjCBnTEL -MAkGA1UEBhMCRVMxIjAgBgNVBAcTGUMvIE11bnRhbmVyIDI0NCBCYXJjZWxvbmExQjBABgNVBAMT -OUF1dG9yaWRhZCBkZSBDZXJ0aWZpY2FjaW9uIEZpcm1hcHJvZmVzaW9uYWwgQ0lGIEE2MjYzNDA2 -ODEmMCQGCSqGSIb3DQEJARYXY2FAZmlybWFwcm9mZXNpb25hbC5jb20wggEiMA0GCSqGSIb3DQEB -AQUAA4IBDwAwggEKAoIBAQDnIwNvbyOlXnjOlSztlB5uCp4Bx+ow0Syd3Tfom5h5VtP8c9/Qit5V -j1H5WuretXDE7aTt/6MNbg9kUDGvASdYrv5sp0ovFy3Tc9UTHI9ZpTQsHVQERc1ouKDAA6XPhUJH -lShbz++AbOCQl4oBPB3zhxAwJkh91/zpnZFx/0GaqUC1N5wpIE8fUuOgfRNtVLcK3ulqTgesrBlf -3H5idPayBQC6haD9HThuy1q7hryUZzM1gywfI834yJFxzJeL764P3CkDG8A563DtwW4O2GcLiam8 -NeTvtjS0pbbELaW+0MOUJEjb35bTALVmGotmBQ/dPz/LP6pemkr4tErvlTcbAgMBAAGjgZ8wgZww -KgYDVR0RBCMwIYYfaHR0cDovL3d3dy5maXJtYXByb2Zlc2lvbmFsLmNvbTASBgNVHRMBAf8ECDAG -AQH/AgEBMCsGA1UdEAQkMCKADzIwMDExMDI0MjIwMDAwWoEPMjAxMzEwMjQyMjAwMDBaMA4GA1Ud -DwEB/wQEAwIBBjAdBgNVHQ4EFgQUMwugZtHq2s7eYpMEKFK1FH84aLcwDQYJKoZIhvcNAQEFBQAD -ggEBAEdz/o0nVPD11HecJ3lXV7cVVuzH2Fi3AQL0M+2TUIiefEaxvT8Ub/GzR0iLjJcG1+p+o1wq -u00vR+L4OQbJnC4xGgN49Lw4xiKLMzHwFgQEffl25EvXwOaD7FnMP97/T2u3Z36mhoEyIwOdyPdf -wUpgpZKpsaSgYMN4h7Mi8yrrW6ntBas3D7Hi05V2Y1Z0jFhyGzflZKG+TQyTmAyX9odtsz/ny4Cm -7YjHX1BiAuiZdBbQ5rQ58SfLyEDW44YQqSMSkuBpQWOnryULwMWSyx6Yo1q6xTMPoJcB3X/ge9YG -VM+h4k0460tQtcsm9MracEpqoeJ5quGnM/b9Sh/22WA= ------END CERTIFICATE----- - Swisscom Root CA 1 ================== -----BEGIN CERTIFICATE----- @@ -1954,40 +1606,6 @@ WyH8EZE0vkHve52Xdf+XlcCWWC/qu0bXu+TZLg== -----END CERTIFICATE----- -AC Ra\xC3\xADz Certic\xC3\xA1mara S.A. -====================================== ------BEGIN CERTIFICATE----- -MIIGZjCCBE6gAwIBAgIPB35Sk3vgFeNX8GmMy+wMMA0GCSqGSIb3DQEBBQUAMHsxCzAJBgNVBAYT -AkNPMUcwRQYDVQQKDD5Tb2NpZWRhZCBDYW1lcmFsIGRlIENlcnRpZmljYWNpw7NuIERpZ2l0YWwg -LSBDZXJ0aWPDoW1hcmEgUy5BLjEjMCEGA1UEAwwaQUMgUmHDrXogQ2VydGljw6FtYXJhIFMuQS4w -HhcNMDYxMTI3MjA0NjI5WhcNMzAwNDAyMjE0MjAyWjB7MQswCQYDVQQGEwJDTzFHMEUGA1UECgw+ -U29jaWVkYWQgQ2FtZXJhbCBkZSBDZXJ0aWZpY2FjacOzbiBEaWdpdGFsIC0gQ2VydGljw6FtYXJh -IFMuQS4xIzAhBgNVBAMMGkFDIFJhw616IENlcnRpY8OhbWFyYSBTLkEuMIICIjANBgkqhkiG9w0B -AQEFAAOCAg8AMIICCgKCAgEAq2uJo1PMSCMI+8PPUZYILrgIem08kBeGqentLhM0R7LQcNzJPNCN -yu5LF6vQhbCnIwTLqKL85XXbQMpiiY9QngE9JlsYhBzLfDe3fezTf3MZsGqy2IiKLUV0qPezuMDU -2s0iiXRNWhU5cxh0T7XrmafBHoi0wpOQY5fzp6cSsgkiBzPZkc0OnB8OIMfuuzONj8LSWKdf/WU3 -4ojC2I+GdV75LaeHM/J4Ny+LvB2GNzmxlPLYvEqcgxhaBvzz1NS6jBUJJfD5to0EfhcSM2tXSExP -2yYe68yQ54v5aHxwD6Mq0Do43zeX4lvegGHTgNiRg0JaTASJaBE8rF9ogEHMYELODVoqDA+bMMCm -8Ibbq0nXl21Ii/kDwFJnmxL3wvIumGVC2daa49AZMQyth9VXAnow6IYm+48jilSH5L887uvDdUhf -HjlvgWJsxS3EF1QZtzeNnDeRyPYL1epjb4OsOMLzP96a++EjYfDIJss2yKHzMI+ko6Kh3VOz3vCa -Mh+DkXkwwakfU5tTohVTP92dsxA7SH2JD/ztA/X7JWR1DhcZDY8AFmd5ekD8LVkH2ZD6mq093ICK -5lw1omdMEWux+IBkAC1vImHFrEsm5VoQgpukg3s0956JkSCXjrdCx2bD0Omk1vUgjcTDlaxECp1b -czwmPS9KvqfJpxAe+59QafMCAwEAAaOB5jCB4zAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQE -AwIBBjAdBgNVHQ4EFgQU0QnQ6dfOeXRU+Tows/RtLAMDG2gwgaAGA1UdIASBmDCBlTCBkgYEVR0g -ADCBiTArBggrBgEFBQcCARYfaHR0cDovL3d3dy5jZXJ0aWNhbWFyYS5jb20vZHBjLzBaBggrBgEF -BQcCAjBOGkxMaW1pdGFjaW9uZXMgZGUgZ2FyYW507WFzIGRlIGVzdGUgY2VydGlmaWNhZG8gc2Ug -cHVlZGVuIGVuY29udHJhciBlbiBsYSBEUEMuMA0GCSqGSIb3DQEBBQUAA4ICAQBclLW4RZFNjmEf -AygPU3zmpFmps4p6xbD/CHwso3EcIRNnoZUSQDWDg4902zNc8El2CoFS3UnUmjIz75uny3XlesuX -EpBcunvFm9+7OSPI/5jOCk0iAUgHforA1SBClETvv3eiiWdIG0ADBaGJ7M9i4z0ldma/Jre7Ir5v -/zlXdLp6yQGVwZVR6Kss+LGGIOk/yzVb0hfpKv6DExdA7ohiZVvVO2Dpezy4ydV/NgIlqmjCMRW3 -MGXrfx1IebHPOeJCgBbT9ZMj/EyXyVo3bHwi2ErN0o42gzmRkBDI8ck1fj+404HGIGQatlDCIaR4 -3NAvO2STdPCWkPHv+wlaNECW8DYSwaN0jJN+Qd53i+yG2dIPPy3RzECiiWZIHiCznCNZc6lEc7wk -eZBWN7PGKX6jD/EpOe9+XCgycDWs2rjIdWb8m0w5R44bb5tNAlQiM+9hup4phO9OSzNHdpdqy35f -/RWmnkJDW2ZaiogN9xa5P1FlK2Zqi9E4UqLWRhH6/JocdJ6PlwsCT2TG9WjTSy3/pDceiz+/RL5h -RqGEPQgnTIEgd4kI6mdAXmwIUV80WoyWaM3X94nCHNMyAK9Sy9NgWyo6R35rMDOhYil/SrnhLecU -Iw4OGEfhefwVVdCx/CVxY3UzHCMrr1zZ7Ud3YA47Dx7SwNxkBYn8eNZcLCZDqQ== ------END CERTIFICATE----- - TC TrustCenter Class 2 CA II ============================ -----BEGIN CERTIFICATE----- @@ -2635,22 +2253,6 @@ tkYNbn5XOmeUwssfnHdKZ05phkOTOPu220+DkdRgfks+KzgHVZhepA== -----END CERTIFICATE----- -Verisign Class 3 Public Primary Certification Authority -======================================================= ------BEGIN CERTIFICATE----- -MIICPDCCAaUCEDyRMcsf9tAbDpq40ES/Er4wDQYJKoZIhvcNAQEFBQAwXzELMAkGA1UEBhMCVVMx -FzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMTcwNQYDVQQLEy5DbGFzcyAzIFB1YmxpYyBQcmltYXJ5 -IENlcnRpZmljYXRpb24gQXV0aG9yaXR5MB4XDTk2MDEyOTAwMDAwMFoXDTI4MDgwMjIzNTk1OVow -XzELMAkGA1UEBhMCVVMxFzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMTcwNQYDVQQLEy5DbGFzcyAz -IFB1YmxpYyBQcmltYXJ5IENlcnRpZmljYXRpb24gQXV0aG9yaXR5MIGfMA0GCSqGSIb3DQEBAQUA -A4GNADCBiQKBgQDJXFme8huKARS0EN8EQNvjV69qRUCPhAwL0TPZ2RHP7gJYHyX3KqhEBarsAx94 -f56TuZoAqiN91qyFomNFx3InzPRMxnVx0jnvT0Lwdd8KkMaOIG+YD/isI19wKTakyYbnsZogy1Ol -hec9vn2a/iRFM9x2Fe0PonFkTGUugWhFpwIDAQABMA0GCSqGSIb3DQEBBQUAA4GBABByUqkFFBky -CEHwxWsKzH4PIRnN5GfcX6kb5sroc50i2JhucwNhkcV8sEVAbkSdjbCxlnRhLQ2pRdKkkirWmnWX -bj9T/UWZYB2oK0z5XqcJ2HUw19JlYD1n1khVdWk/kfVIC0dpImmClr7JyDiGSnoscxlIaU5rfGW/ -D/xwzoiQ ------END CERTIFICATE----- - Microsec e-Szigno Root CA 2009 ============================== -----BEGIN CERTIFICATE----- @@ -3783,3 +3385,476 @@ EHiGG3njxPPyBJUgriOCxLM6AGK/5jYk4Ve6xx6QddVfP5VhK8E7zeWzaGHQRiapIVJpLesux+t3 zqY6tQMzT3bR51xUAV3LePTJDL/PEo4XLSNolOer/qmyKwbQBM0= -----END CERTIFICATE----- + +TeliaSonera Root CA v1 +====================== +-----BEGIN CERTIFICATE----- +MIIFODCCAyCgAwIBAgIRAJW+FqD3LkbxezmCcvqLzZYwDQYJKoZIhvcNAQEFBQAwNzEUMBIGA1UE +CgwLVGVsaWFTb25lcmExHzAdBgNVBAMMFlRlbGlhU29uZXJhIFJvb3QgQ0EgdjEwHhcNMDcxMDE4 +MTIwMDUwWhcNMzIxMDE4MTIwMDUwWjA3MRQwEgYDVQQKDAtUZWxpYVNvbmVyYTEfMB0GA1UEAwwW +VGVsaWFTb25lcmEgUm9vdCBDQSB2MTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAMK+ +6yfwIaPzaSZVfp3FVRaRXP3vIb9TgHot0pGMYzHw7CTww6XScnwQbfQ3t+XmfHnqjLWCi65ItqwA +3GV17CpNX8GH9SBlK4GoRz6JI5UwFpB/6FcHSOcZrr9FZ7E3GwYq/t75rH2D+1665I+XZ75Ljo1k +B1c4VWk0Nj0TSO9P4tNmHqTPGrdeNjPUtAa9GAH9d4RQAEX1jF3oI7x+/jXh7VB7qTCNGdMJjmhn +Xb88lxhTuylixcpecsHHltTbLaC0H2kD7OriUPEMPPCs81Mt8Bz17Ww5OXOAFshSsCPN4D7c3TxH +oLs1iuKYaIu+5b9y7tL6pe0S7fyYGKkmdtwoSxAgHNN/Fnct7W+A90m7UwW7XWjH1Mh1Fj+JWov3 +F0fUTPHSiXk+TT2YqGHeOh7S+F4D4MHJHIzTjU3TlTazN19jY5szFPAtJmtTfImMMsJu7D0hADnJ +oWjiUIMusDor8zagrC/kb2HCUQk5PotTubtn2txTuXZZNp1D5SDgPTJghSJRt8czu90VL6R4pgd7 +gUY2BIbdeTXHlSw7sKMXNeVzH7RcWe/a6hBle3rQf5+ztCo3O3CLm1u5K7fsslESl1MpWtTwEhDc +TwK7EpIvYtQ/aUN8Ddb8WHUBiJ1YFkveupD/RwGJBmr2X7KQarMCpgKIv7NHfirZ1fpoeDVNAgMB +AAGjPzA9MA8GA1UdEwEB/wQFMAMBAf8wCwYDVR0PBAQDAgEGMB0GA1UdDgQWBBTwj1k4ALP1j5qW +DNXr+nuqF+gTEjANBgkqhkiG9w0BAQUFAAOCAgEAvuRcYk4k9AwI//DTDGjkk0kiP0Qnb7tt3oNm +zqjMDfz1mgbldxSR651Be5kqhOX//CHBXfDkH1e3damhXwIm/9fH907eT/j3HEbAek9ALCI18Bmx +0GtnLLCo4MBANzX2hFxc469CeP6nyQ1Q6g2EdvZR74NTxnr/DlZJLo961gzmJ1TjTQpgcmLNkQfW +pb/ImWvtxBnmq0wROMVvMeJuScg/doAmAyYp4Db29iBT4xdwNBedY2gea+zDTYa4EzAvXUYNR0PV +G6pZDrlcjQZIrXSHX8f8MVRBE+LHIQ6e4B4N4cB7Q4WQxYpYxmUKeFfyxiMPAdkgS94P+5KFdSpc +c41teyWRyu5FrgZLAMzTsVlQ2jqIOylDRl6XK1TOU2+NSueW+r9xDkKLfP0ooNBIytrEgUy7onOT +JsjrDNYmiLbAJM+7vVvrdX3pCI6GMyx5dwlppYn8s3CQh3aP0yK7Qs69cwsgJirQmz1wHiRszYd2 +qReWt88NkvuOGKmYSdGe/mBEciG5Ge3C9THxOUiIkCR1VBatzvT4aRRkOfujuLpwQMcnHL/EVlP6 +Y2XQ8xwOFvVrhlhNGNTkDY6lnVuR3HYkUD/GKvvZt5y11ubQ2egZixVxSK236thZiNSQvxaz2ems +WWFUyBy6ysHK4bkgTI86k4mloMy/0/Z1pHWWbVY= +-----END CERTIFICATE----- + +E-Tugra Certification Authority +=============================== +-----BEGIN CERTIFICATE----- +MIIGSzCCBDOgAwIBAgIIamg+nFGby1MwDQYJKoZIhvcNAQELBQAwgbIxCzAJBgNVBAYTAlRSMQ8w +DQYDVQQHDAZBbmthcmExQDA+BgNVBAoMN0UtVHXEn3JhIEVCRyBCaWxpxZ9pbSBUZWtub2xvamls +ZXJpIHZlIEhpem1ldGxlcmkgQS7Fni4xJjAkBgNVBAsMHUUtVHVncmEgU2VydGlmaWthc3lvbiBN +ZXJrZXppMSgwJgYDVQQDDB9FLVR1Z3JhIENlcnRpZmljYXRpb24gQXV0aG9yaXR5MB4XDTEzMDMw +NTEyMDk0OFoXDTIzMDMwMzEyMDk0OFowgbIxCzAJBgNVBAYTAlRSMQ8wDQYDVQQHDAZBbmthcmEx +QDA+BgNVBAoMN0UtVHXEn3JhIEVCRyBCaWxpxZ9pbSBUZWtub2xvamlsZXJpIHZlIEhpem1ldGxl +cmkgQS7Fni4xJjAkBgNVBAsMHUUtVHVncmEgU2VydGlmaWthc3lvbiBNZXJrZXppMSgwJgYDVQQD +DB9FLVR1Z3JhIENlcnRpZmljYXRpb24gQXV0aG9yaXR5MIICIjANBgkqhkiG9w0BAQEFAAOCAg8A +MIICCgKCAgEA4vU/kwVRHoViVF56C/UYB4Oufq9899SKa6VjQzm5S/fDxmSJPZQuVIBSOTkHS0vd +hQd2h8y/L5VMzH2nPbxHD5hw+IyFHnSOkm0bQNGZDbt1bsipa5rAhDGvykPL6ys06I+XawGb1Q5K +CKpbknSFQ9OArqGIW66z6l7LFpp3RMih9lRozt6Plyu6W0ACDGQXwLWTzeHxE2bODHnv0ZEoq1+g +ElIwcxmOj+GMB6LDu0rw6h8VqO4lzKRG+Bsi77MOQ7osJLjFLFzUHPhdZL3Dk14opz8n8Y4e0ypQ +BaNV2cvnOVPAmJ6MVGKLJrD3fY185MaeZkJVgkfnsliNZvcHfC425lAcP9tDJMW/hkd5s3kc91r0 +E+xs+D/iWR+V7kI+ua2oMoVJl0b+SzGPWsutdEcf6ZG33ygEIqDUD13ieU/qbIWGvaimzuT6w+Gz +rt48Ue7LE3wBf4QOXVGUnhMMti6lTPk5cDZvlsouDERVxcr6XQKj39ZkjFqzAQqptQpHF//vkUAq +jqFGOjGY5RH8zLtJVor8udBhmm9lbObDyz51Sf6Pp+KJxWfXnUYTTjF2OySznhFlhqt/7x3U+Lzn +rFpct1pHXFXOVbQicVtbC/DP3KBhZOqp12gKY6fgDT+gr9Oq0n7vUaDmUStVkhUXU8u3Zg5mTPj5 +dUyQ5xJwx0UCAwEAAaNjMGEwHQYDVR0OBBYEFC7j27JJ0JxUeVz6Jyr+zE7S6E5UMA8GA1UdEwEB +/wQFMAMBAf8wHwYDVR0jBBgwFoAULuPbsknQnFR5XPonKv7MTtLoTlQwDgYDVR0PAQH/BAQDAgEG +MA0GCSqGSIb3DQEBCwUAA4ICAQAFNzr0TbdF4kV1JI+2d1LoHNgQk2Xz8lkGpD4eKexd0dCrfOAK +kEh47U6YA5n+KGCRHTAduGN8qOY1tfrTYXbm1gdLymmasoR6d5NFFxWfJNCYExL/u6Au/U5Mh/jO +XKqYGwXgAEZKgoClM4so3O0409/lPun++1ndYYRP0lSWE2ETPo+Aab6TR7U1Q9Jauz1c77NCR807 +VRMGsAnb/WP2OogKmW9+4c4bU2pEZiNRCHu8W1Ki/QY3OEBhj0qWuJA3+GbHeJAAFS6LrVE1Uweo +a2iu+U48BybNCAVwzDk/dr2l02cmAYamU9JgO3xDf1WKvJUawSg5TB9D0pH0clmKuVb8P7Sd2nCc +dlqMQ1DujjByTd//SffGqWfZbawCEeI6FiWnWAjLb1NBnEg4R2gz0dfHj9R0IdTDBZB6/86WiLEV +KV0jq9BgoRJP3vQXzTLlyb/IQ639Lo7xr+L0mPoSHyDYwKcMhcWQ9DstliaxLL5Mq+ux0orJ23gT +Dx4JnW2PAJ8C2sH6H3p6CcRK5ogql5+Ji/03X186zjhZhkuvcQu02PJwT58yE+Owp1fl2tpDy4Q0 +8ijE6m30Ku/Ba3ba+367hTzSU8JNvnHhRdH9I2cNE3X7z2VnIp2usAnRCf8dNL/+I5c30jn6PQ0G +C7TbO6Orb1wdtn7os4I07QZcJA== +-----END CERTIFICATE----- + +T-TeleSec GlobalRoot Class 2 +============================ +-----BEGIN CERTIFICATE----- +MIIDwzCCAqugAwIBAgIBATANBgkqhkiG9w0BAQsFADCBgjELMAkGA1UEBhMCREUxKzApBgNVBAoM +IlQtU3lzdGVtcyBFbnRlcnByaXNlIFNlcnZpY2VzIEdtYkgxHzAdBgNVBAsMFlQtU3lzdGVtcyBU +cnVzdCBDZW50ZXIxJTAjBgNVBAMMHFQtVGVsZVNlYyBHbG9iYWxSb290IENsYXNzIDIwHhcNMDgx +MDAxMTA0MDE0WhcNMzMxMDAxMjM1OTU5WjCBgjELMAkGA1UEBhMCREUxKzApBgNVBAoMIlQtU3lz +dGVtcyBFbnRlcnByaXNlIFNlcnZpY2VzIEdtYkgxHzAdBgNVBAsMFlQtU3lzdGVtcyBUcnVzdCBD +ZW50ZXIxJTAjBgNVBAMMHFQtVGVsZVNlYyBHbG9iYWxSb290IENsYXNzIDIwggEiMA0GCSqGSIb3 +DQEBAQUAA4IBDwAwggEKAoIBAQCqX9obX+hzkeXaXPSi5kfl82hVYAUdAqSzm1nzHoqvNK38DcLZ +SBnuaY/JIPwhqgcZ7bBcrGXHX+0CfHt8LRvWurmAwhiCFoT6ZrAIxlQjgeTNuUk/9k9uN0goOA/F +vudocP05l03Sx5iRUKrERLMjfTlH6VJi1hKTXrcxlkIF+3anHqP1wvzpesVsqXFP6st4vGCvx970 +2cu+fjOlbpSD8DT6IavqjnKgP6TeMFvvhk1qlVtDRKgQFRzlAVfFmPHmBiiRqiDFt1MmUUOyCxGV +WOHAD3bZwI18gfNycJ5v/hqO2V81xrJvNHy+SE/iWjnX2J14np+GPgNeGYtEotXHAgMBAAGjQjBA +MA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgEGMB0GA1UdDgQWBBS/WSA2AHmgoCJrjNXy +YdK4LMuCSjANBgkqhkiG9w0BAQsFAAOCAQEAMQOiYQsfdOhyNsZt+U2e+iKo4YFWz827n+qrkRk4 +r6p8FU3ztqONpfSO9kSpp+ghla0+AGIWiPACuvxhI+YzmzB6azZie60EI4RYZeLbK4rnJVM3YlNf +vNoBYimipidx5joifsFvHZVwIEoHNN/q/xWA5brXethbdXwFeilHfkCoMRN3zUA7tFFHei4R40cR +3p1m0IvVVGb6g1XqfMIpiRvpb7PO4gWEyS8+eIVibslfwXhjdFjASBgMmTnrpMwatXlajRWc2BQN +9noHV8cigwUtPJslJj0Ys6lDfMjIq2SPDqO/nBudMNva0Bkuqjzx+zOAduTNrRlPBSeOE6Fuwg== +-----END CERTIFICATE----- + +Atos TrustedRoot 2011 +===================== +-----BEGIN CERTIFICATE----- +MIIDdzCCAl+gAwIBAgIIXDPLYixfszIwDQYJKoZIhvcNAQELBQAwPDEeMBwGA1UEAwwVQXRvcyBU +cnVzdGVkUm9vdCAyMDExMQ0wCwYDVQQKDARBdG9zMQswCQYDVQQGEwJERTAeFw0xMTA3MDcxNDU4 +MzBaFw0zMDEyMzEyMzU5NTlaMDwxHjAcBgNVBAMMFUF0b3MgVHJ1c3RlZFJvb3QgMjAxMTENMAsG +A1UECgwEQXRvczELMAkGA1UEBhMCREUwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCV +hTuXbyo7LjvPpvMpNb7PGKw+qtn4TaA+Gke5vJrf8v7MPkfoepbCJI419KkM/IL9bcFyYie96mvr +54rMVD6QUM+A1JX76LWC1BTFtqlVJVfbsVD2sGBkWXppzwO3bw2+yj5vdHLqqjAqc2K+SZFhyBH+ +DgMq92og3AIVDV4VavzjgsG1xZ1kCWyjWZgHJ8cblithdHFsQ/H3NYkQ4J7sVaE3IqKHBAUsR320 +HLliKWYoyrfhk/WklAOZuXCFteZI6o1Q/NnezG8HDt0Lcp2AMBYHlT8oDv3FdU9T1nSatCQujgKR +z3bFmx5VdJx4IbHwLfELn8LVlhgf8FQieowHAgMBAAGjfTB7MB0GA1UdDgQWBBSnpQaxLKYJYO7R +l+lwrrw7GWzbITAPBgNVHRMBAf8EBTADAQH/MB8GA1UdIwQYMBaAFKelBrEspglg7tGX6XCuvDsZ +bNshMBgGA1UdIAQRMA8wDQYLKwYBBAGwLQMEAQEwDgYDVR0PAQH/BAQDAgGGMA0GCSqGSIb3DQEB +CwUAA4IBAQAmdzTblEiGKkGdLD4GkGDEjKwLVLgfuXvTBznk+j57sj1O7Z8jvZfza1zv7v1Apt+h +k6EKhqzvINB5Ab149xnYJDE0BAGmuhWawyfc2E8PzBhj/5kPDpFrdRbhIfzYJsdHt6bPWHJxfrrh +TZVHO8mvbaG0weyJ9rQPOLXiZNwlz6bb65pcmaHFCN795trV1lpFDMS3wrUU77QR/w4VtfX128a9 +61qn8FYiqTxlVMYVqL2Gns2Dlmh6cYGJ4Qvh6hEbaAjMaZ7snkGeRDImeuKHCnE96+RapNLbxc3G +3mB/ufNPRJLvKrcYPqcZ2Qt9sTdBQrC6YB3y/gkRsPCHe6ed +-----END CERTIFICATE----- + +QuoVadis Root CA 1 G3 +===================== +-----BEGIN CERTIFICATE----- +MIIFYDCCA0igAwIBAgIUeFhfLq0sGUvjNwc1NBMotZbUZZMwDQYJKoZIhvcNAQELBQAwSDELMAkG +A1UEBhMCQk0xGTAXBgNVBAoTEFF1b1ZhZGlzIExpbWl0ZWQxHjAcBgNVBAMTFVF1b1ZhZGlzIFJv +b3QgQ0EgMSBHMzAeFw0xMjAxMTIxNzI3NDRaFw00MjAxMTIxNzI3NDRaMEgxCzAJBgNVBAYTAkJN +MRkwFwYDVQQKExBRdW9WYWRpcyBMaW1pdGVkMR4wHAYDVQQDExVRdW9WYWRpcyBSb290IENBIDEg +RzMwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQCgvlAQjunybEC0BJyFuTHK3C3kEakE +PBtVwedYMB0ktMPvhd6MLOHBPd+C5k+tR4ds7FtJwUrVu4/sh6x/gpqG7D0DmVIB0jWerNrwU8lm +PNSsAgHaJNM7qAJGr6Qc4/hzWHa39g6QDbXwz8z6+cZM5cOGMAqNF34168Xfuw6cwI2H44g4hWf6 +Pser4BOcBRiYz5P1sZK0/CPTz9XEJ0ngnjybCKOLXSoh4Pw5qlPafX7PGglTvF0FBM+hSo+LdoIN +ofjSxxR3W5A2B4GbPgb6Ul5jxaYA/qXpUhtStZI5cgMJYr2wYBZupt0lwgNm3fME0UDiTouG9G/l +g6AnhF4EwfWQvTA9xO+oabw4m6SkltFi2mnAAZauy8RRNOoMqv8hjlmPSlzkYZqn0ukqeI1RPToV +7qJZjqlc3sX5kCLliEVx3ZGZbHqfPT2YfF72vhZooF6uCyP8Wg+qInYtyaEQHeTTRCOQiJ/GKubX +9ZqzWB4vMIkIG1SitZgj7Ah3HJVdYdHLiZxfokqRmu8hqkkWCKi9YSgxyXSthfbZxbGL0eUQMk1f +iyA6PEkfM4VZDdvLCXVDaXP7a3F98N/ETH3Goy7IlXnLc6KOTk0k+17kBL5yG6YnLUlamXrXXAkg +t3+UuU/xDRxeiEIbEbfnkduebPRq34wGmAOtzCjvpUfzUwIDAQABo0IwQDAPBgNVHRMBAf8EBTAD +AQH/MA4GA1UdDwEB/wQEAwIBBjAdBgNVHQ4EFgQUo5fW816iEOGrRZ88F2Q87gFwnMwwDQYJKoZI +hvcNAQELBQADggIBABj6W3X8PnrHX3fHyt/PX8MSxEBd1DKquGrX1RUVRpgjpeaQWxiZTOOtQqOC +MTaIzen7xASWSIsBx40Bz1szBpZGZnQdT+3Btrm0DWHMY37XLneMlhwqI2hrhVd2cDMT/uFPpiN3 +GPoajOi9ZcnPP/TJF9zrx7zABC4tRi9pZsMbj/7sPtPKlL92CiUNqXsCHKnQO18LwIE6PWThv6ct +Tr1NxNgpxiIY0MWscgKCP6o6ojoilzHdCGPDdRS5YCgtW2jgFqlmgiNR9etT2DGbe+m3nUvriBbP ++V04ikkwj+3x6xn0dxoxGE1nVGwvb2X52z3sIexe9PSLymBlVNFxZPT5pqOBMzYzcfCkeF9OrYMh +3jRJjehZrJ3ydlo28hP0r+AJx2EqbPfgna67hkooby7utHnNkDPDs3b69fBsnQGQ+p6Q9pxyz0fa +wx/kNSBT8lTR32GDpgLiJTjehTItXnOQUl1CxM49S+H5GYQd1aJQzEH7QRTDvdbJWqNjZgKAvQU6 +O0ec7AAmTPWIUb+oI38YB7AL7YsmoWTTYUrrXJ/es69nA7Mf3W1daWhpq1467HxpvMc7hU6eFbm0 +FU/DlXpY18ls6Wy58yljXrQs8C097Vpl4KlbQMJImYFtnh8GKjwStIsPm6Ik8KaN1nrgS7ZklmOV +hMJKzRwuJIczYOXD +-----END CERTIFICATE----- + +QuoVadis Root CA 2 G3 +===================== +-----BEGIN CERTIFICATE----- +MIIFYDCCA0igAwIBAgIURFc0JFuBiZs18s64KztbpybwdSgwDQYJKoZIhvcNAQELBQAwSDELMAkG +A1UEBhMCQk0xGTAXBgNVBAoTEFF1b1ZhZGlzIExpbWl0ZWQxHjAcBgNVBAMTFVF1b1ZhZGlzIFJv +b3QgQ0EgMiBHMzAeFw0xMjAxMTIxODU5MzJaFw00MjAxMTIxODU5MzJaMEgxCzAJBgNVBAYTAkJN +MRkwFwYDVQQKExBRdW9WYWRpcyBMaW1pdGVkMR4wHAYDVQQDExVRdW9WYWRpcyBSb290IENBIDIg +RzMwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQChriWyARjcV4g/Ruv5r+LrI3HimtFh +ZiFfqq8nUeVuGxbULX1QsFN3vXg6YOJkApt8hpvWGo6t/x8Vf9WVHhLL5hSEBMHfNrMWn4rjyduY +NM7YMxcoRvynyfDStNVNCXJJ+fKH46nafaF9a7I6JaltUkSs+L5u+9ymc5GQYaYDFCDy54ejiK2t +oIz/pgslUiXnFgHVy7g1gQyjO/Dh4fxaXc6AcW34Sas+O7q414AB+6XrW7PFXmAqMaCvN+ggOp+o +MiwMzAkd056OXbxMmO7FGmh77FOm6RQ1o9/NgJ8MSPsc9PG/Srj61YxxSscfrf5BmrODXfKEVu+l +V0POKa2Mq1W/xPtbAd0jIaFYAI7D0GoT7RPjEiuA3GfmlbLNHiJuKvhB1PLKFAeNilUSxmn1uIZo +L1NesNKqIcGY5jDjZ1XHm26sGahVpkUG0CM62+tlXSoREfA7T8pt9DTEceT/AFr2XK4jYIVz8eQQ +sSWu1ZK7E8EM4DnatDlXtas1qnIhO4M15zHfeiFuuDIIfR0ykRVKYnLP43ehvNURG3YBZwjgQQvD +6xVu+KQZ2aKrr+InUlYrAoosFCT5v0ICvybIxo/gbjh9Uy3l7ZizlWNof/k19N+IxWA1ksB8aRxh +lRbQ694Lrz4EEEVlWFA4r0jyWbYW8jwNkALGcC4BrTwV1wIDAQABo0IwQDAPBgNVHRMBAf8EBTAD +AQH/MA4GA1UdDwEB/wQEAwIBBjAdBgNVHQ4EFgQU7edvdlq/YOxJW8ald7tyFnGbxD0wDQYJKoZI +hvcNAQELBQADggIBAJHfgD9DCX5xwvfrs4iP4VGyvD11+ShdyLyZm3tdquXK4Qr36LLTn91nMX66 +AarHakE7kNQIXLJgapDwyM4DYvmL7ftuKtwGTTwpD4kWilhMSA/ohGHqPHKmd+RCroijQ1h5fq7K +pVMNqT1wvSAZYaRsOPxDMuHBR//47PERIjKWnML2W2mWeyAMQ0GaW/ZZGYjeVYg3UQt4XAoeo0L9 +x52ID8DyeAIkVJOviYeIyUqAHerQbj5hLja7NQ4nlv1mNDthcnPxFlxHBlRJAHpYErAK74X9sbgz +dWqTHBLmYF5vHX/JHyPLhGGfHoJE+V+tYlUkmlKY7VHnoX6XOuYvHxHaU4AshZ6rNRDbIl9qxV6X +U/IyAgkwo1jwDQHVcsaxfGl7w/U2Rcxhbl5MlMVerugOXou/983g7aEOGzPuVBj+D77vfoRrQ+Nw +mNtddbINWQeFFSM51vHfqSYP1kjHs6Yi9TM3WpVHn3u6GBVv/9YUZINJ0gpnIdsPNWNgKCLjsZWD +zYWm3S8P52dSbrsvhXz1SnPnxT7AvSESBT/8twNJAlvIJebiVDj1eYeMHVOyToV7BjjHLPj4sHKN +JeV3UvQDHEimUF+IIDBu8oJDqz2XhOdT+yHBTw8imoa4WSr2Rz0ZiC3oheGe7IUIarFsNMkd7Egr +O3jtZsSOeWmD3n+M +-----END CERTIFICATE----- + +QuoVadis Root CA 3 G3 +===================== +-----BEGIN CERTIFICATE----- +MIIFYDCCA0igAwIBAgIULvWbAiin23r/1aOp7r0DoM8Sah0wDQYJKoZIhvcNAQELBQAwSDELMAkG +A1UEBhMCQk0xGTAXBgNVBAoTEFF1b1ZhZGlzIExpbWl0ZWQxHjAcBgNVBAMTFVF1b1ZhZGlzIFJv +b3QgQ0EgMyBHMzAeFw0xMjAxMTIyMDI2MzJaFw00MjAxMTIyMDI2MzJaMEgxCzAJBgNVBAYTAkJN +MRkwFwYDVQQKExBRdW9WYWRpcyBMaW1pdGVkMR4wHAYDVQQDExVRdW9WYWRpcyBSb290IENBIDMg +RzMwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQCzyw4QZ47qFJenMioKVjZ/aEzHs286 +IxSR/xl/pcqs7rN2nXrpixurazHb+gtTTK/FpRp5PIpM/6zfJd5O2YIyC0TeytuMrKNuFoM7pmRL +Mon7FhY4futD4tN0SsJiCnMK3UmzV9KwCoWdcTzeo8vAMvMBOSBDGzXRU7Ox7sWTaYI+FrUoRqHe +6okJ7UO4BUaKhvVZR74bbwEhELn9qdIoyhA5CcoTNs+cra1AdHkrAj80//ogaX3T7mH1urPnMNA3 +I4ZyYUUpSFlob3emLoG+B01vr87ERRORFHAGjx+f+IdpsQ7vw4kZ6+ocYfx6bIrc1gMLnia6Et3U +VDmrJqMz6nWB2i3ND0/kA9HvFZcba5DFApCTZgIhsUfei5pKgLlVj7WiL8DWM2fafsSntARE60f7 +5li59wzweyuxwHApw0BiLTtIadwjPEjrewl5qW3aqDCYz4ByA4imW0aucnl8CAMhZa634RylsSqi +Md5mBPfAdOhx3v89WcyWJhKLhZVXGqtrdQtEPREoPHtht+KPZ0/l7DxMYIBpVzgeAVuNVejH38DM +dyM0SXV89pgR6y3e7UEuFAUCf+D+IOs15xGsIs5XPd7JMG0QA4XN8f+MFrXBsj6IbGB/kE+V9/Yt +rQE5BwT6dYB9v0lQ7e/JxHwc64B+27bQ3RP+ydOc17KXqQIDAQABo0IwQDAPBgNVHRMBAf8EBTAD +AQH/MA4GA1UdDwEB/wQEAwIBBjAdBgNVHQ4EFgQUxhfQvKjqAkPyGwaZXSuQILnXnOQwDQYJKoZI +hvcNAQELBQADggIBADRh2Va1EodVTd2jNTFGu6QHcrxfYWLopfsLN7E8trP6KZ1/AvWkyaiTt3px +KGmPc+FSkNrVvjrlt3ZqVoAh313m6Tqe5T72omnHKgqwGEfcIHB9UqM+WXzBusnIFUBhynLWcKzS +t/Ac5IYp8M7vaGPQtSCKFWGafoaYtMnCdvvMujAWzKNhxnQT5WvvoxXqA/4Ti2Tk08HS6IT7SdEQ +TXlm66r99I0xHnAUrdzeZxNMgRVhvLfZkXdxGYFgu/BYpbWcC/ePIlUnwEsBbTuZDdQdm2NnL9Du +DcpmvJRPpq3t/O5jrFc/ZSXPsoaP0Aj/uHYUbt7lJ+yreLVTubY/6CD50qi+YUbKh4yE8/nxoGib +Ih6BJpsQBJFxwAYf3KDTuVan45gtf4Od34wrnDKOMpTwATwiKp9Dwi7DmDkHOHv8XgBCH/MyJnmD +hPbl8MFREsALHgQjDFSlTC9JxUrRtm5gDWv8a4uFJGS3iQ6rJUdbPM9+Sb3H6QrG2vd+DhcI00iX +0HGS8A85PjRqHH3Y8iKuu2n0M7SmSFXRDw4m6Oy2Cy2nhTXN/VnIn9HNPlopNLk9hM6xZdRZkZFW +dSHBd575euFgndOtBBj0fOtek49TSiIp+EgrPk2GrFt/ywaZWWDYWGWVjUTR939+J399roD1B0y2 +PpxxVJkES/1Y+Zj0 +-----END CERTIFICATE----- + +DigiCert Assured ID Root G2 +=========================== +-----BEGIN CERTIFICATE----- +MIIDljCCAn6gAwIBAgIQC5McOtY5Z+pnI7/Dr5r0SzANBgkqhkiG9w0BAQsFADBlMQswCQYDVQQG +EwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNlcnQuY29tMSQw +IgYDVQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJvb3QgRzIwHhcNMTMwODAxMTIwMDAwWhcNMzgw +MTE1MTIwMDAwWjBlMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQL +ExB3d3cuZGlnaWNlcnQuY29tMSQwIgYDVQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJvb3QgRzIw +ggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDZ5ygvUj82ckmIkzTz+GoeMVSAn61UQbVH +35ao1K+ALbkKz3X9iaV9JPrjIgwrvJUXCzO/GU1BBpAAvQxNEP4HteccbiJVMWWXvdMX0h5i89vq +bFCMP4QMls+3ywPgym2hFEwbid3tALBSfK+RbLE4E9HpEgjAALAcKxHad3A2m67OeYfcgnDmCXRw +VWmvo2ifv922ebPynXApVfSr/5Vh88lAbx3RvpO704gqu52/clpWcTs/1PPRCv4o76Pu2ZmvA9OP +YLfykqGxvYmJHzDNw6YuYjOuFgJ3RFrngQo8p0Quebg/BLxcoIfhG69Rjs3sLPr4/m3wOnyqi+Rn +lTGNAgMBAAGjQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQWBBTO +w0q5mVXyuNtgv6l+vVa1lzan1jANBgkqhkiG9w0BAQsFAAOCAQEAyqVVjOPIQW5pJ6d1Ee88hjZv +0p3GeDgdaZaikmkuOGybfQTUiaWxMTeKySHMq2zNixya1r9I0jJmwYrA8y8678Dj1JGG0VDjA9tz +d29KOVPt3ibHtX2vK0LRdWLjSisCx1BL4GnilmwORGYQRI+tBev4eaymG+g3NJ1TyWGqolKvSnAW +hsI6yLETcDbYz+70CjTVW0z9B5yiutkBclzzTcHdDrEcDcRjvq30FPuJ7KJBDkzMyFdA0G4Dqs0M +jomZmWzwPDCvON9vvKO+KSAnq3T/EyJ43pdSVR6DtVQgA+6uwE9W3jfMw3+qBCe703e4YtsXfJwo +IhNzbM8m9Yop5w== +-----END CERTIFICATE----- + +DigiCert Assured ID Root G3 +=========================== +-----BEGIN CERTIFICATE----- +MIICRjCCAc2gAwIBAgIQC6Fa+h3foLVJRK/NJKBs7DAKBggqhkjOPQQDAzBlMQswCQYDVQQGEwJV +UzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNlcnQuY29tMSQwIgYD +VQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJvb3QgRzMwHhcNMTMwODAxMTIwMDAwWhcNMzgwMTE1 +MTIwMDAwWjBlMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3 +d3cuZGlnaWNlcnQuY29tMSQwIgYDVQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJvb3QgRzMwdjAQ +BgcqhkjOPQIBBgUrgQQAIgNiAAQZ57ysRGXtzbg/WPuNsVepRC0FFfLvC/8QdJ+1YlJfZn4f5dwb +RXkLzMZTCp2NXQLZqVneAlr2lSoOjThKiknGvMYDOAdfVdp+CW7if17QRSAPWXYQ1qAk8C3eNvJs +KTmjQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQWBBTL0L2p4ZgF +UaFNN6KDec6NHSrkhDAKBggqhkjOPQQDAwNnADBkAjAlpIFFAmsSS3V0T8gj43DydXLefInwz5Fy +YZ5eEJJZVrmDxxDnOOlYJjZ91eQ0hjkCMHw2U/Aw5WJjOpnitqM7mzT6HtoQknFekROn3aRukswy +1vUhZscv6pZjamVFkpUBtA== +-----END CERTIFICATE----- + +DigiCert Global Root G2 +======================= +-----BEGIN CERTIFICATE----- +MIIDjjCCAnagAwIBAgIQAzrx5qcRqaC7KGSxHQn65TANBgkqhkiG9w0BAQsFADBhMQswCQYDVQQG +EwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNlcnQuY29tMSAw +HgYDVQQDExdEaWdpQ2VydCBHbG9iYWwgUm9vdCBHMjAeFw0xMzA4MDExMjAwMDBaFw0zODAxMTUx +MjAwMDBaMGExCzAJBgNVBAYTAlVTMRUwEwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3 +dy5kaWdpY2VydC5jb20xIDAeBgNVBAMTF0RpZ2lDZXJ0IEdsb2JhbCBSb290IEcyMIIBIjANBgkq +hkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuzfNNNx7a8myaJCtSnX/RrohCgiN9RlUyfuI2/Ou8jqJ +kTx65qsGGmvPrC3oXgkkRLpimn7Wo6h+4FR1IAWsULecYxpsMNzaHxmx1x7e/dfgy5SDN67sH0NO +3Xss0r0upS/kqbitOtSZpLYl6ZtrAGCSYP9PIUkY92eQq2EGnI/yuum06ZIya7XzV+hdG82MHauV +BJVJ8zUtluNJbd134/tJS7SsVQepj5WztCO7TG1F8PapspUwtP1MVYwnSlcUfIKdzXOS0xZKBgyM +UNGPHgm+F6HmIcr9g+UQvIOlCsRnKPZzFBQ9RnbDhxSJITRNrw9FDKZJobq7nMWxM4MphQIDAQAB +o0IwQDAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBhjAdBgNVHQ4EFgQUTiJUIBiV5uNu +5g/6+rkS7QYXjzkwDQYJKoZIhvcNAQELBQADggEBAGBnKJRvDkhj6zHd6mcY1Yl9PMWLSn/pvtsr +F9+wX3N3KjITOYFnQoQj8kVnNeyIv/iPsGEMNKSuIEyExtv4NeF22d+mQrvHRAiGfzZ0JFrabA0U +WTW98kndth/Jsw1HKj2ZL7tcu7XUIOGZX1NGFdtom/DzMNU+MeKNhJ7jitralj41E6Vf8PlwUHBH +QRFXGU7Aj64GxJUTFy8bJZ918rGOmaFvE7FBcf6IKshPECBV1/MUReXgRPTqh5Uykw7+U0b6LJ3/ +iyK5S9kJRaTepLiaWN0bfVKfjllDiIGknibVb63dDcY3fe0Dkhvld1927jyNxF1WW6LZZm6zNTfl +MrY= +-----END CERTIFICATE----- + +DigiCert Global Root G3 +======================= +-----BEGIN CERTIFICATE----- +MIICPzCCAcWgAwIBAgIQBVVWvPJepDU1w6QP1atFcjAKBggqhkjOPQQDAzBhMQswCQYDVQQGEwJV +UzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNlcnQuY29tMSAwHgYD +VQQDExdEaWdpQ2VydCBHbG9iYWwgUm9vdCBHMzAeFw0xMzA4MDExMjAwMDBaFw0zODAxMTUxMjAw +MDBaMGExCzAJBgNVBAYTAlVTMRUwEwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5k +aWdpY2VydC5jb20xIDAeBgNVBAMTF0RpZ2lDZXJ0IEdsb2JhbCBSb290IEczMHYwEAYHKoZIzj0C +AQYFK4EEACIDYgAE3afZu4q4C/sLfyHS8L6+c/MzXRq8NOrexpu80JX28MzQC7phW1FGfp4tn+6O +YwwX7Adw9c+ELkCDnOg/QW07rdOkFFk2eJ0DQ+4QE2xy3q6Ip6FrtUPOZ9wj/wMco+I+o0IwQDAP +BgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBhjAdBgNVHQ4EFgQUs9tIpPmhxdiuNkHMEWNp +Yim8S8YwCgYIKoZIzj0EAwMDaAAwZQIxAK288mw/EkrRLTnDCgmXc/SINoyIJ7vmiI1Qhadj+Z4y +3maTD/HMsQmP3Wyr+mt/oAIwOWZbwmSNuJ5Q3KjVSaLtx9zRSX8XAbjIho9OjIgrqJqpisXRAL34 +VOKa5Vt8sycX +-----END CERTIFICATE----- + +DigiCert Trusted Root G4 +======================== +-----BEGIN CERTIFICATE----- +MIIFkDCCA3igAwIBAgIQBZsbV56OITLiOQe9p3d1XDANBgkqhkiG9w0BAQwFADBiMQswCQYDVQQG +EwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNlcnQuY29tMSEw +HwYDVQQDExhEaWdpQ2VydCBUcnVzdGVkIFJvb3QgRzQwHhcNMTMwODAxMTIwMDAwWhcNMzgwMTE1 +MTIwMDAwWjBiMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3 +d3cuZGlnaWNlcnQuY29tMSEwHwYDVQQDExhEaWdpQ2VydCBUcnVzdGVkIFJvb3QgRzQwggIiMA0G +CSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQC/5pBzaN675F1KPDAiMGkz7MKnJS7JIT3yithZwuEp +pz1Yq3aaza57G4QNxDAf8xukOBbrVsaXbR2rsnnyyhHS5F/WBTxSD1Ifxp4VpX6+n6lXFllVcq9o +k3DCsrp1mWpzMpTREEQQLt+C8weE5nQ7bXHiLQwb7iDVySAdYyktzuxeTsiT+CFhmzTrBcZe7Fsa +vOvJz82sNEBfsXpm7nfISKhmV1efVFiODCu3T6cw2Vbuyntd463JT17lNecxy9qTXtyOj4DatpGY +QJB5w3jHtrHEtWoYOAMQjdjUN6QuBX2I9YI+EJFwq1WCQTLX2wRzKm6RAXwhTNS8rhsDdV14Ztk6 +MUSaM0C/CNdaSaTC5qmgZ92kJ7yhTzm1EVgX9yRcRo9k98FpiHaYdj1ZXUJ2h4mXaXpI8OCiEhtm +mnTK3kse5w5jrubU75KSOp493ADkRSWJtppEGSt+wJS00mFt6zPZxd9LBADMfRyVw4/3IbKyEbe7 +f/LVjHAsQWCqsWMYRJUadmJ+9oCw++hkpjPRiQfhvbfmQ6QYuKZ3AeEPlAwhHbJUKSWJbOUOUlFH +dL4mrLZBdd56rF+NP8m800ERElvlEFDrMcXKchYiCd98THU/Y+whX8QgUWtvsauGi0/C1kVfnSD8 +oR7FwI+isX4KJpn15GkvmB0t9dmpsh3lGwIDAQABo0IwQDAPBgNVHRMBAf8EBTADAQH/MA4GA1Ud +DwEB/wQEAwIBhjAdBgNVHQ4EFgQU7NfjgtJxXWRM3y5nP+e6mK4cD08wDQYJKoZIhvcNAQEMBQAD +ggIBALth2X2pbL4XxJEbw6GiAI3jZGgPVs93rnD5/ZpKmbnJeFwMDF/k5hQpVgs2SV1EY+CtnJYY +ZhsjDT156W1r1lT40jzBQ0CuHVD1UvyQO7uYmWlrx8GnqGikJ9yd+SeuMIW59mdNOj6PWTkiU0Tr +yF0Dyu1Qen1iIQqAyHNm0aAFYF/opbSnr6j3bTWcfFqK1qI4mfN4i/RN0iAL3gTujJtHgXINwBQy +7zBZLq7gcfJW5GqXb5JQbZaNaHqasjYUegbyJLkJEVDXCLG4iXqEI2FCKeWjzaIgQdfRnGTZ6iah +ixTXTBmyUEFxPT9NcCOGDErcgdLMMpSEDQgJlxxPwO5rIHQw0uA5NBCFIRUBCOhVMt5xSdkoF1BN +5r5N0XWs0Mr7QbhDparTwwVETyw2m+L64kW4I1NsBm9nVX9GtUw/bihaeSbSpKhil9Ie4u1Ki7wb +/UdKDd9nZn6yW0HQO+T0O/QEY+nvwlQAUaCKKsnOeMzV6ocEGLPOr0mIr/OSmbaz5mEP0oUA51Aa +5BuVnRmhuZyxm7EAHu/QD09CbMkKvO5D+jpxpchNJqU1/YldvIViHTLSoCtU7ZpXwdv6EM8Zt4tK +G48BtieVU+i2iW1bvGjUI+iLUaJW+fCmgKDWHrO8Dw9TdSmq6hN35N6MgSGtBxBHEa2HPQfRdbzP +82Z+ +-----END CERTIFICATE----- + +WoSign +====== +-----BEGIN CERTIFICATE----- +MIIFdjCCA16gAwIBAgIQXmjWEXGUY1BWAGjzPsnFkTANBgkqhkiG9w0BAQUFADBVMQswCQYDVQQG +EwJDTjEaMBgGA1UEChMRV29TaWduIENBIExpbWl0ZWQxKjAoBgNVBAMTIUNlcnRpZmljYXRpb24g +QXV0aG9yaXR5IG9mIFdvU2lnbjAeFw0wOTA4MDgwMTAwMDFaFw0zOTA4MDgwMTAwMDFaMFUxCzAJ +BgNVBAYTAkNOMRowGAYDVQQKExFXb1NpZ24gQ0EgTGltaXRlZDEqMCgGA1UEAxMhQ2VydGlmaWNh +dGlvbiBBdXRob3JpdHkgb2YgV29TaWduMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA +vcqNrLiRFVaXe2tcesLea9mhsMMQI/qnobLMMfo+2aYpbxY94Gv4uEBf2zmoAHqLoE1UfcIiePyO +CbiohdfMlZdLdNiefvAA5A6JrkkoRBoQmTIPJYhTpA2zDxIIFgsDcSccf+Hb0v1naMQFXQoOXXDX +2JegvFNBmpGN9J42Znp+VsGQX+axaCA2pIwkLCxHC1l2ZjC1vt7tj/id07sBMOby8w7gLJKA84X5 +KIq0VC6a7fd2/BVoFutKbOsuEo/Uz/4Mx1wdC34FMr5esAkqQtXJTpCzWQ27en7N1QhatH/YHGkR ++ScPewavVIMYe+HdVHpRaG53/Ma/UkpmRqGyZxq7o093oL5d//xWC0Nyd5DKnvnyOfUNqfTq1+ez +EC8wQjchzDBwyYaYD8xYTYO7feUapTeNtqwylwA6Y3EkHp43xP901DfA4v6IRmAR3Qg/UDaruHqk +lWJqbrDKaiFaafPz+x1wOZXzp26mgYmhiMU7ccqjUu6Du/2gd/Tkb+dC221KmYo0SLwX3OSACCK2 +8jHAPwQ+658geda4BmRkAjHXqc1S+4RFaQkAKtxVi8QGRkvASh0JWzko/amrzgD5LkhLJuYwTKVY +yrREgk/nkR4zw7CT/xH8gdLKH3Ep3XZPkiWvHYG3Dy+MwwbMLyejSuQOmbp8HkUff6oZRZb9/D0C +AwEAAaNCMEAwDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFOFmzw7R +8bNLtwYgFP6HEtX2/vs+MA0GCSqGSIb3DQEBBQUAA4ICAQCoy3JAsnbBfnv8rWTjMnvMPLZdRtP1 +LOJwXcgu2AZ9mNELIaCJWSQBnfmvCX0KI4I01fx8cpm5o9dU9OpScA7F9dY74ToJMuYhOZO9sxXq +T2r09Ys/L3yNWC7F4TmgPsc9SnOeQHrAK2GpZ8nzJLmzbVUsWh2eJXLOC62qx1ViC777Y7NhRCOj +y+EaDveaBk3e1CNOIZZbOVtXHS9dCF4Jef98l7VNg64N1uajeeAz0JmWAjCnPv/So0M/BVoG6kQC +2nz4SNAzqfkHx5Xh9T71XXG68pWpdIhhWeO/yloTunK0jF02h+mmxTwTv97QRCbut+wucPrXnbes +5cVAWubXbHssw1abR80LzvobtCHXt2a49CUwi1wNuepnsvRtrtWhnk/Yn+knArAdBtaP4/tIEp9/ +EaEQPkxROpaw0RPxx9gmrjrKkcRpnd8BKWRRb2jaFOwIQZeQjdCygPLPwj2/kWjFgGcexGATVdVh +mVd8upUPYUk6ynW8yQqTP2cOEvIo4jEbwFcW3wh8GcF+Dx+FHgo2fFt+J7x6v+Db9NpSvd4MVHAx +kUOVyLzwPt0JfjBkUO1/AaQzZ01oT74V77D2AhGiGxMlOtzCWfHjXEa7ZywCRuoeSKbmW9m1vFGi +kpbbqsY3Iqb+zCB0oy2pLmvLwIIRIbWTee5Ehr7XHuQe+w== +-----END CERTIFICATE----- + +WoSign China +============ +-----BEGIN CERTIFICATE----- +MIIFWDCCA0CgAwIBAgIQUHBrzdgT/BtOOzNy0hFIjTANBgkqhkiG9w0BAQsFADBGMQswCQYDVQQG +EwJDTjEaMBgGA1UEChMRV29TaWduIENBIExpbWl0ZWQxGzAZBgNVBAMMEkNBIOayg+mAmuagueiv +geS5pjAeFw0wOTA4MDgwMTAwMDFaFw0zOTA4MDgwMTAwMDFaMEYxCzAJBgNVBAYTAkNOMRowGAYD +VQQKExFXb1NpZ24gQ0EgTGltaXRlZDEbMBkGA1UEAwwSQ0Eg5rKD6YCa5qC56K+B5LmmMIICIjAN +BgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA0EkhHiX8h8EqwqzbdoYGTufQdDTc7WU1/FDWiD+k +8H/rD195L4mx/bxjWDeTmzj4t1up+thxx7S8gJeNbEvxUNUqKaqoGXqW5pWOdO2XCld19AXbbQs5 +uQF/qvbW2mzmBeCkTVL829B0txGMe41P/4eDrv8FAxNXUDf+jJZSEExfv5RxadmWPgxDT74wwJ85 +dE8GRV2j1lY5aAfMh09Qd5Nx2UQIsYo06Yms25tO4dnkUkWMLhQfkWsZHWgpLFbE4h4TV2TwYeO5 +Ed+w4VegG63XX9Gv2ystP9Bojg/qnw+LNVgbExz03jWhCl3W6t8Sb8D7aQdGctyB9gQjF+BNdeFy +b7Ao65vh4YOhn0pdr8yb+gIgthhid5E7o9Vlrdx8kHccREGkSovrlXLp9glk3Kgtn3R46MGiCWOc +76DbT52VqyBPt7D3h1ymoOQ3OMdc4zUPLK2jgKLsLl3Az+2LBcLmc272idX10kaO6m1jGx6KyX2m ++Jzr5dVjhU1zZmkR/sgO9MHHZklTfuQZa/HpelmjbX7FF+Ynxu8b22/8DU0GAbQOXDBGVWCvOGU6 +yke6rCzMRh+yRpY/8+0mBe53oWprfi1tWFxK1I5nuPHa1UaKJ/kR8slC/k7e3x9cxKSGhxYzoacX +GKUN5AXlK8IrC6KVkLn9YDxOiT7nnO4fuwECAwEAAaNCMEAwDgYDVR0PAQH/BAQDAgEGMA8GA1Ud +EwEB/wQFMAMBAf8wHQYDVR0OBBYEFOBNv9ybQV0T6GTwp+kVpOGBwboxMA0GCSqGSIb3DQEBCwUA +A4ICAQBqinA4WbbaixjIvirTthnVZil6Xc1bL3McJk6jfW+rtylNpumlEYOnOXOvEESS5iVdT2H6 +yAa+Tkvv/vMx/sZ8cApBWNromUuWyXi8mHwCKe0JgOYKOoICKuLJL8hWGSbueBwj/feTZU7n85iY +r83d2Z5AiDEoOqsuC7CsDCT6eiaY8xJhEPRdF/d+4niXVOKM6Cm6jBAyvd0zaziGfjk9DgNyp115 +j0WKWa5bIW4xRtVZjc8VX90xJc/bYNaBRHIpAlf2ltTW/+op2znFuCyKGo3Oy+dCMYYFaA6eFN0A +kLppRQjbbpCBhqcqBT/mhDn4t/lXX0ykeVoQDF7Va/81XwVRHmyjdanPUIPTfPRm94KNPQx96N97 +qA4bLJyuQHCH2u2nFoJavjVsIE4iYdm8UXrNemHcSxH5/mc0zy4EZmFcV5cjjPOGG0jfKq+nwf/Y +jj4Du9gqsPoUJbJRa4ZDhS4HIxaAjUz7tGM7zMN07RujHv41D198HRaG9Q7DlfEvr10lO1Hm13ZB +ONFLAzkopR6RctR9q5czxNM+4Gm2KHmgCY0c0f9BckgG/Jou5yD5m6Leie2uPAmvylezkolwQOQv +T8Jwg0DXJCxr5wkf09XHwQj02w47HAcLQxGEIYbpgNR12KvxAmLBsX5VYc8T1yaw15zLKYs4SgsO +kI26oQ== +-----END CERTIFICATE----- + +COMODO RSA Certification Authority +================================== +-----BEGIN CERTIFICATE----- +MIIF2DCCA8CgAwIBAgIQTKr5yttjb+Af907YWwOGnTANBgkqhkiG9w0BAQwFADCBhTELMAkGA1UE +BhMCR0IxGzAZBgNVBAgTEkdyZWF0ZXIgTWFuY2hlc3RlcjEQMA4GA1UEBxMHU2FsZm9yZDEaMBgG +A1UEChMRQ09NT0RPIENBIExpbWl0ZWQxKzApBgNVBAMTIkNPTU9ETyBSU0EgQ2VydGlmaWNhdGlv +biBBdXRob3JpdHkwHhcNMTAwMTE5MDAwMDAwWhcNMzgwMTE4MjM1OTU5WjCBhTELMAkGA1UEBhMC +R0IxGzAZBgNVBAgTEkdyZWF0ZXIgTWFuY2hlc3RlcjEQMA4GA1UEBxMHU2FsZm9yZDEaMBgGA1UE +ChMRQ09NT0RPIENBIExpbWl0ZWQxKzApBgNVBAMTIkNPTU9ETyBSU0EgQ2VydGlmaWNhdGlvbiBB +dXRob3JpdHkwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQCR6FSS0gpWsawNJN3Fz0Rn +dJkrN6N9I3AAcbxT38T6KhKPS38QVr2fcHK3YX/JSw8Xpz3jsARh7v8Rl8f0hj4K+j5c+ZPmNHrZ +FGvnnLOFoIJ6dq9xkNfs/Q36nGz637CC9BR++b7Epi9Pf5l/tfxnQ3K9DADWietrLNPtj5gcFKt+ +5eNu/Nio5JIk2kNrYrhV/erBvGy2i/MOjZrkm2xpmfh4SDBF1a3hDTxFYPwyllEnvGfDyi62a+pG +x8cgoLEfZd5ICLqkTqnyg0Y3hOvozIFIQ2dOciqbXL1MGyiKXCJ7tKuY2e7gUYPDCUZObT6Z+pUX +2nwzV0E8jVHtC7ZcryxjGt9XyD+86V3Em69FmeKjWiS0uqlWPc9vqv9JWL7wqP/0uK3pN/u6uPQL +OvnoQ0IeidiEyxPx2bvhiWC4jChWrBQdnArncevPDt09qZahSL0896+1DSJMwBGB7FY79tOi4lu3 +sgQiUpWAk2nojkxl8ZEDLXB0AuqLZxUpaVICu9ffUGpVRr+goyhhf3DQw6KqLCGqR84onAZFdr+C +GCe01a60y1Dma/RMhnEw6abfFobg2P9A3fvQQoh/ozM6LlweQRGBY84YcWsr7KaKtzFcOmpH4MN5 +WdYgGq/yapiqcrxXStJLnbsQ/LBMQeXtHT1eKJ2czL+zUdqnR+WEUwIDAQABo0IwQDAdBgNVHQ4E +FgQUu69+Aj36pvE8hI6t7jiY7NkyMtQwDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8w +DQYJKoZIhvcNAQEMBQADggIBAArx1UaEt65Ru2yyTUEUAJNMnMvlwFTPoCWOAvn9sKIN9SCYPBMt +rFaisNZ+EZLpLrqeLppysb0ZRGxhNaKatBYSaVqM4dc+pBroLwP0rmEdEBsqpIt6xf4FpuHA1sj+ +nq6PK7o9mfjYcwlYRm6mnPTXJ9OV2jeDchzTc+CiR5kDOF3VSXkAKRzH7JsgHAckaVd4sjn8OoSg +tZx8jb8uk2IntznaFxiuvTwJaP+EmzzV1gsD41eeFPfR60/IvYcjt7ZJQ3mFXLrrkguhxuhoqEwW +sRqZCuhTLJK7oQkYdQxlqHvLI7cawiiFwxv/0Cti76R7CZGYZ4wUAc1oBmpjIXUDgIiKboHGhfKp +pC3n9KUkEEeDys30jXlYsQab5xoq2Z0B15R97QNKyvDb6KkBPvVWmckejkk9u+UJueBPSZI9FoJA +zMxZxuY67RIuaTxslbH9qh17f4a+Hg4yRvv7E491f0yLS0Zj/gA0QHDBw7mh3aZw4gSzQbzpgJHq +ZJx64SIDqZxubw5lT2yHh17zbqD5daWbQOhTsiedSrnAdyGN/4fy3ryM7xfft0kL0fJuMAsaDk52 +7RH89elWsn2/x20Kk4yl0MC2Hb46TpSi125sC8KKfPog88Tk5c0NqMuRkrF8hey1FGlmDoLnzc7I +LaZRfyHBNVOFBkpdn627G190 +-----END CERTIFICATE----- + +USERTrust RSA Certification Authority +===================================== +-----BEGIN CERTIFICATE----- +MIIF3jCCA8agAwIBAgIQAf1tMPyjylGoG7xkDjUDLTANBgkqhkiG9w0BAQwFADCBiDELMAkGA1UE +BhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0plcnNleSBDaXR5MR4wHAYDVQQK +ExVUaGUgVVNFUlRSVVNUIE5ldHdvcmsxLjAsBgNVBAMTJVVTRVJUcnVzdCBSU0EgQ2VydGlmaWNh +dGlvbiBBdXRob3JpdHkwHhcNMTAwMjAxMDAwMDAwWhcNMzgwMTE4MjM1OTU5WjCBiDELMAkGA1UE +BhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0plcnNleSBDaXR5MR4wHAYDVQQK +ExVUaGUgVVNFUlRSVVNUIE5ldHdvcmsxLjAsBgNVBAMTJVVTRVJUcnVzdCBSU0EgQ2VydGlmaWNh +dGlvbiBBdXRob3JpdHkwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQCAEmUXNg7D2wiz +0KxXDXbtzSfTTK1Qg2HiqiBNCS1kCdzOiZ/MPans9s/B3PHTsdZ7NygRK0faOca8Ohm0X6a9fZ2j +Y0K2dvKpOyuR+OJv0OwWIJAJPuLodMkYtJHUYmTbf6MG8YgYapAiPLz+E/CHFHv25B+O1ORRxhFn +RghRy4YUVD+8M/5+bJz/Fp0YvVGONaanZshyZ9shZrHUm3gDwFA66Mzw3LyeTP6vBZY1H1dat//O ++T23LLb2VN3I5xI6Ta5MirdcmrS3ID3KfyI0rn47aGYBROcBTkZTmzNg95S+UzeQc0PzMsNT79uq +/nROacdrjGCT3sTHDN/hMq7MkztReJVni+49Vv4M0GkPGw/zJSZrM233bkf6c0Plfg6lZrEpfDKE +Y1WJxA3Bk1QwGROs0303p+tdOmw1XNtB1xLaqUkL39iAigmTYo61Zs8liM2EuLE/pDkP2QKe6xJM +lXzzawWpXhaDzLhn4ugTncxbgtNMs+1b/97lc6wjOy0AvzVVdAlJ2ElYGn+SNuZRkg7zJn0cTRe8 +yexDJtC/QV9AqURE9JnnV4eeUB9XVKg+/XRjL7FQZQnmWEIuQxpMtPAlR1n6BB6T1CZGSlCBst6+ +eLf8ZxXhyVeEHg9j1uliutZfVS7qXMYoCAQlObgOK6nyTJccBz8NUvXt7y+CDwIDAQABo0IwQDAd +BgNVHQ4EFgQUU3m/WqorSs9UgOHYm8Cd8rIDZsswDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQF +MAMBAf8wDQYJKoZIhvcNAQEMBQADggIBAFzUfA3P9wF9QZllDHPFUp/L+M+ZBn8b2kMVn54CVVeW +FPFSPCeHlCjtHzoBN6J2/FNQwISbxmtOuowhT6KOVWKR82kV2LyI48SqC/3vqOlLVSoGIG1VeCkZ +7l8wXEskEVX/JJpuXior7gtNn3/3ATiUFJVDBwn7YKnuHKsSjKCaXqeYalltiz8I+8jRRa8YFWSQ +Eg9zKC7F4iRO/Fjs8PRF/iKz6y+O0tlFYQXBl2+odnKPi4w2r78NBc5xjeambx9spnFixdjQg3IM +8WcRiQycE0xyNN+81XHfqnHd4blsjDwSXWXavVcStkNr/+XeTWYRUc+ZruwXtuhxkYzeSf7dNXGi +FSeUHM9h4ya7b6NnJSFd5t0dCy5oGzuCr+yDZ4XUmFF0sbmZgIn/f3gZXHlKYC6SQK5MNyosycdi +yA5d9zZbyuAlJQG03RoHnHcAP9Dc1ew91Pq7P8yF1m9/qS3fuQL39ZeatTXaw2ewh0qpKJ4jjv9c +J2vhsE/zB+4ALtRZh8tSQZXq9EfX7mRBVXyNWQKV3WKdwrnuWih0hKWbt5DHDAff9Yk2dDLWKMGw +sAvgnEzDHNb842m1R0aBL6KCq9NjRHDEjf8tM7qtj3u1cIiuPhnPQCjY/MiQu12ZIvVS5ljFH4gx +Q+6IHdfGjjxDah2nGN59PRbxYvnKkKj9 +-----END CERTIFICATE----- + +USERTrust ECC Certification Authority +===================================== +-----BEGIN CERTIFICATE----- +MIICjzCCAhWgAwIBAgIQXIuZxVqUxdJxVt7NiYDMJjAKBggqhkjOPQQDAzCBiDELMAkGA1UEBhMC +VVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0plcnNleSBDaXR5MR4wHAYDVQQKExVU +aGUgVVNFUlRSVVNUIE5ldHdvcmsxLjAsBgNVBAMTJVVTRVJUcnVzdCBFQ0MgQ2VydGlmaWNhdGlv +biBBdXRob3JpdHkwHhcNMTAwMjAxMDAwMDAwWhcNMzgwMTE4MjM1OTU5WjCBiDELMAkGA1UEBhMC +VVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0plcnNleSBDaXR5MR4wHAYDVQQKExVU +aGUgVVNFUlRSVVNUIE5ldHdvcmsxLjAsBgNVBAMTJVVTRVJUcnVzdCBFQ0MgQ2VydGlmaWNhdGlv +biBBdXRob3JpdHkwdjAQBgcqhkjOPQIBBgUrgQQAIgNiAAQarFRaqfloI+d61SRvU8Za2EurxtW2 +0eZzca7dnNYMYf3boIkDuAUU7FfO7l0/4iGzzvfUinngo4N+LZfQYcTxmdwlkWOrfzCjtHDix6Ez +nPO/LlxTsV+zfTJ/ijTjeXmjQjBAMB0GA1UdDgQWBBQ64QmG1M8ZwpZ2dEl23OA1xmNjmjAOBgNV +HQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAKBggqhkjOPQQDAwNoADBlAjA2Z6EWCNzklwBB +HU6+4WMBzzuqQhFkoJ2UOQIReVx7Hfpkue4WQrO/isIJxOzksU0CMQDpKmFHjFJKS04YcPbWRNZu +9YO6bVi9JNlWSOrvxKJGgYhqOkbRqZtNyWHa0V1Xahg= +-----END CERTIFICATE----- + +GlobalSign ECC Root CA - R4 +=========================== +-----BEGIN CERTIFICATE----- +MIIB4TCCAYegAwIBAgIRKjikHJYKBN5CsiilC+g0mAIwCgYIKoZIzj0EAwIwUDEkMCIGA1UECxMb +R2xvYmFsU2lnbiBFQ0MgUm9vdCBDQSAtIFI0MRMwEQYDVQQKEwpHbG9iYWxTaWduMRMwEQYDVQQD +EwpHbG9iYWxTaWduMB4XDTEyMTExMzAwMDAwMFoXDTM4MDExOTAzMTQwN1owUDEkMCIGA1UECxMb +R2xvYmFsU2lnbiBFQ0MgUm9vdCBDQSAtIFI0MRMwEQYDVQQKEwpHbG9iYWxTaWduMRMwEQYDVQQD +EwpHbG9iYWxTaWduMFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEuMZ5049sJQ6fLjkZHAOkrprl +OQcJFspjsbmG+IpXwVfOQvpzofdlQv8ewQCybnMO/8ch5RikqtlxP6jUuc6MHaNCMEAwDgYDVR0P +AQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFFSwe61FuOJAf/sKbvu+M8k8o4TV +MAoGCCqGSM49BAMCA0gAMEUCIQDckqGgE6bPA7DmxCGXkPoUVy0D7O48027KqGx2vKLeuwIgJ6iF +JzWbVsaj8kfSt24bAgAXqmemFZHe+pTsewv4n4Q= +-----END CERTIFICATE----- + +GlobalSign ECC Root CA - R5 +=========================== +-----BEGIN CERTIFICATE----- +MIICHjCCAaSgAwIBAgIRYFlJ4CYuu1X5CneKcflK2GwwCgYIKoZIzj0EAwMwUDEkMCIGA1UECxMb +R2xvYmFsU2lnbiBFQ0MgUm9vdCBDQSAtIFI1MRMwEQYDVQQKEwpHbG9iYWxTaWduMRMwEQYDVQQD +EwpHbG9iYWxTaWduMB4XDTEyMTExMzAwMDAwMFoXDTM4MDExOTAzMTQwN1owUDEkMCIGA1UECxMb +R2xvYmFsU2lnbiBFQ0MgUm9vdCBDQSAtIFI1MRMwEQYDVQQKEwpHbG9iYWxTaWduMRMwEQYDVQQD +EwpHbG9iYWxTaWduMHYwEAYHKoZIzj0CAQYFK4EEACIDYgAER0UOlvt9Xb/pOdEh+J8LttV7HpI6 +SFkc8GIxLcB6KP4ap1yztsyX50XUWPrRd21DosCHZTQKH3rd6zwzocWdTaRvQZU4f8kehOvRnkmS +h5SHDDqFSmafnVmTTZdhBoZKo0IwQDAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAd +BgNVHQ4EFgQUPeYpSJvqB8ohREom3m7e0oPQn1kwCgYIKoZIzj0EAwMDaAAwZQIxAOVpEslu28Yx +uglB4Zf4+/2a4n0Sye18ZNPLBSWLVtmg515dTguDnFt2KaAJJiFqYgIwcdK1j1zqO+F4CYWodZI7 +yFz9SO8NdCKoCOJuxUnOxwy8p2Fp8fc74SrL+SvzZpA3 +-----END CERTIFICATE----- diff -Nru ruby-excon-0.33.0/debian/changelog ruby-excon-0.45.1/debian/changelog --- ruby-excon-0.33.0/debian/changelog 2014-06-27 15:03:27.000000000 +0000 +++ ruby-excon-0.45.1/debian/changelog 2015-04-28 04:52:50.000000000 +0000 @@ -1,3 +1,23 @@ +ruby-excon (0.45.1-2) unstable; urgency=medium + + * Re-upload to unstable + + -- Pirate Praveen Tue, 28 Apr 2015 10:22:47 +0530 + +ruby-excon (0.45.1-1) experimental; urgency=medium + + * New upstream release. + + -- Pirate Praveen Fri, 10 Apr 2015 23:10:48 +0530 + +ruby-excon (0.38.0-1) experimental; urgency=medium + + * New upstream release. + * Add myself to uploaders. + * Bump standards version to 3.9.6 (no changes). + + -- Pirate Praveen Sat, 22 Nov 2014 13:48:37 +0530 + ruby-excon (0.33.0-2) unstable; urgency=medium * Team upload diff -Nru ruby-excon-0.33.0/debian/control ruby-excon-0.45.1/debian/control --- ruby-excon-0.33.0/debian/control 2014-05-20 09:24:16.000000000 +0000 +++ ruby-excon-0.45.1/debian/control 2014-11-22 08:10:01.000000000 +0000 @@ -2,11 +2,11 @@ Section: ruby Priority: optional Maintainer: Debian Ruby Extras Maintainers -Uploaders: Laurent Bigonville +Uploaders: Laurent Bigonville , Pirate Praveen Build-Depends: debhelper (>= 7.0.50~), gem2deb (>= 0.3.0~), rake, ruby-rspec, ruby-chronic, ruby-shindo, ruby-sinatra, ruby-open4, ruby-activesupport, ruby-delorean, ruby-eventmachine, unicorn -Standards-Version: 3.9.5 +Standards-Version: 3.9.6 Vcs-Git: git://anonscm.debian.org/pkg-ruby-extras/ruby-excon.git Vcs-Browser: http://anonscm.debian.org/gitweb/?p=pkg-ruby-extras/ruby-excon.git;a=summary Homepage: https://github.com/geemus/excon diff -Nru ruby-excon-0.33.0/excon.gemspec ruby-excon-0.45.1/excon.gemspec --- ruby-excon-0.33.0/excon.gemspec 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/excon.gemspec 2015-04-10 16:36:11.000000000 +0000 @@ -13,8 +13,8 @@ ## If your rubyforge_project name is different, then edit it and comment out ## the sub! line in the Rakefile s.name = 'excon' - s.version = '0.33.0' - s.date = '2014-04-15' + s.version = '0.45.1' + s.date = '2015-03-27' s.rubyforge_project = 'excon' ## Make sure your summary is short. The description may be as long @@ -27,7 +27,7 @@ ## a custom homepage, consider using your GitHub URL or the like. s.authors = ["dpiddy (Dan Peterson)", "geemus (Wesley Beary)", "nextmat (Matt Sanders)"] s.email = 'geemus@gmail.com' - s.homepage = 'https://github.com/geemus/excon' + s.homepage = 'https://github.com/excon/excon' s.license = 'MIT' ## This gets added to the $LOAD_PATH so that 'lib/NAME.rb' can be required as @@ -56,12 +56,13 @@ # s.add_development_dependency('DEVDEPNAME', [">= 1.1.0", "< 2.0.0"]) s.add_development_dependency('activesupport') s.add_development_dependency('delorean') - s.add_development_dependency('eventmachine') + s.add_development_dependency('eventmachine', '>= 1.0.4') s.add_development_dependency('open4') s.add_development_dependency('rake') s.add_development_dependency('rdoc') s.add_development_dependency('shindo') s.add_development_dependency('sinatra') + s.add_development_dependency('json', '>= 1.8.2') ## Leave this section as-is. It will be automatically generated from the ## contents of your Git repository via the gemspec task. DO NOT REMOVE @@ -100,6 +101,7 @@ lib/excon/connection.rb lib/excon/constants.rb lib/excon/errors.rb + lib/excon/extensions/uri.rb lib/excon/headers.rb lib/excon/middlewares/base.rb lib/excon/middlewares/decompress.rb @@ -110,6 +112,7 @@ lib/excon/middlewares/mock.rb lib/excon/middlewares/redirect_follower.rb lib/excon/middlewares/response_parser.rb + lib/excon/pretty_printer.rb lib/excon/response.rb lib/excon/socket.rb lib/excon/ssl_socket.rb @@ -119,6 +122,8 @@ tests/authorization_header_tests.rb tests/bad_tests.rb tests/basic_tests.rb + tests/data/127.0.0.1.cert.crt + tests/data/127.0.0.1.cert.key tests/data/excon.cert.crt tests/data/excon.cert.key tests/data/xs @@ -140,11 +145,14 @@ tests/rackups/deflater.ru tests/rackups/proxy.ru tests/rackups/query_string.ru + tests/rackups/redirecting.ru tests/rackups/request_headers.ru tests/rackups/request_methods.ru tests/rackups/response_header.ru tests/rackups/ssl.ru + tests/rackups/ssl_mismatched_cn.ru tests/rackups/ssl_verify_peer.ru + tests/rackups/streaming.ru tests/rackups/thread_safety.ru tests/rackups/timeout.ru tests/rackups/webrick_patch.rb diff -Nru ruby-excon-0.33.0/Gemfile ruby-excon-0.45.1/Gemfile --- ruby-excon-0.33.0/Gemfile 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/Gemfile 2015-04-10 16:36:11.000000000 +0000 @@ -5,6 +5,7 @@ gem 'jruby-openssl', :platform => :jruby gem 'unicorn', :platforms => [:mri, :rbx] gem 'rubysl', '~> 2.0', :platform => :rbx +gem 'rack', '~> 1.6' # group :benchmark do # gem 'em-http-request' diff -Nru ruby-excon-0.33.0/Gemfile.lock ruby-excon-0.45.1/Gemfile.lock --- ruby-excon-0.33.0/Gemfile.lock 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/Gemfile.lock 2015-04-10 16:36:11.000000000 +0000 @@ -1,7 +1,7 @@ PATH remote: . specs: - excon (0.33.0) + excon (0.45.1) GEM remote: http://rubygems.org/ @@ -13,23 +13,23 @@ chronic (0.6.7) delorean (2.0.0) chronic - eventmachine (1.0.0) - eventmachine (1.0.0-java) + eventmachine (1.0.4) + eventmachine (1.0.4-java) ffi2-generators (0.1.1) formatador (0.2.3) i18n (0.6.0) jruby-openssl (0.8.8) bouncy-castle-java (>= 1.5.0147) - json (1.7.3) - json (1.7.3-java) - kgio (2.8.0) + json (1.8.2) + json (1.8.2-java) + kgio (2.9.2) minitest (4.7.5) multi_json (1.3.6) open4 (1.3.0) - rack (1.4.1) + rack (1.6.0) rack-protection (1.2.0) rack - raindrops (0.11.0) + raindrops (0.13.0) rake (0.9.2.2) rdoc (3.12) json (~> 1.4) @@ -245,7 +245,7 @@ rack-protection (~> 1.2) tilt (~> 1.3, >= 1.3.3) tilt (1.3.3) - unicorn (4.6.3) + unicorn (4.8.3) kgio (~> 2.6) rack raindrops (~> 0.7) @@ -257,10 +257,12 @@ DEPENDENCIES activesupport delorean - eventmachine + eventmachine (>= 1.0.4) excon! jruby-openssl + json (>= 1.8.2) open4 + rack (~> 1.6) rake rdoc rubysl (~> 2.0) diff -Nru ruby-excon-0.33.0/lib/excon/connection.rb ruby-excon-0.45.1/lib/excon/connection.rb --- ruby-excon-0.33.0/lib/excon/connection.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/connection.rb 2015-04-10 16:36:11.000000000 +0000 @@ -35,7 +35,8 @@ # @param [Hash] params One or more optional params # @option params [String] :body Default text to be sent over a socket. Only used if :body absent in Connection#request params # @option params [Hash] :headers The default headers to supply in a request. Only used if params[:headers] is not supplied to Connection#request - # @option params [String] :host The destination host's reachable DNS name or IP, in the form of a String + # @option params [String] :host The destination host's reachable DNS name or IP, in the form of a String. IPv6 addresses must be wrapped (e.g. [::1]). See URI#host. + # @option params [String] :hostname Same as host, but usable for socket connections. IPv6 addresses must not be wrapped (e.g. ::1). See URI#hostname. # @option params [String] :path Default path; appears after 'scheme://host:port/'. Only used if params[:path] is not supplied to Connection#request # @option params [Fixnum] :port The port on which to connect, to the destination host # @option params [Hash] :query Default query; appended to the 'scheme://host:port/path/' in the form of '?key=value'. Will only be used if params[:query] is not supplied to Connection#request @@ -57,36 +58,15 @@ params = validate_params(:connection, params) @data.merge!(params) - unless @data[:scheme] == UNIX - no_proxy_env = ENV["no_proxy"] || ENV["NO_PROXY"] || "" - no_proxy_list = no_proxy_env.scan(/\*?\.?([^\s,:]+)(?::(\d+))?/i).map { |s| [s[0], s[1]] } - unless no_proxy_list.index { |h| /(^|\.)#{h[0]}$/.match(@data[:host]) && (h[1].nil? || h[1].to_i == @data[:port]) } - if @data[:scheme] == HTTPS && (ENV.has_key?('https_proxy') || ENV.has_key?('HTTPS_PROXY')) - @data[:proxy] = setup_proxy(ENV['https_proxy'] || ENV['HTTPS_PROXY']) - elsif (ENV.has_key?('http_proxy') || ENV.has_key?('HTTP_PROXY')) - @data[:proxy] = setup_proxy(ENV['http_proxy'] || ENV['HTTP_PROXY']) - elsif @data.has_key?(:proxy) - @data[:proxy] = setup_proxy(@data[:proxy]) - end - end - end + setup_proxy - if @data[:proxy] - @data[:headers]['Proxy-Connection'] ||= 'Keep-Alive' - # https credentials happen in handshake - if @data[:scheme] == 'http' && (@data[:proxy][:user] || @data[:proxy][:password]) - user, pass = Utils.unescape_form(@data[:proxy][:user].to_s), Utils.unescape_form(@data[:proxy][:password].to_s) - auth = ['' << user.to_s << ':' << pass.to_s].pack('m').delete(Excon::CR_NL) - @data[:headers]['Proxy-Authorization'] = 'Basic ' << auth - end + if ENV.has_key?('EXCON_STANDARD_INSTRUMENTOR') + @data[:instrumentor] = Excon::StandardInstrumentor end - if ENV.has_key?('EXCON_DEBUG') || ENV.has_key?('EXCON_STANDARD_INSTRUMENTOR') + if @data[:debug] || ENV.has_key?('EXCON_DEBUG') + @data[:debug_request] = @data[:debug_response] = true @data[:instrumentor] = Excon::StandardInstrumentor - - if ENV.has_key?('EXCON_DEBUG') - @data[:debug_request] = @data[:debug_reponse] = true - end end # Use Basic Auth if url contains a login @@ -126,7 +106,7 @@ socket.data = datum # start with "METHOD /path" request = datum[:method].to_s.upcase << ' ' - if datum[:proxy] + if datum[:proxy] && datum[:scheme] != HTTPS request << datum[:scheme] << '://' << datum[:host] << port_string(datum) end request << datum[:path] @@ -151,13 +131,6 @@ end end - if datum[:response_block] - datum[:headers]['TE'] = 'trailers' - else - datum[:headers]['TE'] = 'trailers, deflate, gzip' - end - datum[:headers]['Connection'] = datum[:persistent] ? 'TE' : 'TE, close' - # add headers to request datum[:headers].each do |key, values| [values].flatten.each do |value| @@ -186,8 +159,8 @@ if body.respond_to?(:binmode) body.binmode end - if body.respond_to?(:pos=) - body.pos = 0 + if body.respond_to?(:rewind) + body.rewind rescue nil end while chunk = body.read(datum[:chunk_size]) socket.write(chunk) @@ -207,8 +180,10 @@ end def response_call(datum) + # ensure response_block is yielded to and body is empty from middlewares if datum.has_key?(:response_block) && !datum[:response][:body].empty? response_body = datum[:response][:body].dup + datum[:response][:body] = '' content_length = remaining = response_body.bytesize while remaining > 0 datum[:response_block].call(response_body.slice!(0, [datum[:chunk_size], remaining].min), [remaining - datum[:chunk_size], 0].max, content_length) @@ -248,17 +223,6 @@ datum[:response_block] = Proc.new end - if datum[:idempotent] - if datum[:request_block] - Excon.display_warning('Excon requests with a :request_block can not be :idempotent.') - datum[:idempotent] = false - end - if datum[:pipeline] - Excon.display_warning("Excon requests can not be :idempotent when pipelining.") - datum[:idempotent] = false - end - end - datum[:connection] = self datum[:stack] = datum[:middlewares].map do |middleware| @@ -273,7 +237,7 @@ if datum[:persistent] if key = datum[:response][:headers].keys.detect {|k| k.casecmp('Connection') == 0 } - if split_header_value(datum[:response][:headers][key]).any? {|t| t.casecmp('close') == 0 } + if datum[:response][:headers][key].casecmp('close') == 0 reset end end @@ -309,7 +273,7 @@ if @data[:persistent] if key = responses.last[:headers].keys.detect {|k| k.casecmp('Connection') == 0 } - if split_header_value(responses.last[:headers][key]).any? {|t| t.casecmp('close') == 0 } + if responses.last[:headers][key].casecmp('close') == 0 reset end end @@ -384,9 +348,9 @@ def validate_params(validation, params) valid_keys = case validation when :connection - valid_connection_keys(params) + Excon::VALID_CONNECTION_KEYS when :request - valid_request_keys(params) + Excon::VALID_REQUEST_KEYS end invalid_keys = params.keys - valid_keys unless invalid_keys.empty? @@ -395,6 +359,12 @@ #params = params.dup #invalid_keys.each {|key| params.delete(key) } end + + if validation == :connection && params.key?(:host) && !params.key?(:hostname) + Excon.display_warning('hostname is missing! For IPv6 support, provide both host and hostname: Excon::Connection#new(:host => uri.host, :hostname => uri.hostname, ...).') + params[:hostname] = params[:host] + end + params end @@ -410,35 +380,89 @@ end def socket - sockets[@socket_key] ||= if @data[:scheme] == HTTPS - Excon::SSLSocket.new(@data) - elsif @data[:scheme] == UNIX + unix_proxy = @data[:proxy] ? @data[:proxy][:scheme] == UNIX : false + sockets[@socket_key] ||= if @data[:scheme] == UNIX || unix_proxy Excon::UnixSocket.new(@data) + elsif @data[:scheme] == HTTPS + Excon::SSLSocket.new(@data) else Excon::Socket.new(@data) end end def sockets - Thread.current[:_excon_sockets] ||= {} + if @data[:thread_safe_sockets] + Thread.current[:_excon_sockets] ||= {} + else + @_excon_sockets ||= {} + end end - def setup_proxy(proxy) - case proxy - when String - uri = URI.parse(proxy) - unless uri.host and uri.port and uri.scheme + def setup_proxy + if @data[:disable_proxy] + if @data[:proxy] + raise ArgumentError, "`:disable_proxy` parameter and `:proxy` parameter cannot both be set at the same time." + end + return + end + + unless @data[:scheme] == UNIX + if no_proxy_env = ENV["no_proxy"] || ENV["NO_PROXY"] + no_proxy_list = no_proxy_env.scan(/\*?\.?([^\s,:]+)(?::(\d+))?/i).map { |s| [s[0], s[1]] } + end + + unless no_proxy_env && no_proxy_list.index { |h| /(^|\.)#{h[0]}$/.match(@data[:host]) && (h[1].nil? || h[1].to_i == @data[:port]) } + if @data[:scheme] == HTTPS && (ENV.has_key?('https_proxy') || ENV.has_key?('HTTPS_PROXY')) + @data[:proxy] = ENV['https_proxy'] || ENV['HTTPS_PROXY'] + elsif (ENV.has_key?('http_proxy') || ENV.has_key?('HTTP_PROXY')) + @data[:proxy] = ENV['http_proxy'] || ENV['HTTP_PROXY'] + end + end + + case @data[:proxy] + when nil + @data.delete(:proxy) + when Hash + # no processing needed + when String, URI + uri = @data[:proxy].is_a?(String) ? URI.parse(@data[:proxy]) : @data[:proxy] + @data[:proxy] = { + :host => uri.host, + :hostname => uri.hostname, + # path is only sensible for a Unix socket proxy + :path => uri.scheme == UNIX ? uri.path : nil, + :port => uri.port, + :scheme => uri.scheme, + } + if uri.password + @data[:proxy][:password] = uri.password + end + if uri.user + @data[:proxy][:user] = uri.user + end + if @data[:proxy][:scheme] == UNIX + if @data[:proxy][:host] + raise ArgumentError, "The `:host` parameter should not be set for `unix://` proxies.\n" + + "When supplying a `unix://` URI, it should start with `unix:/` or `unix:///`." + end + else + unless uri.host && uri.port && uri.scheme + raise Excon::Errors::ProxyParseError, "Proxy is invalid" + end + end + else raise Excon::Errors::ProxyParseError, "Proxy is invalid" end - { - :host => uri.host, - :password => uri.password, - :port => uri.port, - :scheme => uri.scheme, - :user => uri.user - } - else - proxy + + if @data.has_key?(:proxy) && @data[:scheme] == 'http' + @data[:headers]['Proxy-Connection'] ||= 'Keep-Alive' + # https credentials happen in handshake + if @data[:proxy].has_key?(:user) || @data[:proxy].has_key?(:password) + user, pass = Utils.unescape_form(@data[:proxy][:user].to_s), Utils.unescape_form(@data[:proxy][:password].to_s) + auth = ['' << user << ':' << pass].pack('m').delete(Excon::CR_NL) + @data[:headers]['Proxy-Authorization'] = 'Basic ' << auth + end + end end end end diff -Nru ruby-excon-0.33.0/lib/excon/constants.rb ruby-excon-0.45.1/lib/excon/constants.rb --- ruby-excon-0.33.0/lib/excon/constants.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/constants.rb 2015-04-10 16:36:11.000000000 +0000 @@ -1,6 +1,6 @@ module Excon - VERSION = '0.33.0' + VERSION = '0.45.1' CR_NL = "\r\n" @@ -31,6 +31,8 @@ USER_AGENT = 'excon/' << VERSION + VERSIONS = USER_AGENT + ' (' << RUBY_PLATFORM << ') ruby/' << RUBY_VERSION + VALID_REQUEST_KEYS = [ :body, :captures, @@ -54,20 +56,24 @@ :response_block, :retries_remaining, # used internally :retry_limit, + :versions, :write_timeout ] VALID_CONNECTION_KEYS = VALID_REQUEST_KEYS + [ :ciphers, :client_key, + :client_key_pass, :client_cert, :certificate, :certificate_path, + :disable_proxy, :private_key, :private_key_path, :connect_timeout, :family, :host, + :hostname, :omit_default_port, :nonblock, :reuseaddr, @@ -77,9 +83,14 @@ :scheme, :socket, :ssl_ca_file, + :ssl_ca_path, + :ssl_cert_store, + :ssl_verify_callback, :ssl_verify_peer, + :ssl_verify_peer_host, :ssl_version, :tcp_nodelay, + :thread_safe_sockets, :uri_parser, :user ] @@ -95,5 +106,37 @@ module WaitWritable; end end end + # these come last as they rely on the above + DEFAULTS = { + :chunk_size => CHUNK_SIZE || DEFAULT_CHUNK_SIZE, + :ciphers => 'HIGH:!SSLv2:!aNULL:!eNULL:!3DES', + :connect_timeout => 60, + :debug_request => false, + :debug_response => false, + :headers => { + 'User-Agent' => USER_AGENT + }, + :idempotent => false, + :instrumentor_name => 'excon', + :middlewares => [ + Excon::Middleware::ResponseParser, + Excon::Middleware::Expects, + Excon::Middleware::Idempotent, + Excon::Middleware::Instrumentor, + Excon::Middleware::Mock + ], + :mock => false, + :nonblock => true, + :omit_default_port => false, + :persistent => false, + :read_timeout => 60, + :retry_limit => DEFAULT_RETRY_LIMIT, + :ssl_verify_peer => true, + :tcp_nodelay => false, + :thread_safe_sockets => true, + :uri_parser => URI, + :versions => VERSIONS, + :write_timeout => 60 + } end diff -Nru ruby-excon-0.33.0/lib/excon/errors.rb ruby-excon-0.45.1/lib/excon/errors.rb --- ruby-excon-0.33.0/lib/excon/errors.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/errors.rb 2015-04-10 16:36:11.000000000 +0000 @@ -3,13 +3,14 @@ class Error < StandardError; end class StubNotFound < StandardError; end + class InvalidStub < StandardError; end class SocketError < Error attr_reader :socket_error - def initialize(socket_error=nil) + def initialize(socket_error=Excon::Error.new) if socket_error.message =~ /certificate verify failed/ - super("Unable to verify certificate, please set `Excon.defaults[:ssl_ca_path] = path_to_certs`, `ENV['SSL_CERT_DIR'] = path_to_certs`, `Excon.defaults[:ssl_ca_file] = path_to_file`, `ENV['SSL_CERT_FILE'] = path_to_file` or `Excon.defaults[:ssl_verify_peer] = false` (less secure).") + super("Unable to verify certificate, please set `Excon.defaults[:ssl_ca_path] = path_to_certs`, `ENV['SSL_CERT_DIR'] = path_to_certs`, `Excon.defaults[:ssl_ca_file] = path_to_file`, `ENV['SSL_CERT_FILE'] = path_to_file`, `Excon.defaults[:ssl_verify_callback] = callback` (see OpenSSL::SSL::SSLContext#verify_callback), or `Excon.defaults[:ssl_verify_peer] = false` (less secure).") else super("#{socket_error.message} (#{socket_error.class})") end @@ -35,7 +36,7 @@ @response = response end end - + # HTTP Error classes class Informational < HTTPStatusError; end class Success < HTTPStatusError; end @@ -78,6 +79,7 @@ class RequestedRangeNotSatisfiable < ClientError; end # 416 class ExpectationFailed < ClientError; end # 417 class UnprocessableEntity < ClientError; end # 422 + class TooManyRequests < ClientError; end # 429 class InternalServerError < ServerError; end # 500 class NotImplemented < ServerError; end # 501 class BadGateway < ServerError; end # 502 @@ -122,6 +124,7 @@ 416 => [Excon::Errors::RequestedRangeNotSatisfiable, 'Request Range Not Satisfiable'], 417 => [Excon::Errors::ExpectationFailed, 'Expectation Failed'], 422 => [Excon::Errors::UnprocessableEntity, 'Unprocessable Entity'], + 429 => [Excon::Errors::TooManyRequests, 'Too Many Requests'], 500 => [Excon::Errors::InternalServerError, 'InternalServerError'], 501 => [Excon::Errors::NotImplemented, 'Not Implemented'], 502 => [Excon::Errors::BadGateway, 'Bad Gateway'], @@ -129,24 +132,23 @@ 504 => [Excon::Errors::GatewayTimeout, 'Gateway Timeout'] } - error, message = @errors[response[:status]] || [Excon::Errors::HTTPStatusError, 'Unknown'] + error_class, error_message = @errors[response[:status]] || [Excon::Errors::HTTPStatusError, 'Unknown'] - message = "Expected(#{request[:expects].inspect}) <=> Actual(#{response[:status]} #{message})" + message = StringIO.new + message.puts("Expected(#{request[:expects].inspect}) <=> Actual(#{response[:status]} #{error_message})") if request[:debug_request] - # scrub authorization - req = request.dup - req.reject! {|key, value| [:connection, :stack].include?(key)} - if req.has_key?(:headers) && req[:headers].has_key?('Authorization') - req[:headers] = req[:headers].dup - req[:headers]['Authorization'] = REDACTED - end - message << "\n request => #{req.inspect}" + message.puts('excon.error.request') + Excon::PrettyPrinter.pp(message, request) end - message << "\n response => #{response.inspect}" if request[:debug_response] + if request[:debug_response] + message.puts('excon.error.response') + Excon::PrettyPrinter.pp(message, response.data) + end - error.new(message, request, response) + message.rewind + error_class.new(message.read, request, response) end end diff -Nru ruby-excon-0.33.0/lib/excon/extensions/uri.rb ruby-excon-0.45.1/lib/excon/extensions/uri.rb --- ruby-excon-0.33.0/lib/excon/extensions/uri.rb 1970-01-01 00:00:00.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/extensions/uri.rb 2015-04-10 16:36:11.000000000 +0000 @@ -0,0 +1,33 @@ +# TODO: Remove this monkey patch once ruby 1.9.3+ is the minimum supported version. +# +# This patch backports URI#hostname to ruby 1.9.2 and older. +# URI#hostname is used for IPv6 support in Excon. +# +# URI#hostname was added in stdlib in v1_9_3_0 in this commit: +# https://github.com/ruby/ruby/commit/5fd45a4b79dd26f9e7b6dc41142912df911e4d7d +# +# Addressable::URI is also an URI parser accepted in some parts of Excon. +# Addressable::URI#hostname was added in addressable-2.3.5+ in this commit: +# https://github.com/sporkmonger/addressable/commit/1b94abbec1f914d5f707c92a10efbb9e69aab65e +# +# Users who want to use Addressable::URI to parse URIs must upgrade to 2.3.5 or newer. +require 'uri' +unless URI("http://foo/bar").respond_to?(:hostname) + module URI + class Generic + # extract the host part of the URI and unwrap brackets for IPv6 addresses. + # + # This method is same as URI::Generic#host except + # brackets for IPv6 (and future IP) addresses are removed. + # + # u = URI("http://[::1]/bar") + # p u.hostname #=> "::1" + # p u.host #=> "[::1]" + # + def hostname + v = self.host + /\A\[(.*)\]\z/ =~ v ? $1 : v + end + end + end +end diff -Nru ruby-excon-0.33.0/lib/excon/headers.rb ruby-excon-0.45.1/lib/excon/headers.rb --- ruby-excon-0.33.0/lib/excon/headers.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/headers.rb 2015-04-10 16:36:11.000000000 +0000 @@ -14,103 +14,69 @@ alias_method :raw_include?, :include? alias_method :raw_key?, :key? alias_method :raw_member?, :member? + alias_method :raw_merge, :merge + alias_method :raw_merge!, :merge! alias_method :raw_rehash, :rehash alias_method :raw_store, :store alias_method :raw_values_at, :values_at + def initialize + @downcased = {} + end + def [](key) - if should_delegate?(key) - @downcased[key.downcase] - else - raw_reader(key) - end + @downcased[key.to_s.downcase] end alias_method :[]=, :store def []=(key, value) raw_writer(key, value) - unless @downcased.nil? - @downcased[key.downcase] = value - end + @downcased[key.to_s.downcase] = value end if SENTINEL.respond_to? :assoc def assoc(obj) - if should_delegate?(obj) - @downcased.assoc(obj.downcase) - else - raw_assoc(obj) - end + @downcased.assoc(obj.downcase) end end def delete(key, &proc) - if should_delegate?(key) - @downcased.delete(key.downcase, &proc) - else - raw_delete(key, &proc) - end + raw_delete(key, &proc) + @downcased.delete(key.to_s.downcase, &proc) end def fetch(key, default = nil, &proc) - if should_delegate?(key) - if proc - @downcased.fetch(key.downcase, &proc) - else - @downcased.fetch(key.downcase, default) - end + if proc + @downcased.fetch(key.to_s.downcase, &proc) else - if proc - raw_fetch(key, &proc) - else - raw_fetch(key, default) - end + @downcased.fetch(key.to_s.downcase, default) end end alias_method :has_key?, :key? alias_method :has_key?, :member? def has_key?(key) - raw_has_key?(key) || begin - index_case_insensitive - @downcased.has_key?(key.downcase) - end + raw_key?(key) || @downcased.has_key?(key.to_s.downcase) end - def rehash - raw_rehash - if @downcased - @downcased.rehash - end + def merge(other_hash) + self.dup.merge!(other_hash) end - def values_at(*keys) - raw_values_at(*keys).zip(keys).map do |v, k| - if v.nil? - index_case_insensitive - @downcased[k.downcase] - end + def merge!(other_hash) + other_hash.each do |key, value| + self[key] = value end + raw_merge!(other_hash) end - private - - def should_delegate?(key) - if raw_has_key?(key) - false - else - index_case_insensitive - true - end + def rehash + @downcased.rehash + raw_rehash end - def index_case_insensitive - if @downcased.nil? - @downcased = {} - each_pair do |key, value| - @downcased[key.downcase] = value - end - end + def values_at(*keys) + @downcased.values_at(*keys.map {|key| key.to_s.downcase}) end end diff -Nru ruby-excon-0.33.0/lib/excon/middlewares/idempotent.rb ruby-excon-0.45.1/lib/excon/middlewares/idempotent.rb --- ruby-excon-0.33.0/lib/excon/middlewares/idempotent.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/middlewares/idempotent.rb 2015-04-10 16:36:11.000000000 +0000 @@ -2,13 +2,27 @@ module Middleware class Idempotent < Excon::Middleware::Base def error_call(datum) + if datum[:idempotent] + if datum.has_key?(:request_block) + if datum[:request_block].respond_to?(:rewind) + datum[:request_block].rewind + else + Excon.display_warning('Excon requests with a :request_block must implement #rewind in order to be :idempotent.') + datum[:idempotent] = false + end + end + if datum.has_key?(:pipeline) + Excon.display_warning("Excon requests can not be :idempotent when pipelining.") + datum[:idempotent] = false + end + end + if datum[:idempotent] && [Excon::Errors::Timeout, Excon::Errors::SocketError, Excon::Errors::HTTPStatusError].any? {|ex| datum[:error].kind_of?(ex) } && datum[:retries_remaining] > 1 # reduces remaining retries, reset connection, and restart request_call datum[:retries_remaining] -= 1 connection = datum.delete(:connection) - request_keys = Utils.valid_request_keys(datum) - datum.reject! {|key, _| !request_keys.include?(key) } + datum.reject! {|key, _| !Excon::VALID_REQUEST_KEYS.include?(key) } connection.request(datum) else @stack.error_call(datum) diff -Nru ruby-excon-0.33.0/lib/excon/middlewares/mock.rb ruby-excon-0.45.1/lib/excon/middlewares/mock.rb --- ruby-excon-0.33.0/lib/excon/middlewares/mock.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/middlewares/mock.rb 2015-04-10 16:36:11.000000000 +0000 @@ -4,7 +4,7 @@ def request_call(datum) if datum[:mock] # convert File/Tempfile body to string before matching: - unless datum[:body].nil? || datum[:body].is_a?(String) + if datum[:body].respond_to?(:read) if datum[:body].respond_to?(:binmode) datum[:body].binmode end @@ -12,6 +12,8 @@ datum[:body].rewind end datum[:body] = datum[:body].read + elsif !datum[:body].nil? && !datum[:body].is_a?(String) + raise Excon::Errors::InvalidStub.new("Request body should be a string or an IO object. #{datum[:body].class} provided") end if stub = Excon.stub_for(datum) @@ -35,7 +37,10 @@ end else # if we reach here no stubs matched - raise(Excon::Errors::StubNotFound.new('no stubs matched ' << datum.inspect)) + message = StringIO.new + message.puts('no stubs matched') + Excon::PrettyPrinter.pp(message, datum) + raise(Excon::Errors::StubNotFound.new(message.string)) end end diff -Nru ruby-excon-0.33.0/lib/excon/middlewares/redirect_follower.rb ruby-excon-0.45.1/lib/excon/middlewares/redirect_follower.rb --- ruby-excon-0.33.0/lib/excon/middlewares/redirect_follower.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/middlewares/redirect_follower.rb 2015-04-10 16:36:11.000000000 +0000 @@ -2,9 +2,9 @@ module Middleware class RedirectFollower < Excon::Middleware::Base def response_call(datum) - if datum.has_key?(:response) && [:get, :head].include?(datum[:method].to_s.downcase.to_sym) + if datum.has_key?(:response) case datum[:response][:status] - when 301, 302, 303, 307 + when 301, 302, 303, 307, 308 uri_parser = datum[:uri_parser] || Excon.defaults[:uri_parser] _, location = datum[:response][:headers].detect do |key, value| key.casecmp('Location') == 0 @@ -12,11 +12,19 @@ uri = uri_parser.parse(location) # delete old/redirect response - datum.delete(:response) + response = datum.delete(:response) params = datum.dup - params.delete(:stack) params.delete(:connection) + params.delete(:password) + params.delete(:stack) + params.delete(:user) + + if [301, 302, 303].include?(response[:status]) + params[:method] = :get + params.delete(:body) + params[:headers].delete('Content-Length') + end params[:headers] = datum[:headers].dup params[:headers].delete('Authorization') params[:headers].delete('Proxy-Connection') @@ -25,13 +33,15 @@ params.merge!( :scheme => uri.scheme || datum[:scheme], :host => uri.host || datum[:host], + :hostname => uri.hostname || datum[:hostname], :port => uri.port || datum[:port], :path => uri.path, - :query => uri.query, - :user => (Utils.unescape_uri(uri.user) if uri.user), - :password => (Utils.unescape_uri(uri.password) if uri.password) + :query => uri.query ) + params.merge!(:user => Utils.unescape_uri(uri.user)) if uri.user + params.merge!(:password => Utils.unescape_uri(uri.password)) if uri.password + response = Excon::Connection.new(params).request datum.merge!({:response => response.data}) else diff -Nru ruby-excon-0.33.0/lib/excon/middlewares/response_parser.rb ruby-excon-0.45.1/lib/excon/middlewares/response_parser.rb --- ruby-excon-0.33.0/lib/excon/middlewares/response_parser.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/middlewares/response_parser.rb 2015-04-10 16:36:11.000000000 +0000 @@ -4,24 +4,6 @@ def response_call(datum) unless datum.has_key?(:response) datum = Excon::Response.parse(datum[:connection].send(:socket), datum) - - # only requests without a :response_block add 'deflate, gzip' to the TE header. - unless datum[:response_block] - if key = datum[:response][:headers].keys.detect {|k| k.casecmp('Transfer-Encoding') == 0 } - encodings = Utils.split_header_value(datum[:response][:headers][key]) - if encoding = encodings.last - if encoding.casecmp('deflate') == 0 - # assume inflate omits header - datum[:response][:body] = Zlib::Inflate.new(-Zlib::MAX_WBITS).inflate(datum[:response][:body]) - encodings.pop - elsif encoding.casecmp('gzip') == 0 || encoding.casecmp('x-gzip') == 0 - datum[:response][:body] = Zlib::GzipReader.new(StringIO.new(datum[:response][:body])).read - encodings.pop - end - datum[:response][:headers][key] = encodings.join(', ') - end - end - end end @stack.response_call(datum) end diff -Nru ruby-excon-0.33.0/lib/excon/pretty_printer.rb ruby-excon-0.45.1/lib/excon/pretty_printer.rb --- ruby-excon-0.33.0/lib/excon/pretty_printer.rb 1970-01-01 00:00:00.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/pretty_printer.rb 2015-04-10 16:36:11.000000000 +0000 @@ -0,0 +1,45 @@ +module Excon + class PrettyPrinter + def self.pp(io, datum, indent=0) + datum = datum.dup + + # reduce duplication/noise of output + unless datum.is_a?(Excon::Headers) + datum.delete(:connection) + datum.delete(:stack) + + if datum.has_key?(:headers) && datum[:headers].has_key?('Authorization') + datum[:headers] = datum[:headers].dup + datum[:headers]['Authorization'] = REDACTED + end + + if datum.has_key?(:password) + datum[:password] = REDACTED + end + end + + indent += 2 + max_key_length = datum.keys.map {|key| key.inspect.length}.max + datum.keys.sort_by {|key| key.to_s}.each do |key| + value = datum[key] + io.write("#{' ' * indent}#{key.inspect.ljust(max_key_length)} => ") + case value + when Array + io.puts("[") + value.each do |v| + io.puts("#{' ' * indent} #{v.inspect}") + end + io.write("#{' ' * indent}]") + when Hash + io.puts("{") + self.pp(io, value, indent) + io.write("#{' ' * indent}}") + else + io.write("#{value.inspect}") + end + io.puts + end + indent -= 2 + end + end +end diff -Nru ruby-excon-0.33.0/lib/excon/response.rb ruby-excon-0.45.1/lib/excon/response.rb --- ruby-excon-0.33.0/lib/excon/response.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/response.rb 2015-04-10 16:36:11.000000000 +0000 @@ -22,6 +22,12 @@ def status @data[:status] end + def reason_phrase=(new_reason_phrase) + @data[:reason_phrase] = new_reason_phrase + end + def reason_phrase + @data[:reason_phrase] + end def remote_ip=(new_remote_ip) @data[:remote_ip] = new_remote_ip end @@ -37,18 +43,28 @@ def self.parse(socket, datum) # this will discard any trailing lines from the previous response if any. - until match = /^HTTP\/\d+\.\d+\s(\d{3})\s/.match(socket.readline); end - status = match[1].to_i + begin + line = socket.readline + end until status = line[9, 3].to_i + + reason_phrase = line[13..-3] # -3 strips the trailing "\r\n" datum[:response] = { :body => '', :headers => Excon::Headers.new, :status => status, - :remote_ip => socket.respond_to?(:remote_ip) && socket.remote_ip, - :local_port => socket.respond_to?(:local_port) && socket.local_port, - :local_address => socket.respond_to?(:local_address) && socket.local_address + :reason_phrase => reason_phrase } + unix_proxy = datum[:proxy] ? datum[:proxy][:scheme] == UNIX : false + unless datum[:scheme] == UNIX || unix_proxy + datum[:response].merge!( + :remote_ip => socket.remote_ip, + :local_port => socket.local_port, + :local_address => socket.local_address + ) + end + parse_headers(socket, datum) unless (['HEAD', 'CONNECT'].include?(datum[:method].to_s.upcase)) || NO_ENTITY.include?(datum[:response][:status]) @@ -57,13 +73,11 @@ encodings = Utils.split_header_value(datum[:response][:headers][key]) if (encoding = encodings.last) && encoding.casecmp('chunked') == 0 transfer_encoding_chunked = true - encodings.pop - datum[:response][:headers][key] = encodings.join(', ') - end - end - unless transfer_encoding_chunked - if key = datum[:response][:headers].keys.detect {|k| k.casecmp('Content-Length') == 0 } - content_length = datum[:response][:headers][key].to_i + if encodings.length == 1 + datum[:response][:headers].delete(key) + else + datum[:response][:headers][key] = encodings[0...-1].join(', ') + end end end @@ -76,36 +90,61 @@ end if transfer_encoding_chunked - # 2 == "\r\n".length if response_block - while (chunk_size = socket.readline.chop!.to_i(16)) > 0 - response_block.call(socket.read(chunk_size + 2).chop!, nil, nil) + while (chunk_size = socket.readline.chomp!.to_i(16)) > 0 + while chunk_size > 0 + chunk = socket.read(chunk_size) + chunk_size -= chunk.bytesize + response_block.call(chunk, nil, nil) + end + new_line_size = 2 # 2 == "\r\n".length + while new_line_size > 0 + new_line_size -= socket.read(new_line_size).length + end end else - while (chunk_size = socket.readline.chop!.to_i(16)) > 0 - datum[:response][:body] << socket.read(chunk_size + 2).chop! + while (chunk_size = socket.readline.chomp!.to_i(16)) > 0 + while chunk_size > 0 + chunk = socket.read(chunk_size) + chunk_size -= chunk.bytesize + datum[:response][:body] << chunk + end + new_line_size = 2 # 2 == "\r\n".length + while new_line_size > 0 + new_line_size -= socket.read(new_line_size).length + end end end parse_headers(socket, datum) # merge trailers into headers - elsif remaining = content_length - if response_block - while remaining > 0 - response_block.call(socket.read([datum[:chunk_size], remaining].min), [remaining - datum[:chunk_size], 0].max, content_length) - remaining -= datum[:chunk_size] - end - else - while remaining > 0 - datum[:response][:body] << socket.read([datum[:chunk_size], remaining].min) - remaining -= datum[:chunk_size] - end - end else - if response_block - while chunk = socket.read(datum[:chunk_size]) - response_block.call(chunk, nil, nil) + if key = datum[:response][:headers].keys.detect {|k| k.casecmp('Content-Length') == 0 } + content_length = datum[:response][:headers][key].to_i + end + + if remaining = content_length + if response_block + while remaining > 0 + chunk = socket.read([datum[:chunk_size], remaining].min) + response_block.call(chunk, [remaining - chunk.bytesize, 0].max, content_length) + remaining -= chunk.bytesize + end + else + while remaining > 0 + chunk = socket.read([datum[:chunk_size], remaining].min) + datum[:response][:body] << chunk + remaining -= chunk.bytesize + end end else - datum[:response][:body] << socket.read + if response_block + while chunk = socket.read(datum[:chunk_size]) + response_block.call(chunk, nil, nil) + end + else + while chunk = socket.read(datum[:chunk_size]) + datum[:response][:body] << chunk + end + end end end end @@ -114,7 +153,7 @@ def self.parse_headers(socket, datum) last_key = nil - until (data = socket.readline.chop!).empty? + until (data = socket.readline.chomp!).empty? if !data.lstrip!.nil? raise Excon::Errors::ResponseParseError, 'malformed header' unless last_key # append to last_key's last value @@ -131,9 +170,10 @@ def initialize(params={}) @data = { - :body => '', - :headers => Excon::Headers.new + :body => '' }.merge(params) + @data[:headers] = Excon::Headers.new.merge!(params[:headers] || {}) + @body = @data[:body] @headers = @data[:headers] @status = @data[:status] @@ -151,6 +191,10 @@ data end + def pp + Excon::PrettyPrinter.pp($stdout, @data) + end + # Retrieve a specific header value. Header names are treated case-insensitively. # @param [String] name Header name def get_header(name) diff -Nru ruby-excon-0.33.0/lib/excon/socket.rb ruby-excon-0.45.1/lib/excon/socket.rb --- ruby-excon-0.33.0/lib/excon/socket.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/socket.rb 2015-04-10 16:36:11.000000000 +0000 @@ -10,6 +10,7 @@ Excon.display_warning('Excon::Socket#params is deprecated use Excon::Socket#data instead.') @data end + def params=(new_params) Excon.display_warning('Excon::Socket#params= is deprecated use Excon::Socket#data= instead.') @data = new_params @@ -17,149 +18,75 @@ attr_reader :remote_ip - def_delegators(:@socket, :close, :close) + def_delegators(:@socket, :close) def initialize(data = {}) @data = data @nonblock = data[:nonblock] @read_buffer = '' @eof = false - connect end - def read(max_length=nil) + def read(max_length = nil) if @eof return max_length ? nil : '' elsif @nonblock - begin - if max_length - until @read_buffer.length >= max_length - @read_buffer << @socket.read_nonblock(max_length - @read_buffer.length) - end - else - while true - @read_buffer << @socket.read_nonblock(@data[:chunk_size]) - end - end - rescue OpenSSL::SSL::SSLError => error - if error.message == 'read would block' - if IO.select([@socket], nil, nil, @data[:read_timeout]) - retry - else - raise(Excon::Errors::Timeout.new("read timeout reached")) - end - else - raise(error) - end - rescue Errno::EAGAIN, Errno::EWOULDBLOCK, IO::WaitReadable - if IO.select([@socket], nil, nil, @data[:read_timeout]) - retry - else - raise(Excon::Errors::Timeout.new("read timeout reached")) - end - rescue EOFError - @eof = true - end - - if max_length - if @read_buffer.empty? - nil # EOF met at beginning - else - @read_buffer.slice!(0, max_length) - end - else - # read until EOFError, so return everything - @read_buffer.slice!(0, @read_buffer.length) - end + read_nonblock(max_length) else - begin - Timeout.timeout(@data[:read_timeout]) do - @socket.read(max_length) - end - rescue Timeout::Error - raise Excon::Errors::Timeout.new('read timeout reached') - end + read_block(max_length) end end def readline - if @eof - raise EOFError, 'end of file reached' - else - line = '' - if @nonblock - while char = read(1) - line << char - break if char == $/ - end - raise EOFError, 'end of file reached' if line.empty? + return legacy_readline if RUBY_VERSION.to_f <= 1.8_7 + buffer = '' + begin + buffer << @socket.read_nonblock(1) while buffer[-1] != "\n" + buffer + rescue Errno::EAGAIN, Errno::EWOULDBLOCK, IO::WaitReadable + if timeout_reached('read') + raise_timeout_error('read') else - begin - Timeout.timeout(@data[:read_timeout]) do - line = @socket.readline - end - rescue Timeout::Error - raise Excon::Errors::Timeout.new('read timeout reached') + retry + end + rescue OpenSSL::SSL::SSLError => e + if e.message == 'read would block' + if timeout_reached('read') + raise_timeout_error('read') + else + retry end + else + raise(error) end - line + end + end + + def legacy_readline + begin + Timeout.timeout(@data[:read_timeout]) do + @socket.readline + end + rescue Timeout::Error + raise Excon::Errors::Timeout.new('read timeout reached') end end def write(data) if @nonblock - if FORCE_ENC - data.force_encoding('BINARY') - end - while true - written = nil - begin - # I wish that this API accepted a start position, then we wouldn't - # have to slice data when there is a short write. - written = @socket.write_nonblock(data) - rescue OpenSSL::SSL::SSLError, Errno::EAGAIN, Errno::EWOULDBLOCK, IO::WaitWritable => error - if error.is_a?(OpenSSL::SSL::SSLError) && error.message != 'write would block' - raise error - else - if IO.select(nil, [@socket], nil, @data[:write_timeout]) - retry - else - raise Excon::Errors::Timeout.new('write timeout reached') - end - end - end - - # Fast, common case. - break if written == data.size - - # This takes advantage of the fact that most ruby implementations - # have Copy-On-Write strings. Thusly why requesting a subrange - # of data, we actually don't copy data because the new string - # simply references a subrange of the original. - data = data[written, data.size] - end + write_nonblock(data) else - begin - Timeout.timeout(@data[:write_timeout]) do - @socket.write(data) - end - rescue Timeout::Error - raise(Excon::Errors::Timeout.new('write timeout reached')) - end + write_block(data) end end - def local_port - ::Socket.unpack_sockaddr_in(@socket.to_io.getsockname)[0] - rescue ArgumentError => e - raise unless e.message == 'not an AF_INET/AF_INET6 sockaddr' + def local_address + unpacked_sockaddr[1] end - def local_address - ::Socket.unpack_sockaddr_in(@socket.to_io.getsockname)[1] - rescue ArgumentError => e - raise unless e.message == 'not an AF_INET/AF_INET6 sockaddr' + def local_port + unpacked_sockaddr[0] end private @@ -170,10 +97,10 @@ if @data[:proxy] family = @data[:proxy][:family] || ::Socket::Constants::AF_UNSPEC - args = [@data[:proxy][:host], @data[:proxy][:port], family, ::Socket::Constants::SOCK_STREAM] + args = [@data[:proxy][:hostname], @data[:proxy][:port], family, ::Socket::Constants::SOCK_STREAM] else family = @data[:family] || ::Socket::Constants::AF_UNSPEC - args = [@data[:host], @data[:port], family, ::Socket::Constants::SOCK_STREAM] + args = [@data[:hostname], @data[:port], family, ::Socket::Constants::SOCK_STREAM] end if RUBY_VERSION >= '1.9.2' && defined?(RUBY_ENGINE) && RUBY_ENGINE == 'ruby' args << nil << nil << false # no reverse lookup @@ -183,6 +110,11 @@ addrinfo.each do |_, port, _, ip, a_family, s_type| @remote_ip = ip + # already succeeded on previous addrinfo + if @socket + break + end + # nonblocking connect begin sockaddr = ::Socket.sockaddr_in(port, ip) @@ -196,46 +128,31 @@ end end - begin - Timeout.timeout(@data[:connect_timeout]) do - if @nonblock - socket.connect_nonblock(sockaddr) - else - socket.connect(sockaddr) - end - end - rescue Timeout::Error - raise Excon::Errors::Timeout.new('connect timeout reached') + if @nonblock + socket.connect_nonblock(sockaddr) + else + socket.connect(sockaddr) end - @socket = socket - break rescue Errno::EINPROGRESS unless IO.select(nil, [socket], nil, @data[:connect_timeout]) - raise(Excon::Errors::Timeout.new("connect timeout reached")) + raise(Excon::Errors::Timeout.new('connect timeout reached')) end begin socket.connect_nonblock(sockaddr) - @socket = socket - break rescue Errno::EISCONN @socket = socket - break rescue SystemCallError => exception socket.close rescue nil - next end rescue SystemCallError => exception socket.close rescue nil if socket - next end end - unless @socket - # this will be our last encountered exception - raise exception - end + # this will be our last encountered exception + fail exception unless @socket if @data[:tcp_nodelay] @socket.setsockopt(::Socket::IPPROTO_TCP, @@ -244,5 +161,150 @@ end end + def read_nonblock(max_length) + begin + if max_length + until @read_buffer.length >= max_length + @read_buffer << @socket.read_nonblock(max_length - @read_buffer.length) + end + else + loop do + @read_buffer << @socket.read_nonblock(@data[:chunk_size]) + end + end + rescue OpenSSL::SSL::SSLError => error + if error.message == 'read would block' + if timeout_reached('read') + raise_timeout_error('read') + else + retry + end + else + raise(error) + end + rescue Errno::EAGAIN, Errno::EWOULDBLOCK, IO::WaitReadable + if @read_buffer.empty? + # if we didn't read anything, try again... + if timeout_reached('read') + raise_timeout_error('read') + else + retry + end + end + rescue EOFError + @eof = true + end + + if max_length + if @read_buffer.empty? + nil # EOF met at beginning + else + @read_buffer.slice!(0, max_length) + end + else + # read until EOFError, so return everything + @read_buffer.slice!(0, @read_buffer.length) + end + end + + def read_block(max_length) + @socket.read(max_length) + rescue OpenSSL::SSL::SSLError => error + if error.message == 'read would block' + if timeout_reached('read') + raise_timeout_error('read') + else + retry + end + else + raise(error) + end + rescue Errno::EAGAIN, Errno::EWOULDBLOCK, IO::WaitReadable + if @read_buffer.empty? + if timeout_reached('read') + raise_timeout_error('read') + else + retry + end + end + rescue EOFError + @eof = true + end + + def write_nonblock(data) + if FORCE_ENC + data.force_encoding('BINARY') + end + loop do + written = nil + begin + # I wish that this API accepted a start position, then we wouldn't + # have to slice data when there is a short write. + written = @socket.write_nonblock(data) + rescue Errno::EFAULT + if OpenSSL::OPENSSL_LIBRARY_VERSION.split(' ')[1] == '1.0.2' + msg = "The version of OpenSSL this ruby is built against (1.0.2) has a vulnerability + which causes a fault. For more, see https://github.com/excon/excon/issues/467" + raise SecurityError.new(msg) + else + raise error + end + rescue OpenSSL::SSL::SSLError, Errno::EAGAIN, Errno::EWOULDBLOCK, IO::WaitWritable => error + if error.is_a?(OpenSSL::SSL::SSLError) && error.message != 'write would block' + raise error + else + if timeout_reached('write') + raise_timeout_error('write') + else + retry + end + end + end + + # Fast, common case. + break if written == data.size + + # This takes advantage of the fact that most ruby implementations + # have Copy-On-Write strings. Thusly why requesting a subrange + # of data, we actually don't copy data because the new string + # simply references a subrange of the original. + data = data[written, data.size] + end + end + + def write_block(data) + @socket.write(data) + rescue OpenSSL::SSL::SSLError, Errno::EAGAIN, Errno::EWOULDBLOCK, IO::WaitWritable => error + if error.is_a?(OpenSSL::SSL::SSLError) && error.message != 'write would block' + raise error + else + if timeout_reached('write') + raise_timeout_error('write') + else + retry + end + end + end + + def timeout_reached(type) + if type == 'read' + args = [[@socket], nil, nil, @data[:read_timeout]] + else + args = [nil, [@socket], nil, @data[:write_timeout]] + end + IO.select(*args) ? nil : true + end + + def raise_timeout_error(type) + fail Excon::Errors::Timeout.new("#{type} timeout reached") + end + + def unpacked_sockaddr + @unpacked_sockaddr ||= ::Socket.unpack_sockaddr_in(@socket.to_io.getsockname) + rescue ArgumentError => e + unless e.message == 'not an AF_INET/AF_INET6 sockaddr' + raise + end + end end end diff -Nru ruby-excon-0.33.0/lib/excon/ssl_socket.rb ruby-excon-0.45.1/lib/excon/ssl_socket.rb --- ruby-excon-0.33.0/lib/excon/ssl_socket.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/ssl_socket.rb 2015-04-10 16:36:11.000000000 +0000 @@ -1,9 +1,8 @@ module Excon class SSLSocket < Socket - - HAVE_NONBLOCK = [:connect_nonblock, :read_nonblock, :write_nonblock].all? {|m| + HAVE_NONBLOCK = [:connect_nonblock, :read_nonblock, :write_nonblock].all? do |m| OpenSSL::SSL::SSLSocket.public_method_defined?(m) - } + end def initialize(data = {}) super @@ -16,6 +15,7 @@ if defined?(OpenSSL::SSL::OP_DONT_INSERT_EMPTY_FRAGMENTS) ssl_context_options &= ~OpenSSL::SSL::OP_DONT_INSERT_EMPTY_FRAGMENTS end + if defined?(OpenSSL::SSL::OP_NO_COMPRESSION) ssl_context_options |= OpenSSL::SSL::OP_NO_COMPRESSION end @@ -25,28 +25,40 @@ if @data[:ssl_version] ssl_context.ssl_version = @data[:ssl_version] end + if @data[:ssl_verify_peer] # turn verification on ssl_context.verify_mode = OpenSSL::SSL::VERIFY_PEER - if ca_path = ENV['SSL_CERT_DIR'] || @data[:ssl_ca_path] - ssl_context.ca_path = ca_path - elsif ca_file = ENV['SSL_CERT_FILE'] || @data[:ssl_ca_file] + if ca_file = @data[:ssl_ca_file] || ENV['SSL_CERT_FILE'] ssl_context.ca_file = ca_file - else # attempt default, fallback to bundled + end + if ca_path = @data[:ssl_ca_path] || ENV['SSL_CERT_DIR'] + ssl_context.ca_path = ca_path + end + if cert_store = @data[:ssl_cert_store] + ssl_context.cert_store = cert_store + end + + # no defaults, fallback to bundled + unless ca_file || ca_path || cert_store ssl_context.cert_store = OpenSSL::X509::Store.new ssl_context.cert_store.set_default_paths # workaround issue #257 (JRUBY-6970) ca_file = DEFAULT_CA_FILE - ca_file.gsub!(/^jar:/, "") if ca_file =~ /^jar:file:\// + ca_file.gsub!(/^jar:/, '') if ca_file =~ /^jar:file:\// begin ssl_context.cert_store.add_file(ca_file) - rescue => e - Excon.display_warning("Excon unable to add file to cert store, ignoring: #{ca_file}\n[#{e.class}] #{e.message}") + rescue + Excon.display_warning("Excon unable to add file to cert store, ignoring: #{ca_file}\n[#{$!.class}] #{$!.message}") end end + + if verify_callback = @data[:ssl_verify_callback] + ssl_context.verify_callback = verify_callback + end else # turn verification off ssl_context.verify_mode = OpenSSL::SSL::VERIFY_NONE @@ -55,22 +67,31 @@ # maintain existing API certificate_path = @data[:client_cert] || @data[:certificate_path] private_key_path = @data[:client_key] || @data[:private_key_path] + private_key_pass = @data[:client_key_pass] || @data[:private_key_pass] if certificate_path && private_key_path ssl_context.cert = OpenSSL::X509::Certificate.new(File.read(certificate_path)) - ssl_context.key = OpenSSL::PKey::RSA.new(File.read(private_key_path)) - elsif @data.has_key?(:certificate) && @data.has_key?(:private_key) + if OpenSSL::PKey.respond_to? :read + ssl_context.key = OpenSSL::PKey.read(File.read(private_key_path), private_key_pass) + else + ssl_context.key = OpenSSL::PKey::RSA.new(File.read(private_key_path), private_key_pass) + end + elsif @data.key?(:certificate) && @data.key?(:private_key) ssl_context.cert = OpenSSL::X509::Certificate.new(@data[:certificate]) - ssl_context.key = OpenSSL::PKey::RSA.new(@data[:private_key]) + if OpenSSL::PKey.respond_to? :read + ssl_context.key = OpenSSL::PKey.read(@data[:private_key], private_key_pass) + else + ssl_context.key = OpenSSL::PKey::RSA.new(@data[:private_key], private_key_pass) + end end if @data[:proxy] - request = 'CONNECT ' << @data[:host] << port_string(@data) << Excon::HTTP_1_1 + request = 'CONNECT ' << @data[:host] << port_string(@data.merge(:omit_default_port => false)) << Excon::HTTP_1_1 request << 'Host: ' << @data[:host] << port_string(@data) << Excon::CR_NL if @data[:proxy][:password] || @data[:proxy][:user] auth = ['' << @data[:proxy][:user].to_s << ':' << @data[:proxy][:password].to_s].pack('m').delete(Excon::CR_NL) - request << "Proxy-Authorization: Basic " << auth << Excon::CR_NL + request << 'Proxy-Authorization: Basic ' << auth << Excon::CR_NL end request << 'Proxy-Connection: Keep-Alive' << Excon::CR_NL @@ -81,43 +102,38 @@ @socket.write(request) # eat the proxy's connection response - Excon::Response.parse(@socket, { :expects => 200, :method => "CONNECT" }) + Excon::Response.parse(self, :expects => 200, :method => 'CONNECT') end # convert Socket to OpenSSL::SSL::SSLSocket @socket = OpenSSL::SSL::SSLSocket.new(@socket, ssl_context) @socket.sync_close = true - + # Server Name Indication (SNI) RFC 3546 if @socket.respond_to?(:hostname=) @socket.hostname = @data[:host] end - + begin - Timeout.timeout(@data[:connect_timeout]) do - if @nonblock - while true - begin - @socket.connect_nonblock - break # connect succeeded - rescue OpenSSL::SSL::SSLError => error - # would block, rescue and retry as select is non-helpful - unless error.message == 'read would block' - raise error - end - end - end - else - @socket.connect + if @nonblock + begin + @socket.connect_nonblock + rescue IO::WaitReadable + IO.select([@socket]) + retry end + else + @socket.connect end - rescue Timeout::Error + rescue OpenSSL::SSL::SSLError + raise + rescue raise Excon::Errors::Timeout.new('connect timeout reached') end # verify connection if @data[:ssl_verify_peer] - @socket.post_connection_check(@data[:host]) + @socket.post_connection_check(@data[:ssl_verify_peer_host] || @data[:host]) end @socket @@ -130,6 +146,5 @@ @nonblock = HAVE_NONBLOCK && @nonblock super end - end end diff -Nru ruby-excon-0.33.0/lib/excon/standard_instrumentor.rb ruby-excon-0.45.1/lib/excon/standard_instrumentor.rb --- ruby-excon-0.33.0/lib/excon/standard_instrumentor.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/standard_instrumentor.rb 2015-04-10 16:36:11.000000000 +0000 @@ -2,14 +2,23 @@ class StandardInstrumentor def self.instrument(name, params = {}, &block) params = params.dup + + # reduce duplication/noise of output + params.delete(:connection) + params.delete(:stack) + if params.has_key?(:headers) && params[:headers].has_key?('Authorization') params[:headers] = params[:headers].dup params[:headers]['Authorization'] = REDACTED end + if params.has_key?(:password) params[:password] = REDACTED end - $stderr.puts("#{name} #{params.inspect}") + + $stderr.puts(name) + Excon::PrettyPrinter.pp($stderr, params) + if block_given? yield end diff -Nru ruby-excon-0.33.0/lib/excon/unix_socket.rb ruby-excon-0.45.1/lib/excon/unix_socket.rb --- ruby-excon-0.33.0/lib/excon/unix_socket.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/unix_socket.rb 2015-04-10 16:36:11.000000000 +0000 @@ -5,8 +5,10 @@ def connect @socket = ::Socket.new(::Socket::AF_UNIX, ::Socket::SOCK_STREAM, 0) - sockaddr = ::Socket.sockaddr_un(@data[:socket]) - + # If a Unix proxy was specified, the :path option will be set for it, + # otherwise fall back to the :socket option. + proxy_path = @data[:proxy] ? @data[:proxy][:path] : nil + sockaddr = ::Socket.sockaddr_un(proxy_path || @data[:socket]) if @nonblock begin @socket.connect_nonblock(sockaddr) diff -Nru ruby-excon-0.33.0/lib/excon/utils.rb ruby-excon-0.45.1/lib/excon/utils.rb --- ruby-excon-0.33.0/lib/excon/utils.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon/utils.rb 2015-04-10 16:36:11.000000000 +0000 @@ -2,21 +2,13 @@ module Utils extend self - control = (0x0..0x1f).map {|c| c.chr }.join + "\x7f" - delims = '<>#%"' - unwise = '{}|\\^[]`' - nonascii = (0x80..0xff).map {|c| c.chr }.join - UNESCAPED = /([#{ Regexp.escape(control + ' ' + delims + unwise + nonascii) }])/ + CONTROL = (0x0..0x1f).map {|c| c.chr }.join + "\x7f" + DELIMS = '<>#%"' + UNWISE = '{}|\\^[]`' + NONASCII = (0x80..0xff).map {|c| c.chr }.join + UNESCAPED = /([#{ Regexp.escape(CONTROL + ' ' + DELIMS + UNWISE + NONASCII) }])/ ESCAPED = /%([0-9a-fA-F]{2})/ - def valid_connection_keys(params = {}) - Excon::VALID_CONNECTION_KEYS - end - - def valid_request_keys(params = {}) - Excon::VALID_REQUEST_KEYS - end - def connection_uri(datum = @data) unless datum raise ArgumentError, '`datum` must be given unless called on a Connection' @@ -64,7 +56,7 @@ # Splits a header value +str+ according to HTTP specification. def split_header_value(str) return [] if str.nil? - str = str.strip + str = str.dup.strip str.force_encoding('BINARY') if FORCE_ENC str.scan(%r'\G((?:"(?:\\.|[^"])+?"|[^",]+)+) (?:,\s*|\Z)'xn).flatten @@ -74,16 +66,14 @@ def escape_uri(str) str = str.dup str.force_encoding('BINARY') if FORCE_ENC - str.gsub!(UNESCAPED) { "%%%02X" % $1[0].ord } - str + str.gsub(UNESCAPED) { "%%%02X" % $1[0].ord } end # Unescapes HTTP reserved and unwise characters in +str+ def unescape_uri(str) str = str.dup str.force_encoding('BINARY') if FORCE_ENC - str.gsub!(ESCAPED) { $1.hex.chr } - str + str.gsub(ESCAPED) { $1.hex.chr } end # Unescape form encoded values in +str+ @@ -91,8 +81,7 @@ str = str.dup str.force_encoding('BINARY') if FORCE_ENC str.gsub!(/\+/, ' ') - str.gsub!(ESCAPED) { $1.hex.chr } - str + str.gsub(ESCAPED) { $1.hex.chr } end end end diff -Nru ruby-excon-0.33.0/lib/excon.rb ruby-excon-0.45.1/lib/excon.rb --- ruby-excon-0.33.0/lib/excon.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/lib/excon.rb 2015-04-10 16:36:11.000000000 +0000 @@ -11,78 +11,49 @@ require 'zlib' require 'stringio' -# Define defaults first so they will be available to other files -module Excon - class << self - - # @return [Hash] defaults for Excon connections - def defaults - @defaults ||= { - :chunk_size => CHUNK_SIZE || DEFAULT_CHUNK_SIZE, - :ciphers => 'HIGH:!SSLv2:!aNULL:!eNULL:!3DES', - :connect_timeout => 60, - :debug_request => false, - :debug_response => false, - :headers => { - 'User-Agent' => USER_AGENT - }, - :idempotent => false, - :instrumentor_name => 'excon', - :middlewares => [ - Excon::Middleware::ResponseParser, - Excon::Middleware::Expects, - Excon::Middleware::Idempotent, - Excon::Middleware::Instrumentor, - Excon::Middleware::Mock - ], - :mock => false, - :nonblock => true, - :omit_default_port => false, - :persistent => false, - :read_timeout => 60, - :retry_limit => DEFAULT_RETRY_LIMIT, - :ssl_verify_peer => true, - :tcp_nodelay => false, - :uri_parser => URI, - :write_timeout => 60 - } - end - - # Change defaults for Excon connections - # @return [Hash] defaults for Excon connections - def defaults=(new_defaults) - @defaults = new_defaults - end +require 'excon/extensions/uri' - end -end - -require 'excon/utils' -require 'excon/constants' -require 'excon/connection' -require 'excon/errors' require 'excon/middlewares/base' -require 'excon/middlewares/decompress' -require 'excon/middlewares/escape_path' require 'excon/middlewares/expects' require 'excon/middlewares/idempotent' require 'excon/middlewares/instrumentor' require 'excon/middlewares/mock' -require 'excon/middlewares/redirect_follower' require 'excon/middlewares/response_parser' -require 'excon/response' + +require 'excon/constants' +require 'excon/utils' + +require 'excon/connection' +require 'excon/errors' require 'excon/headers' +require 'excon/response' +require 'excon/middlewares/decompress' +require 'excon/middlewares/escape_path' +require 'excon/middlewares/redirect_follower' +require 'excon/pretty_printer' require 'excon/socket' require 'excon/ssl_socket' -require 'excon/unix_socket' require 'excon/standard_instrumentor' +require 'excon/unix_socket' +# Define defaults first so they will be available to other files module Excon class << self + # @return [Hash] defaults for Excon connections + def defaults + @defaults ||= DEFAULTS + end + + # Change defaults for Excon connections + # @return [Hash] defaults for Excon connections + def defaults=(new_defaults) + @defaults = new_defaults + end + def display_warning(warning) - # Respect Ruby's $VERBOSE setting, unless EXCON_DEBUG is set - if !$VERBOSE.nil? || ENV['EXCON_DEBUG'] + # Show warning if $VERBOSE or ENV['EXCON_DEBUG'] is set + if $VERBOSE || ENV['EXCON_DEBUG'] $stderr.puts '[excon][WARNING] ' << warning << "\n#{ caller.join("\n") }" end end @@ -133,18 +104,25 @@ # @param [Hash] params One or more option params to set on the Connection instance # @return [Connection] A new Excon::Connection instance def new(url, params = {}) - uri_parser = params[:uri_parser] || Excon.defaults[:uri_parser] + uri_parser = params[:uri_parser] || defaults[:uri_parser] uri = uri_parser.parse(url) - raise ArgumentError.new("Invalid URI: #{uri}") unless uri.scheme + unless uri.scheme + raise ArgumentError.new("Invalid URI: #{uri}") + end params = { :host => uri.host, + :hostname => uri.hostname, :path => uri.path, :port => uri.port, :query => uri.query, - :scheme => uri.scheme, - :user => (Utils.unescape_uri(uri.user) if uri.user), - :password => (Utils.unescape_uri(uri.password) if uri.password) - }.merge!(params) + :scheme => uri.scheme + }.merge(params) + if uri.password + params[:password] = Utils.unescape_uri(uri.password) + end + if uri.user + params[:user] = Utils.unescape_uri(uri.user) + end Excon::Connection.new(params) end @@ -157,19 +135,26 @@ end if url = request_params.delete(:url) uri = URI.parse(url) - request_params.update( + request_params = { :host => uri.host, :path => uri.path, :port => uri.port, :query => uri.query, :scheme => uri.scheme - ) + }.merge!(request_params) if uri.user || uri.password request_params[:headers] ||= {} user, pass = Utils.unescape_form(uri.user.to_s), Utils.unescape_form(uri.password.to_s) request_params[:headers]['Authorization'] ||= 'Basic ' << ['' << user << ':' << pass].pack('m').delete(Excon::CR_NL) end end + if request_params.has_key?(:headers) + headers = Excon::Headers.new + request_params[:headers].each do |key, value| + headers[key] = value + end + request_params[:headers] = headers + end if block_given? if response_params raise(ArgumentError.new("stub requires either response_params OR a block")) diff -Nru ruby-excon-0.33.0/LICENSE.md ruby-excon-0.45.1/LICENSE.md --- ruby-excon-0.33.0/LICENSE.md 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/LICENSE.md 2015-04-10 16:36:11.000000000 +0000 @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2009-2014 [CONTRIBUTORS.md](https://github.com/geemus/excon/blob/master/CONTRIBUTORS.md) +Copyright (c) 2009-2015 [CONTRIBUTORS.md](https://github.com/excon/excon/blob/master/CONTRIBUTORS.md) Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in diff -Nru ruby-excon-0.33.0/metadata.yml ruby-excon-0.45.1/metadata.yml --- ruby-excon-0.33.0/metadata.yml 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/metadata.yml 2015-04-10 16:36:11.000000000 +0000 @@ -1,7 +1,7 @@ --- !ruby/object:Gem::Specification name: excon version: !ruby/object:Gem::Version - version: 0.33.0 + version: 0.45.1 platform: ruby authors: - dpiddy (Dan Peterson) @@ -10,120 +10,134 @@ autorequire: bindir: bin cert_chain: [] -date: 2014-04-15 00:00:00.000000000 Z +date: 2015-03-27 00:00:00.000000000 Z dependencies: - !ruby/object:Gem::Dependency name: activesupport requirement: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' type: :development prerelease: false version_requirements: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' - !ruby/object:Gem::Dependency name: delorean requirement: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' type: :development prerelease: false version_requirements: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' - !ruby/object:Gem::Dependency name: eventmachine requirement: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version - version: '0' + version: 1.0.4 type: :development prerelease: false version_requirements: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version - version: '0' + version: 1.0.4 - !ruby/object:Gem::Dependency name: open4 requirement: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' type: :development prerelease: false version_requirements: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' - !ruby/object:Gem::Dependency name: rake requirement: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' type: :development prerelease: false version_requirements: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' - !ruby/object:Gem::Dependency name: rdoc requirement: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' type: :development prerelease: false version_requirements: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' - !ruby/object:Gem::Dependency name: shindo requirement: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' type: :development prerelease: false version_requirements: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' - !ruby/object:Gem::Dependency name: sinatra requirement: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' type: :development prerelease: false version_requirements: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' +- !ruby/object:Gem::Dependency + name: json + requirement: !ruby/object:Gem::Requirement + requirements: + - - ">=" + - !ruby/object:Gem::Version + version: 1.8.2 + type: :development + prerelease: false + version_requirements: !ruby/object:Gem::Requirement + requirements: + - - ">=" + - !ruby/object:Gem::Version + version: 1.8.2 description: EXtended http(s) CONnections email: geemus@gmail.com executables: [] @@ -163,6 +177,7 @@ - lib/excon/connection.rb - lib/excon/constants.rb - lib/excon/errors.rb +- lib/excon/extensions/uri.rb - lib/excon/headers.rb - lib/excon/middlewares/base.rb - lib/excon/middlewares/decompress.rb @@ -173,6 +188,7 @@ - lib/excon/middlewares/mock.rb - lib/excon/middlewares/redirect_follower.rb - lib/excon/middlewares/response_parser.rb +- lib/excon/pretty_printer.rb - lib/excon/response.rb - lib/excon/socket.rb - lib/excon/ssl_socket.rb @@ -182,6 +198,8 @@ - tests/authorization_header_tests.rb - tests/bad_tests.rb - tests/basic_tests.rb +- tests/data/127.0.0.1.cert.crt +- tests/data/127.0.0.1.cert.key - tests/data/excon.cert.crt - tests/data/excon.cert.key - tests/data/xs @@ -203,11 +221,14 @@ - tests/rackups/deflater.ru - tests/rackups/proxy.ru - tests/rackups/query_string.ru +- tests/rackups/redirecting.ru - tests/rackups/request_headers.ru - tests/rackups/request_methods.ru - tests/rackups/response_header.ru - tests/rackups/ssl.ru +- tests/rackups/ssl_mismatched_cn.ru - tests/rackups/ssl_verify_peer.ru +- tests/rackups/streaming.ru - tests/rackups/thread_safety.ru - tests/rackups/timeout.ru - tests/rackups/webrick_patch.rb @@ -223,23 +244,23 @@ - tests/thread_safety_tests.rb - tests/timeout_tests.rb - tests/utils_tests.rb -homepage: https://github.com/geemus/excon +homepage: https://github.com/excon/excon licenses: - MIT metadata: {} post_install_message: rdoc_options: -- --charset=UTF-8 +- "--charset=UTF-8" require_paths: - lib required_ruby_version: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' required_rubygems_version: !ruby/object:Gem::Requirement requirements: - - - ! '>=' + - - ">=" - !ruby/object:Gem::Version version: '0' requirements: [] diff -Nru ruby-excon-0.33.0/Rakefile ruby-excon-0.45.1/Rakefile --- ruby-excon-0.33.0/Rakefile 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/Rakefile 2015-04-10 16:36:11.000000000 +0000 @@ -1,7 +1,7 @@ require 'rubygems' require 'rake' require 'date' - +include Rake::DSL ############################################################################# # # Helper functions @@ -75,7 +75,7 @@ # ############################################################################# -task :release => :build do +task :release => [:update_certs, :build] do unless `git branch` =~ /^\* master$/ puts "You must be on the master branch to release!" exit! diff -Nru ruby-excon-0.33.0/README.md ruby-excon-0.45.1/README.md --- ruby-excon-0.33.0/README.md 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/README.md 2015-04-10 16:36:11.000000000 +0000 @@ -4,10 +4,10 @@ Excon was designed to be simple, fast and performant. It works great as a general HTTP(s) client and is particularly well suited to usage in API clients. -[![Build Status](https://secure.travis-ci.org/geemus/excon.png)](http://travis-ci.org/geemus/excon) -[![Dependency Status](https://gemnasium.com/geemus/excon.png)](https://gemnasium.com/geemus/excon) -[![Gem Version](https://fury-badge.herokuapp.com/rb/excon.png)](http://badge.fury.io/rb/excon) -[![Gittip](http://img.shields.io/gittip/geemus.png)](https://www.gittip.com/geemus/) +[![Build Status](https://secure.travis-ci.org/excon/excon.svg)](http://travis-ci.org/excon/excon) +[![Dependency Status](https://gemnasium.com/geemus/excon.svg)](https://gemnasium.com/geemus/excon) +[![Gem Version](https://badge.fury.io/rb/excon.svg)](http://badge.fury.io/rb/excon) +[![Gittip](http://img.shields.io/gittip/geemus.svg)](https://www.gittip.com/geemus/) ## Getting Started @@ -85,6 +85,9 @@ Here are a few common examples: ```ruby +# Output debug info, similar to ENV['EXCON_DEBUG'] +connection = Excon.new('http://geemus.com/', :debug => true) + # Custom headers Excon.get('http://geemus.com', :headers => {'Authorization' => 'Basic 0123456789ABCDEF'}) connection.get(:headers => {'Authorization' => 'Basic 0123456789ABCDEF'}) @@ -142,6 +145,10 @@ connection = Excon.new('http://username:password@secure.geemus.com') connection = Excon.new('http://secure.geemus.com', :user => 'username', :password => 'password') + +# use custom uri parser +require 'addressable/uri' +connection = Excon.new('http://geemus.com/', uri_parser: Addressable::URI) ``` ## Chunked Requests @@ -255,11 +262,11 @@ connection.request(:method => :get, :path => 'example', :mock => true) ``` -Add stubs by providing the request_attributes to match and response attributes to return. Response params can be specified as either a hash or block which will yield with response_params. +Add stubs by providing the request attributes to match and response attributes to return. Response params can be specified as either a hash or block which will yield with the request params. ```ruby Excon.stub({}, {:body => 'body', :status => 200}) -Excon.stub({}, lambda {|request_params| :body => request_params[:body], :status => 200}) +Excon.stub({}, lambda {|request_params| {:body => request_params[:body], :status => 200}}) ``` Omitted attributes are assumed to match, so this stub will match *any* request and return an Excon::Response with a body of 'body' and status of 200. You can add whatever stubs you might like this way and they will be checked against in the order they were added, if none of them match then excon will raise an `Excon::Errors::StubNotFound` error to let you know. @@ -301,7 +308,7 @@ ) ``` -Excon will then instrument each request, retry, and error. The corresponding events are named excon.request, excon.retry, and excon.error respectively. +Excon will then instrument each request, retry, and error. The corresponding events are named `excon.request`, `excon.retry`, and `excon.error` respectively. ```ruby ActiveSupport::Notifications.subscribe(/excon/) do |*args| @@ -309,7 +316,7 @@ end ``` -If you prefer to label each event with something other than "excon," you may specify +If you prefer to label each event with a namespace other than "excon", you may specify an alternate name in the constructor: ```ruby @@ -320,7 +327,23 @@ ) ``` -If you don't want to add activesupport to your application, simply define a class which implements the same #instrument method like so: +Note: Excon's ActiveSupport::Notifications implementation has the following event format: `.` which is the opposite of the Rails' implementation. + +ActiveSupport provides a [subscriber](http://api.rubyonrails.org/classes/ActiveSupport/Subscriber.html) interface which lets you attach a subscriber to a namespace. Due to the incompability above, you won't be able to attach a subscriber to the "excon" namespace out of the box. + +If you want this functionality, you can use a simple adapter such as this one: + +```ruby +class ExconToRailsInstrumentor + def self.instrument(name, datum, &block) + namespace, *event = name.split(".") + rails_name = [event, namespace].flatten.join(".") + ActiveSupport::Notifications.instrument(rails_name, datum, &block) + end +end +``` + +If you don't want to add ActiveSupport to your application, simply define a class which implements the same `#instrument` method like so: ```ruby class SimpleInstrumentor @@ -337,9 +360,22 @@ The #instrument method will be called for each HTTP request, response, retry, and error. -For debugging purposes you can also use Excon::StandardInstrumentor to output all events to stderr. This can also be specified by setting the `EXCON_DEBUG` ENV var. +For debugging purposes you can also use `Excon::StandardInstrumentor` to output all events to stderr. This can also be specified by setting the `EXCON_DEBUG` ENV var. + +See [the documentation for ActiveSupport::Notifications](http://api.rubyonrails.org/classes/ActiveSupport/Notifications.html) for more detail on using the subscription interface. See excon's [instrumentation_test.rb](https://github.com/excon/excon/blob/master/tests/middlewares/instrumentation_tests.rb) for more examples of instrumenting excon. + +## HTTPS client certificate + +You can supply a client side certificate if the server requires it for authentication: + +```ruby +connection = Excon.new('https://example.com', + client_cert: 'mycert.pem', + client_key: 'mycert.key', + client_key_pass: 'my pass phrase') +``` -See [the documentation for ActiveSupport::Notifications](http://api.rubyonrails.org/classes/ActiveSupport/Notifications.html) for more detail on using the subscription interface. See excon's instrumentation_test.rb for more examples of instrumenting excon. +`client_key_pass` is optional. ## HTTPS/SSL Issues @@ -361,14 +397,13 @@ ## Getting Help -* [General Documentation](http://excon.io). * Ask specific questions on [Stack Overflow](http://stackoverflow.com/questions/tagged/excon). -* Report bugs and discuss potential features in [Github issues](https://github.com/geemus/excon/issues). +* Report bugs and discuss potential features in [Github issues](https://github.com/excon/excon/issues). ## Contributing -Please refer to [CONTRIBUTING.md](https://github.com/geemus/excon/blob/master/CONTRIBUTING.md). +Please refer to [CONTRIBUTING.md](https://github.com/excon/excon/blob/master/CONTRIBUTING.md). ## License -Please refer to [LICENSE.md](https://github.com/geemus/excon/blob/master/LICENSE.md). +Please refer to [LICENSE.md](https://github.com/excon/excon/blob/master/LICENSE.md). diff -Nru ruby-excon-0.33.0/tests/basic_tests.rb ruby-excon-0.45.1/tests/basic_tests.rb --- ruby-excon-0.33.0/tests/basic_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/basic_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -6,6 +6,7 @@ tests('GET /content-length/100').returns(200) do connection = Excon::Connection.new({ :host => '127.0.0.1', + :hostname => '127.0.0.1', :nonblock => false, :port => 9292, :scheme => 'http', @@ -18,22 +19,97 @@ end end +Shindo.tests('Excon streaming basics') do + pending if RUBY_PLATFORM == 'java' # need to find suitable server for jruby + with_unicorn('streaming.ru') do + # expected values: the response, in pieces, and a timeout after each piece + res = %w{Hello streamy world} + timeout = 0.1 + + # expect the full response as a string + # and expect it to take a (timeout * pieces) seconds + tests('simple blocking request on streaming endpoint').returns([res.join(''),'response time ok']) do + start = Time.now + ret = Excon.get('http://127.0.0.1:9292/streamed/simple').body + + if Time.now - start <= timeout*3 + [ret, 'streaming response came too quickly'] + else + [ret, 'response time ok'] + end + end + + # expect the full response as a string and expect it to + # take a (timeout * pieces) seconds (with fixed Content-Length header) + tests('simple blocking request on streaming endpoint with fixed length').returns([res.join(''),'response time ok']) do + start = Time.now + ret = Excon.get('http://127.0.0.1:9292/streamed/fixed_length').body + + if Time.now - start <= timeout*3 + [ret, 'streaming response came too quickly'] + else + [ret, 'response time ok'] + end + end + + # expect each response piece to arrive to the body right away + # and wait for timeout until next one arrives + def timed_streaming_test(endpoint, timeout) + ret = [] + timing = 'response times ok' + start = Time.now + Excon.get(endpoint, :response_block => lambda do |c,r,t| + # add the response + ret.push(c) + # check if the timing is ok + # each response arrives after timeout and before timeout + 1 + cur_time = Time.now - start + if cur_time < ret.length * timeout or cur_time > (ret.length+1) * timeout + timing = 'response time not ok!' + end + end) + # validate the final timing + if Time.now - start <= timeout*3 + timing = 'final timing was not ok!' + end + [ret, timing] + end + + tests('simple request with response_block on streaming endpoint').returns([res,'response times ok']) do + timed_streaming_test('http://127.0.0.1:9292/streamed/simple', timeout) + end + + tests('simple request with response_block on streaming endpoint with fixed length').returns([res,'response times ok']) do + timed_streaming_test('http://127.0.0.1:9292/streamed/fixed_length', timeout) + end + + end +end + Shindo.tests('Excon basics (Basic Auth Pass)') do with_rackup('basic_auth.ru') do basic_tests('http://test_user:test_password@127.0.0.1:9292') + tests('with frozen args').returns(200) do + user, pass, uri = ['test_user', 'test_password', 'http://127.0.0.1:9292'].map(&:freeze) + connection = Excon.new(uri, :user => user, :password => pass ) + response = connection.request(:method => :get, :path => '/content-length/100') + response.status + end + end +end - tests('Excon basics (Basic Auth Fail)') do - cases = [ - ['correct user, no password', 'http://test_user@127.0.0.1:9292'], - ['correct user, wrong password', 'http://test_user:fake_password@127.0.0.1:9292'], - ['wrong user, correct password', 'http://fake_user:test_password@127.0.0.1:9292'], - ] - cases.each do |desc,url| - tests("response.status for #{desc}").returns(401) do - connection = Excon.new(url) - response = connection.request(:method => :get, :path => '/content-length/100') - response.status - end +Shindo.tests('Excon basics (Basic Auth Fail)') do + with_rackup('basic_auth.ru') do + cases = [ + ['correct user, no password', 'http://test_user@127.0.0.1:9292'], + ['correct user, wrong password', 'http://test_user:fake_password@127.0.0.1:9292'], + ['wrong user, correct password', 'http://fake_user:test_password@127.0.0.1:9292'] + ] + cases.each do |desc,url| + tests("response.status for #{desc}").returns(401) do + connection = Excon.new(url) + response = connection.request(:method => :get, :path => '/content-length/100') + response.status end end end @@ -45,12 +121,64 @@ end end +Shindo.tests('Excon ssl verify peer (ssl)') do + with_rackup('ssl.ru') do + connection = nil + test do + ssl_ca_file = File.join(File.dirname(__FILE__), 'data', '127.0.0.1.cert.crt') + connection = Excon.new('https://127.0.0.1:9443', :ssl_verify_peer => true, :ssl_ca_file => ssl_ca_file ) + true + end + + tests('response.status').returns(200) do + response = connection.request(:method => :get, :path => '/content-length/100') + + response.status + end + end + + with_rackup('ssl_mismatched_cn.ru') do + connection = nil + test do + ssl_ca_file = File.join(File.dirname(__FILE__), 'data', 'excon.cert.crt') + connection = Excon.new('https://127.0.0.1:9443', :ssl_verify_peer => true, :ssl_ca_file => ssl_ca_file, :ssl_verify_peer_host => 'Excon' ) + true + end + + tests('response.status').returns(200) do + response = connection.request(:method => :get, :path => '/content-length/100') + + response.status + end + end +end + +Shindo.tests('Excon ssl verify peer (ssl cert store)') do + with_rackup('ssl.ru') do + connection = nil + test do + ssl_ca_cert = File.read(File.join(File.dirname(__FILE__), 'data', '127.0.0.1.cert.crt')) + ssl_cert_store = OpenSSL::X509::Store.new + ssl_cert_store.add_cert OpenSSL::X509::Certificate.new ssl_ca_cert + connection = Excon.new('https://127.0.0.1:9443', :ssl_verify_peer => true, :ssl_cert_store => ssl_cert_store ) + true + end + + tests('response.status').returns(200) do + response = connection.request(:method => :get, :path => '/content-length/100') + + response.status + end + end +end + Shindo.tests('Excon basics (ssl file)',['focus']) do with_rackup('ssl_verify_peer.ru') do tests('GET /content-length/100').raises(Excon::Errors::SocketError) do connection = Excon::Connection.new({ :host => '127.0.0.1', + :hostname => '127.0.0.1', :nonblock => false, :port => 8443, :scheme => 'https', @@ -73,6 +201,7 @@ tests('GET /content-length/100').raises(Excon::Errors::SocketError) do connection = Excon::Connection.new({ :host => '127.0.0.1', + :hostname => '127.0.0.1', :nonblock => false, :port => 8443, :scheme => 'https', @@ -102,7 +231,7 @@ pending if RUBY_PLATFORM == 'java' # need to find suitable server for jruby file_name = '/tmp/unicorn.sock' - with_unicorn('basic.ru', file_name) do + with_unicorn('basic.ru', 'unix://'+file_name) do basic_tests("unix:/", :socket => file_name) tests('explicit uri passed to connection') do diff -Nru ruby-excon-0.33.0/tests/data/127.0.0.1.cert.crt ruby-excon-0.45.1/tests/data/127.0.0.1.cert.crt --- ruby-excon-0.33.0/tests/data/127.0.0.1.cert.crt 1970-01-01 00:00:00.000000000 +0000 +++ ruby-excon-0.45.1/tests/data/127.0.0.1.cert.crt 2015-04-10 16:36:11.000000000 +0000 @@ -0,0 +1,14 @@ +-----BEGIN CERTIFICATE----- +MIICEzCCAXwCCQC94mWSE0+JcjANBgkqhkiG9w0BAQUFADBOMQswCQYDVQQGEwJV +UzELMAkGA1UECBMCQ0ExDjAMBgNVBAoTBUV4Y29uMQ4wDAYDVQQLEwVFeGNvbjES +MBAGA1UEAxMJMTI3LjAuMC4xMB4XDTE0MTAyODIwMjMzMVoXDTE5MTAyNzIwMjMz +MVowTjELMAkGA1UEBhMCVVMxCzAJBgNVBAgTAkNBMQ4wDAYDVQQKEwVFeGNvbjEO +MAwGA1UECxMFRXhjb24xEjAQBgNVBAMTCTEyNy4wLjAuMTCBnzANBgkqhkiG9w0B +AQEFAAOBjQAwgYkCgYEAvqlKlQMoS4q9jgsm+sBh7B9jEJVYHqNBluqgLubMEmjs +xFZUIicx+LmMPfUdnqtGDihR7q3yh/xeJuzzux38FBwTBDl8NRXWSyRkJqdi9XUA +qihAlkqDoZ6Eb867isF7C5FEqohAuCE0FUaYU1HY3bV/foLqxEbyvQVwaRZ4rjkC +AwEAATANBgkqhkiG9w0BAQUFAAOBgQCRxnrtbFJrBT4duYtOVuG/j8G46bf1DPrF +wuRf38gdO2Ldu+kdNRMhQrgSA9CfkjwwQpcVK2gZTuGTdmtqTnvIKilsomtG3tFK +ThWxuW6HrU9XgZ5KXIguVnL5tjYBNslsCFiQUeU/b8GF2MyMkOGUIC0p411ZB9v/ +mTKRgzf/qQ== +-----END CERTIFICATE----- diff -Nru ruby-excon-0.33.0/tests/data/127.0.0.1.cert.key ruby-excon-0.45.1/tests/data/127.0.0.1.cert.key --- ruby-excon-0.33.0/tests/data/127.0.0.1.cert.key 1970-01-01 00:00:00.000000000 +0000 +++ ruby-excon-0.45.1/tests/data/127.0.0.1.cert.key 2015-04-10 16:36:11.000000000 +0000 @@ -0,0 +1,15 @@ +-----BEGIN RSA PRIVATE KEY----- +MIICXQIBAAKBgQC+qUqVAyhLir2OCyb6wGHsH2MQlVgeo0GW6qAu5swSaOzEVlQi +JzH4uYw99R2eq0YOKFHurfKH/F4m7PO7HfwUHBMEOXw1FdZLJGQmp2L1dQCqKECW +SoOhnoRvzruKwXsLkUSqiEC4ITQVRphTUdjdtX9+gurERvK9BXBpFniuOQIDAQAB +AoGAEwJB41VrQQzWFUFbY4imuqnucIrTPEq+kVNXIRX1pqg7Yt/Qh48s1kV5i/vS +Ni2RUHwInylMku5AXNUm/7LfnN1zCHiYVkddL6df73BdzKfM86j+eQJdqye3AOkZ +GKrutsE8AEwOBCPtM9z3EbbAQZQpBBGyvAH3z8/GFLa34LkCQQDwEhEJleUGxiSR +anm43iFWsNBqW680YSz3kh1O7aC+09u8BOvOJ6azOMBYgxBno0IR9Oe7k0iBl+8e +YJmAuCVHAkEAy0/wdYeKwv9Dd3y9I+lS11VvaQaY2dmFmhbkPl/AAjUHju5ZF7me +Znwpq0jLlKRlKatVjkO/mkOeWs1/8MhQfwJBAO5VkVKJ3IjAF7fCFDvjUwfEm/Sr +NyJyQvk5tx0PrqEkpSZhYFUXaljNQ6/b1mJ9Yu9+yrye+MGnu73Vuy9eIasCQFT4 +fejA0y+X+5xul6Xwl9zDKiLczPkPPhUeSBoBbn/9pcEIwFd4DkmKzud1LxBafKUj +pEgm7GcOp5oPlM8PCQUCQQCtPFpgobUK9nRewxWagUL+xlEo6C1CPFhTwtQvnyi9 +6UwgxZtOdzAc3xRvHo4uK3OwGuOklqkpIeiZg3hoZb6B +-----END RSA PRIVATE KEY----- diff -Nru ruby-excon-0.33.0/tests/errors_tests.rb ruby-excon-0.45.1/tests/errors_tests.rb --- ruby-excon-0.33.0/tests/errors_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/errors_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -14,32 +14,32 @@ tests('message does not include response or response info').returns(true) do begin Excon.get('http://127.0.0.1:9292/error/not_found', :expects => 200) - rescue => err + rescue Excon::Errors::HTTPStatusError => err err.message.include?('Expected(200) <=> Actual(404 Not Found)') && - !err.message.include?('request =>') && - !err.message.include?('response =>') + !err.message.include?('excon.error.request') && + !err.message.include?('excon.error.response') end end - tests('message includes only response info').returns(true) do + tests('message includes only request info').returns(true) do begin Excon.get('http://127.0.0.1:9292/error/not_found', :expects => 200, - :debug_response => true) - rescue => err + :debug_request => true) + rescue Excon::Errors::HTTPStatusError => err err.message.include?('Expected(200) <=> Actual(404 Not Found)') && - !err.message.include?('request =>') && - !!(err.message =~ /response =>(.*)server says not found/) + err.message.include?('excon.error.request') && + !err.message.include?('excon.error.response') end end - tests('message includes only request info').returns(true) do + tests('message includes only response info').returns(true) do begin Excon.get('http://127.0.0.1:9292/error/not_found', :expects => 200, - :debug_request => true) - rescue => err + :debug_response => true) + rescue Excon::Errors::HTTPStatusError => err err.message.include?('Expected(200) <=> Actual(404 Not Found)') && - !!(err.message =~ /request =>(.*)error\/not_found/) && - !err.message.include?('response =>') + !err.message.include?('excon.error.request') && + err.message.include?('excon.error.response') end end @@ -47,10 +47,10 @@ begin Excon.get('http://127.0.0.1:9292/error/not_found', :expects => 200, :debug_request => true, :debug_response => true) - rescue => err + rescue Excon::Errors::HTTPStatusError => err err.message.include?('Expected(200) <=> Actual(404 Not Found)') && - !!(err.message =~ /request =>(.*)not_found/) && - !!(err.message =~ /response =>(.*)server says not found/) + err.message.include?('excon.error.request') && + err.message.include?('excon.error.response') end end diff -Nru ruby-excon-0.33.0/tests/middlewares/canned_response_tests.rb ruby-excon-0.45.1/tests/middlewares/canned_response_tests.rb --- ruby-excon-0.33.0/tests/middlewares/canned_response_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/middlewares/canned_response_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -12,13 +12,23 @@ end end - tests('does not mutate the canned response body').returns("canned") do + tests('does not mutate the canned response body').returns(the_body) do + Excon.get( + 'http://some-host.com/some-path', + :middlewares => [canned_response_middleware] + Excon.defaults[:middlewares] + ).body + end + + tests('yields non-mutated body to response_block').returns(the_body) do + body = '' + response_block = lambda { |chunk, _, _| body << chunk } Excon.get( 'http://some-host.com/some-path', :middlewares => [canned_response_middleware] + Excon.defaults[:middlewares], - :response_block => Proc.new { } # to force streaming + :response_block => response_block ) - the_body + body end + end diff -Nru ruby-excon-0.33.0/tests/middlewares/escape_path_tests.rb ruby-excon-0.45.1/tests/middlewares/escape_path_tests.rb --- ruby-excon-0.33.0/tests/middlewares/escape_path_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/middlewares/escape_path_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -5,6 +5,7 @@ tests('GET /echo%20dirty').returns(200) do connection = Excon::Connection.new({ :host => '127.0.0.1', + :hostname => '127.0.0.1', :middlewares => Excon.defaults[:middlewares] + [Excon::Middleware::EscapePath], :nonblock => false, :port => 9292, @@ -20,6 +21,7 @@ tests('GET /echo dirty').returns(200) do connection = Excon::Connection.new({ :host => '127.0.0.1', + :hostname => '127.0.0.1', :middlewares => Excon.defaults[:middlewares] + [Excon::Middleware::EscapePath], :nonblock => false, :port => 9292, diff -Nru ruby-excon-0.33.0/tests/middlewares/instrumentation_tests.rb ruby-excon-0.45.1/tests/middlewares/instrumentation_tests.rb --- ruby-excon-0.33.0/tests/middlewares/instrumentation_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/middlewares/instrumentation_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -155,7 +155,7 @@ connection.get(:idempotent => true) end - captured_stderr.string.split("\n").map {|event| event.split(' ').first} + captured_stderr.string.split("\n").reject {|line| line =~ %r{^ }}.map {|event| event.split(' ').first} ensure $stderr = original_stderr end diff -Nru ruby-excon-0.33.0/tests/middlewares/mock_tests.rb ruby-excon-0.45.1/tests/middlewares/mock_tests.rb --- ruby-excon-0.33.0/tests/middlewares/mock_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/middlewares/mock_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -35,7 +35,7 @@ response.status end - tests('request body with response_block given').returns('body') do + tests('response_block yields body').returns('body') do body = '' response_block = lambda do |chunk, remaining_bytes, total_bytes| body << chunk @@ -44,6 +44,11 @@ body end + tests('response.body empty with response_block').returns('') do + response_block = lambda { |_, _, _| } + connection.request(:method => :get, :path => '/content-length/100', :response_block => response_block).body + end + Excon.stubs.clear end @@ -99,7 +104,7 @@ response.status end - tests('request body with response block given').returns('body') do + tests('response_block yields body').returns('body') do body = '' response_block = lambda do |chunk, remaining_bytes, total_bytes| body << chunk @@ -108,6 +113,11 @@ body end + tests('response.body empty with response_block').returns('') do + response_block = lambda { |_, _, _| } + connection.request(:body => 'body', :method => :get, :path => '/content-length/100', :response_block => response_block).body + end + Excon.stubs.clear end @@ -132,6 +142,12 @@ end + tests("invalid stub response").raises(Excon::Errors::InvalidStub) do + Excon.stub({:body => 42, :method => :get}, {:status => 200}) + connection = Excon.new('http://127.0.0.1:9292', :mock => true) + connection.request(:body => 42, :method => :get, :path => '/').status + end + tests("mismatched stub").raises(Excon::Errors::StubNotFound) do Excon.stub({:method => :post}, {:body => 'body'}) Excon.get('http://127.0.0.1:9292/', :mock => true) @@ -140,7 +156,8 @@ Excon.stubs.clear tests("stub({}, {:body => 'x' * (Excon::DEFAULT_CHUNK_SIZE + 1)})") do - test("with response_block") do + + test("response_block yields body") do connection = Excon.new('http://127.0.0.1:9292', :mock => true) Excon.stub({}, {:body => 'x' * (Excon::DEFAULT_CHUNK_SIZE + 1)}) @@ -151,6 +168,14 @@ connection.request(:method => :get, :path => '/content-length/100', :response_block => response_block) chunks == ['x' * Excon::DEFAULT_CHUNK_SIZE, 'x'] end + + tests("response.body empty with response_block").returns('') do + connection = Excon.new('http://127.0.0.1:9292', :mock => true) + Excon.stub({}, {:body => 'x' * (Excon::DEFAULT_CHUNK_SIZE + 1)}) + response_block = lambda { |_, _, _| } + connection.request(:method => :get, :path => '/content-length/100', :response_block => response_block).body + end + end Excon.stubs.clear diff -Nru ruby-excon-0.33.0/tests/middlewares/redirect_follower_tests.rb ruby-excon-0.45.1/tests/middlewares/redirect_follower_tests.rb --- ruby-excon-0.33.0/tests/middlewares/redirect_follower_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/middlewares/redirect_follower_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -61,3 +61,20 @@ env_restore end + +Shindo.tests("Excon redirecting post request") do + env_init + + with_rackup('redirecting.ru') do + tests("request not have content-length and body").returns('ok') do + Excon.post( + 'http://127.0.0.1:9292', + :path => '/first', + :middlewares => Excon.defaults[:middlewares] + [Excon::Middleware::RedirectFollower], + :body => "a=Some_content" + ).body + end + end + + env_restore +end diff -Nru ruby-excon-0.33.0/tests/proxy_tests.rb ruby-excon-0.45.1/tests/proxy_tests.rb --- ruby-excon-0.33.0/tests/proxy_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/proxy_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -27,6 +27,27 @@ end end + tests('with fully-specified Unix socket proxy: unix:///') do + connection = nil + + tests('connection.data[:proxy][:host]').returns(nil) do + connection = Excon.new('http://foo.com', :proxy => 'unix:///tmp/myproxy.sock') + connection.data[:proxy][:host] + end + + tests('connection.data[:proxy][:port]').returns(nil) do + connection.data[:proxy][:port] + end + + tests('connection.data[:proxy][:scheme]').returns('unix') do + connection.data[:proxy][:scheme] + end + + tests('connection.data[:proxy][:path]').returns('/tmp/myproxy.sock') do + connection.data[:proxy][:path] + end + end + def env_proxy_tests(env) env_init(env) @@ -45,6 +66,15 @@ tests('connection.data[:proxy][:scheme]').returns('http') do connection.data[:proxy][:scheme] end + + tests('with disable_proxy set') do + connection = nil + + tests('connection.data[:proxy]').returns(nil) do + connection = Excon.new('http://foo.com', :disable_proxy => true) + connection.data[:proxy] + end + end end tests('an https connection') do @@ -62,6 +92,15 @@ tests('connection.data[:proxy][:scheme]').returns('http') do connection.data[:proxy][:scheme] end + + tests('with disable_proxy set') do + connection = nil + + tests('connection.data[:proxy]').returns(nil) do + connection = Excon.new('https://foo.com', :disable_proxy => true) + connection.data[:proxy] + end + end end tests('http proxy from the environment overrides config') do @@ -138,6 +177,35 @@ env_restore end + tests('with a unix socket proxy config from the environment') do + env_init({ + 'http_proxy' => 'unix:///tmp/myproxy.sock', + }) + + tests('an https connection') do + connection = nil + + tests('connection.data[:proxy][:host]').returns(nil) do + connection = Excon.new('https://secret.com') + connection.data[:proxy][:host] + end + + tests('connection.data[:proxy][:port]').returns(nil) do + connection.data[:proxy][:port] + end + + tests('connection.data[:proxy][:scheme]').returns('unix') do + connection.data[:proxy][:scheme] + end + + tests('connection.data[:proxy][:path]').returns('/tmp/myproxy.sock') do + connection.data[:proxy][:path] + end + end + + env_restore + end + end with_rackup('proxy.ru') do @@ -200,5 +268,32 @@ end + with_unicorn('proxy.ru', 'unix:///tmp/myproxy.sock') do + pending if RUBY_PLATFORM == 'java' # need to find suitable server for jruby + + tests('http proxying over unix socket: http://foo.com:8080') do + response = nil + + tests('response.status').returns(200) do + connection = Excon.new('http://foo.com:8080', :proxy => 'unix:///tmp/myproxy.sock') + response = connection.request(:method => :get, :path => '/bar', :query => {:alpha => 'kappa'}) + + response.status + end + + tests('sent Sent-Host header').returns('foo.com:8080') do + response.headers['Sent-Host'] + end + + tests('sent Proxy-Connection header').returns('Keep-Alive') do + response.headers['Sent-Proxy-Connection'] + end + + tests('response.body (proxied content)').returns('proxied content') do + response.body + end + end + end + env_restore end diff -Nru ruby-excon-0.33.0/tests/rackups/redirecting.ru ruby-excon-0.45.1/tests/rackups/redirecting.ru --- ruby-excon-0.33.0/tests/rackups/redirecting.ru 1970-01-01 00:00:00.000000000 +0000 +++ ruby-excon-0.45.1/tests/rackups/redirecting.ru 2015-04-10 16:36:11.000000000 +0000 @@ -0,0 +1,23 @@ +require 'sinatra' +require 'json' +require File.join(File.dirname(__FILE__), 'webrick_patch') + +class App < Sinatra::Base + set :environment, :production + enable :dump_errors + + post('/first') do + redirect "/second" + end + + get('/second') do + post_body = request.body.read + if post_body == "" && request["CONTENT_LENGTH"].nil? + "ok" + else + JSON.pretty_generate(request.env) + end + end +end + +run App diff -Nru ruby-excon-0.33.0/tests/rackups/ssl_mismatched_cn.ru ruby-excon-0.45.1/tests/rackups/ssl_mismatched_cn.ru --- ruby-excon-0.33.0/tests/rackups/ssl_mismatched_cn.ru 1970-01-01 00:00:00.000000000 +0000 +++ ruby-excon-0.45.1/tests/rackups/ssl_mismatched_cn.ru 2015-04-10 16:36:11.000000000 +0000 @@ -0,0 +1,15 @@ +require 'openssl' +require 'webrick' +require 'webrick/https' + +require File.join(File.dirname(__FILE__), 'basic') +key_file = File.join(File.dirname(__FILE__), '..', 'data', 'excon.cert.key') +cert_file = File.join(File.dirname(__FILE__), '..', 'data', 'excon.cert.crt') +Rack::Handler::WEBrick.run(Basic, { + :Port => 9443, + :SSLEnable => true, + :SSLPrivateKey => OpenSSL::PKey::RSA.new(File.open(key_file).read), + :SSLCertificate => OpenSSL::X509::Certificate.new(File.open(cert_file).read), + :SSLCACertificateFile => cert_file, + :SSLVerifyClient => OpenSSL::SSL::VERIFY_NONE, +}) diff -Nru ruby-excon-0.33.0/tests/rackups/ssl.ru ruby-excon-0.45.1/tests/rackups/ssl.ru --- ruby-excon-0.33.0/tests/rackups/ssl.ru 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/rackups/ssl.ru 2015-04-10 16:36:11.000000000 +0000 @@ -4,9 +4,13 @@ require File.join(File.dirname(__FILE__), 'basic') +key_file = File.join(File.dirname(__FILE__), '..', 'data', '127.0.0.1.cert.key') +cert_file = File.join(File.dirname(__FILE__), '..', 'data', '127.0.0.1.cert.crt') Rack::Handler::WEBrick.run(Basic, { :Port => 9443, - :SSLCertName => [["CN", WEBrick::Utils::getservername]], :SSLEnable => true, - :SSLVerifyClient => OpenSSL::SSL::VERIFY_NONE + :SSLPrivateKey => OpenSSL::PKey::RSA.new(File.open(key_file).read), + :SSLCertificate => OpenSSL::X509::Certificate.new(File.open(cert_file).read), + :SSLCACertificateFile => cert_file, + :SSLVerifyClient => OpenSSL::SSL::VERIFY_NONE, }) diff -Nru ruby-excon-0.33.0/tests/rackups/streaming.ru ruby-excon-0.45.1/tests/rackups/streaming.ru --- ruby-excon-0.33.0/tests/rackups/streaming.ru 1970-01-01 00:00:00.000000000 +0000 +++ ruby-excon-0.45.1/tests/rackups/streaming.ru 2015-04-10 16:36:11.000000000 +0000 @@ -0,0 +1,30 @@ +use Rack::ContentType, "text/plain" + +app = lambda do |env| + # streamed pieces to be sent + pieces = %w{Hello streamy world} + + response_headers = {} + + # set a fixed content length in the header if requested + if env['REQUEST_PATH'] == '/streamed/fixed_length' + response_headers['Content-Length'] = pieces.join.length.to_s + end + + response_headers["rack.hijack"] = lambda do |io| + # Write directly to IO of the response + begin + # return the response in pieces + pieces.each do |x| + sleep(0.1) + io.write(x) + io.flush + end + ensure + io.close + end + end + [200, response_headers, nil] +end + +run app diff -Nru ruby-excon-0.33.0/tests/request_tests.rb ruby-excon-0.45.1/tests/request_tests.rb --- ruby-excon-0.33.0/tests/request_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/request_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -1,113 +1,59 @@ Shindo.tests('Request Tests') do with_server('good') do - tests('sets transfer-coding and connection options') do - - tests('without a :response_block') do - request = nil - - returns('trailers, deflate, gzip', 'sets encoding options') do - request = Marshal.load( - Excon.get('http://127.0.0.1:9292/echo/request').body - ) - - request[:headers]['TE'] - end - - returns(true, 'TE added to Connection header') do - request[:headers]['Connection'].include?('TE') - end - end - - tests('with a :response_block') do - request = nil - - returns('trailers', 'does not set encoding options') do - captures = capture_response_block do |block| - Excon.get('http://127.0.0.1:9292/echo/request', - :response_block => block) - end - data = captures.map {|capture| capture[0] }.join - request = Marshal.load(data) - - request[:headers]['TE'] - end - - returns(true, 'TE added to Connection header') do - request[:headers]['Connection'].include?('TE') - end - end - - end - tests('persistent connections') do - - tests('with default :persistent => true') do - connection = nil - - returns(['1', '2'], 'uses a persistent connection') do - connection = Excon.new('http://127.0.0.1:9292', :persistent => true) - 2.times.map do - connection.request(:method => :get, :path => '/echo/request_count').body + ip_ports = %w(127.0.0.1:9292) + ip_ports << "[::1]:9293" unless RUBY_PLATFORM == 'java' + ip_ports.each do |ip_port| + + tests("with default :persistent => true, #{ip_port}") do + connection = nil + + returns(['1', '2'], 'uses a persistent connection') do + connection = Excon.new("http://#{ip_port}", :persistent => true) + 2.times.map do + connection.request(:method => :get, :path => '/echo/request_count').body + end end - end - returns(['3', '1', '2'], ':persistent => false resets connection') do - ret = [] - ret << connection.request(:method => :get, - :path => '/echo/request_count', - :persistent => false).body - ret << connection.request(:method => :get, - :path => '/echo/request_count').body - ret << connection.request(:method => :get, - :path => '/echo/request_count').body + returns(['3', '1', '2'], ':persistent => false resets connection') do + ret = [] + ret << connection.request(:method => :get, + :path => '/echo/request_count', + :persistent => false).body + ret << connection.request(:method => :get, + :path => '/echo/request_count').body + ret << connection.request(:method => :get, + :path => '/echo/request_count').body + end end - end - tests('with default :persistent => false') do - connection = nil + tests("with default :persistent => false, #{ip_port}") do + connection = nil - returns(['1', '1'], 'does not use a persistent connection') do - connection = Excon.new('http://127.0.0.1:9292', :persistent => false) - 2.times.map do - connection.request(:method => :get, :path => '/echo/request_count').body + returns(['1', '1'], 'does not use a persistent connection') do + connection = Excon.new("http://#{ip_port}", :persistent => false) + 2.times.map do + connection.request(:method => :get, :path => '/echo/request_count').body + end end - end - returns(['1', '2', '3', '1'], ':persistent => true enables persistence') do - ret = [] - ret << connection.request(:method => :get, - :path => '/echo/request_count', - :persistent => true).body - ret << connection.request(:method => :get, - :path => '/echo/request_count', - :persistent => true).body - ret << connection.request(:method => :get, - :path => '/echo/request_count').body - ret << connection.request(:method => :get, - :path => '/echo/request_count').body - end - end - - tests('sends `Connection: close`') do - returns(true, 'when :persistent => false') do - request = Marshal.load( - Excon.get('http://127.0.0.1:9292/echo/request', - :persistent => false).body - ) - request[:headers]['Connection'].include?('close') + returns(['1', '2', '3', '1'], ':persistent => true enables persistence') do + ret = [] + ret << connection.request(:method => :get, + :path => '/echo/request_count', + :persistent => true).body + ret << connection.request(:method => :get, + :path => '/echo/request_count', + :persistent => true).body + ret << connection.request(:method => :get, + :path => '/echo/request_count').body + ret << connection.request(:method => :get, + :path => '/echo/request_count').body + end end - returns(false, 'not when :persistent => true') do - request = Marshal.load( - Excon.get('http://127.0.0.1:9292/echo/request', - :persistent => true).body - ) - request[:headers]['Connection'].include?('close') - end end - end - end end diff -Nru ruby-excon-0.33.0/tests/response_tests.rb ruby-excon-0.45.1/tests/response_tests.rb --- ruby-excon-0.33.0/tests/response_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/response_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -20,6 +20,11 @@ end end + tests('simple response has empty body').returns('') do + response_block = lambda { |_, _, _| } + Excon.get('http://127.0.0.1:9292/chunked/simple', :response_block => response_block).body + end + tests('with expected response status'). returns([['hello ', nil, nil], ['world', nil, nil]]) do capture_response_block do |block| @@ -46,7 +51,7 @@ Excon.get('http://127.0.0.1:9292/chunked/trailers').headers['Test-Header'] end - tests("removes 'chunked' from Transfer-Encoding").returns('') do + tests("removes 'chunked' from Transfer-Encoding").returns(nil) do Excon.get('http://127.0.0.1:9292/chunked/simple').headers['Transfer-Encoding'] end @@ -69,6 +74,11 @@ end end + tests('simple response has empty body').returns('') do + response_block = lambda { |_, _, _| } + Excon.get('http://127.0.0.1:9292/content-length/simple', :response_block => response_block).body + end + tests('with expected response status'). returns([['hello', 6, 11], [' worl', 1, 11], ['d', 0, 11]]) do capture_response_block do |block| @@ -111,6 +121,11 @@ end end + tests('simple response has empty body').returns('') do + response_block = lambda { |_, _, _| } + Excon.get('http://127.0.0.1:9292/unknown/simple', :response_block => response_block).body + end + tests('with expected response status'). returns([['hello', nil, nil], [' worl', nil, nil], ['d', nil, nil]]) do capture_response_block do |block| @@ -153,69 +168,16 @@ end - tests('Transfer-Encoding') do - - tests('used with chunked response') do - resp = nil - - tests('server sent transfer-encoding').returns('gzip, chunked') do - resp = Excon.post( - 'http://127.0.0.1:9292/echo/transfer-encoded/chunked', - :body => 'hello world' - ) + tests('status line parsing') do - resp[:headers]['Transfer-Encoding-Sent'] - end - - tests('processed encodings removed from header').returns('') do - resp[:headers]['Transfer-Encoding'] - end - - tests('response body decompressed').returns('hello world') do - resp[:body] - end + tests('proper status code').returns(404) do + resp = Excon.get('http://127.0.0.1:9292/not-found') + resp.status end - tests('used with non-chunked response') do - resp = nil - - tests('server sent transfer-encoding').returns('gzip') do - resp = Excon.post( - 'http://127.0.0.1:9292/echo/transfer-encoded', - :body => 'hello world' - ) - - resp[:headers]['Transfer-Encoding-Sent'] - end - - tests('processed encoding removed from header').returns('') do - resp[:headers]['Transfer-Encoding'] - end - - tests('response body decompressed').returns('hello world') do - resp[:body] - end - end - - # sends TE header without gzip/deflate accepted (see requests_tests) - tests('with a :response_block') do - captures = nil - - tests('server does not compress').returns('chunked') do - resp = nil - captures = capture_response_block do |block| - resp = Excon.post('http://127.0.0.1:9292/echo/transfer-encoded/chunked', - :body => 'hello world', - :response_block => block) - end - - resp[:headers]['Transfer-Encoding-Sent'] - end - - tests('block receives uncompressed response').returns('hello world') do - captures.map {|capture| capture[0] }.join - end - + tests('proper reason phrase').returns("Not Found") do + resp = Excon.get('http://127.0.0.1:9292/not-found') + resp.reason_phrase end end diff -Nru ruby-excon-0.33.0/tests/servers/good.rb ruby-excon-0.45.1/tests/servers/good.rb --- ruby-excon-0.33.0/tests/servers/good.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/servers/good.rb 2015-04-10 16:36:11.000000000 +0000 @@ -163,6 +163,12 @@ send_data "\r\n" send_data "hello world" end + + when 'not-found' + start_response(:status => "404 Not Found") + send_data "Content-Length: 11\r\n" + send_data "\r\n" + send_data "hello world" end end @@ -327,5 +333,6 @@ EM.run do EM.start_server("127.0.0.1", 9292, GoodServer) + EM.start_server("::1", 9293, GoodServer) unless RUBY_PLATFORM == 'java' $stderr.puts "ready" end diff -Nru ruby-excon-0.33.0/tests/test_helper.rb ruby-excon-0.45.1/tests/test_helper.rb --- ruby-excon-0.33.0/tests/test_helper.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/test_helper.rb 2015-04-10 16:36:11.000000000 +0000 @@ -263,10 +263,11 @@ end end -def with_unicorn(name, file_name='/tmp/unicorn.sock') +def with_unicorn(name, listen='127.0.0.1:9292') unless RUBY_PLATFORM == 'java' GC.disable if RUBY_VERSION < '1.9' - pid, w, r, e = Open4.popen4("unicorn", "-l", "unix://#{file_name}", rackup_path(name)) + unix_socket = listen.sub('unix://', '') if listen.start_with? 'unix://' + pid, w, r, e = Open4.popen4("unicorn", "--no-default-middleware","-l", listen, rackup_path(name)) until e.gets =~ /worker=0 ready/; end else # need to find suitable server for jruby @@ -278,8 +279,8 @@ GC.enable if RUBY_VERSION < '1.9' Process.wait(pid) end - if File.exist?(file_name) - File.delete(file_name) + if not unix_socket.nil? and File.exist?(unix_socket) + File.delete(unix_socket) end end diff -Nru ruby-excon-0.33.0/tests/thread_safety_tests.rb ruby-excon-0.45.1/tests/thread_safety_tests.rb --- ruby-excon-0.33.0/tests/thread_safety_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/thread_safety_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -1,4 +1,17 @@ Shindo.tests('Excon thread safety') do + + tests('thread_safe_sockets configuration') do + tests('thread_safe_sockets default').returns(true) do + connection = Excon.new('http://foo.com') + connection.data[:thread_safe_sockets] + end + + tests('with thread_safe_sockets set false').returns(false) do + connection = Excon.new('http://foo.com', :thread_safe_sockets => false) + connection.data[:thread_safe_sockets] + end + end + with_rackup('thread_safety.ru') do connection = Excon.new('http://127.0.0.1:9292') diff -Nru ruby-excon-0.33.0/tests/utils_tests.rb ruby-excon-0.45.1/tests/utils_tests.rb --- ruby-excon-0.33.0/tests/utils_tests.rb 2014-04-21 17:12:51.000000000 +0000 +++ ruby-excon-0.45.1/tests/utils_tests.rb 2015-04-10 16:36:11.000000000 +0000 @@ -65,4 +65,17 @@ end end + + tests('#escape_uri').returns('/hello%20excon') do + Excon::Utils.escape_uri('/hello excon') + end + + tests('#unescape_uri').returns('/hello excon') do + Excon::Utils.unescape_uri('/hello%20excon') + end + + tests('#unescape_form').returns('message=We love excon!') do + Excon::Utils.unescape_form('message=We+love+excon!') + end + end