Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

SSL v3 alert handshake failure #55

Closed
rparrish opened this issue Oct 30, 2014 · 7 comments · Fixed by #56
Closed

SSL v3 alert handshake failure #55

rparrish opened this issue Oct 30, 2014 · 7 comments · Fixed by #56

Comments

@rparrish
Copy link
Contributor

After updating the SSL certificate on our site, I'm getting this error from 'redcap_read*' functions:

Error in function (type, msg, asError = TRUE)  : 
  error:14094410:SSL routines:SSL3_READ_BYTES:sslv3 alert handshake failure

However, this error is not showing up when using Postman or with RCurl, httr, or redcapAPI, as illustrated below. I've updated all the relevant packages but that didn't help.

Any ideas or suggestions with troubleshooting?

Set API parameters

redcap_uri <- "https://ampa.org/redcap/api/"
token <- "D1BB670A719F1D481A5574F33125A04C" ## expires 11/2/2014

RCurl

## RCurl
library(RCurl)

# SO post:
# http://stackoverflow.com/questions/15347233/ssl-certificate-failed-for-twitter-in-r
options(RCurlOptions = 
            list(cainfo=system.file("CurlSSL", 
                                    "cacert.pem", 
                                    package = "RCurl")))

RCurl_raw <- RCurl::postForm(
    uri = redcap_uri
    , token = token
    , content = 'record'
    , format = 'csv'
    , type = 'flat'
    , rawOrLabel = 'raw'
    , exportDataAccessGroups = 'true'
    , .opts = RCurl::curlOptions(ssl.verifypeer=TRUE, verbose=TRUE)
)

RCurl_raw
## [1] "record_id,fruit,fruit_size,data_complete\n1,Apple,Small,2\n2,Apple,Large,2\n3,Orange,Medium,2\n4,Grapefruit,Large,2\n"
## attr(,"Content-Type")
##                 charset 
## "text/html"     "utf-8"

httr

## httr 
library(httr)
post_body <- list(
    token = token,
    content = 'record',
    format = 'csv',
    type = 'flat',
    rawOrLabel = 'raw',
    exportDataAccessGroups = 'true'
)

httr_raw <- httr::POST(
    url = redcap_uri,
    body = post_body,
    config = httr::config(ssl.verifypeer=TRUE)
    #httr::verbose() 
)
httr_raw
## Response [https://ampa.org/redcap/api/]
##   Date: 2014-10-29 18:55
##   Status: 200
##   Content-type: text/html; charset=utf-8
##   Size: 112 B
## record_id,fruit,fruit_size,data_complete
## 1,Apple,Small,2
## 2,Apple,Large,2
## 3,Orange,Medium,2
## 4,Grapefruit,Large,2

redcapAPI

## redcapAPI
library(redcapAPI)
rcon <- redcapConnection(url=redcap_uri, token=token, 
                         config = list(ssl.verifypeer=TRUE))
redcap_API_data <- exportRecords(rcon)

redcap_API_data
##   record_id      fruit fruit_size data_complete
## 1         1      Apple      Small             2
## 2         2      Apple      Large             2
## 3         3     Orange     Medium             2
## 4         4 Grapefruit      Large             2

REDCapR

## REDCapR
library(REDCapR)
REDCapR_data <- redcap_read_oneshot(redcap_uri=redcap_uri, token=token,
                           raw_or_label = "label", 
                           verbose = TRUE)
Error in function (type, msg, asError = TRUE)  : 
  error:14094410:SSL routines:SSL3_READ_BYTES:sslv3 alert handshake failure
@nutterb
Copy link
Contributor

nutterb commented Oct 30, 2014

In line 109 of redcap_read_oneshot, the option is set sslversion=3. It looks like the error is with SSL3. Perhaps the certs only work for SSL2? (I'm not sure why they aren't matching up).

But consider the following--you'll see that when I switch the cURL option to sslversion=3, I replicate your error. The only reason that REDCapR is having a problem is the SSL version. I'm not entirely sure what the resolution is.

> redcap_uri <- "https://ampa.org/redcap/api/"
> token <- "E653F6B53DCDF44A860D0F6B3EE262ED"
> 
> options(RCurlOptions = 
+           list(cainfo=system.file("CurlSSL", 
+                                   "cacert.pem", 
+                                   package = "RCurl")))
> 
> RCurl_raw <- RCurl::postForm(
+   uri = redcap_uri
+   , token = token
+   , content = 'record'
+   , format = 'csv'
+   , type = 'flat'
+   , rawOrLabel = 'raw'
+   , exportDataAccessGroups = 'true'
+   , .opts = RCurl::curlOptions(ssl.verifypeer=TRUE, verbose=TRUE)
+ )
* About to connect() to ampa.org port 443 (#0)
*   Trying 67.205.8.39... * connected
* Connected to ampa.org (67.205.8.39) port 443 (#0)
* successfully set certificate verify locations:
*   CAfile: C:/Program Files/R/R-devel/library/RCurl/CurlSSL/cacert.pem
  CApath: none
* SSL connection using RC4-SHA
* Server certificate:
*    subject: OU=Domain Control Validated; OU=Provided by New Dream Network, LLC; OU=DreamHost Basic SSL; CN=ampa.org
*    start date: 2014-10-27 00:00:00 GMT
*    expire date: 2015-11-08 23:59:59 GMT
*    subjectAltName: ampa.org matched
*    issuer: C=GB; ST=Greater Manchester; L=Salford; O=COMODO CA Limited; CN=PositiveSSL CA 2
*    SSL certificate verify ok.
> POST /redcap/api/ HTTP/1.1
Host: ampa.org
Accept: */*
Content-Length: 686
Expect: 100-continue
Content-Type: multipart/form-data; boundary=----------------------------dc1063c12ed4

< HTTP/1.1 100 Continue
< HTTP/1.1 200 OK
< Date: Thu, 30 Oct 2014 02:31:43 GMT
< Server: Apache
< Expires: 0
< cache-control: no-store, no-cache, must-revalidate
< Pragma: no-cache
< Access-Control-Allow-Origin: *
< X-Mod-Pagespeed: 1.4.26.5-3533
< Vary: Accept-Encoding
< Cache-Control: max-age=0, no-cache
< Content-Length: 112
< Content-Type: text/html; charset=utf-8
< 
* Connection #0 to host ampa.org left intact
> 
> RCurl_raw <- RCurl::postForm(
+   uri = redcap_uri
+   , token = token
+   , content = 'record'
+   , format = 'csv'
+   , type = 'flat'
+   , rawOrLabel = 'raw'
+   , exportDataAccessGroups = 'true'
+   , .opts = RCurl::curlOptions(ssl.verifypeer=TRUE, verbose=TRUE, sslversion=3)
+ )
* About to connect() to ampa.org port 443 (#0)
*   Trying 67.205.8.39... * connected
* Connected to ampa.org (67.205.8.39) port 443 (#0)
* successfully set certificate verify locations:
*   CAfile: C:/Program Files/R/R-devel/library/RCurl/CurlSSL/cacert.pem
  CApath: none
* error:14094410:SSL routines:SSL3_READ_BYTES:sslv3 alert handshake failure
* Closing connection #0
Error in function (type, msg, asError = TRUE)  : 
  error:14094410:SSL routines:SSL3_READ_BYTES:sslv3 alert handshake failure
> 

@nutterb
Copy link
Contributor

nutterb commented Oct 30, 2014

I'll also add, having played around with this a bit more, that I'm observing the same error even when I start a fresh session and use httr's cert file with SSL3. So this isn't really a REDCapR problem. That being said, is hardcoding sslversion=3 really the best idea, or should that be left as an option the user can change?

@wibeasley
Copy link
Member

I think both of you are right on. I forced it to SSL 3 because that's the only way I could get it working reliably in my two Linux test machines.

I was aware this might happen (see r-lib/httr#155), but I thought I'd have more time to work things out.

Let me see if I can find a quick solution that still allow the Ubuntu machines to work with their version of libcurl (if that's indeed the discrepancy).

I think you're right that the solution probably involves avoiding a hardcoded V3

@nutterb
Copy link
Contributor

nutterb commented Oct 30, 2014

I should really develop complete thoughts before I post my comments :)

The easiest fix might be moving that one line (line 109) into the arguments. Then the user also has the full flexibility of the cURL options.

@wibeasley
Copy link
Member

@rparrish, thanks again for digging so deeply with all the comparisons, and also submitting the patch. I've tried this on a few Linux machines, and I think it's something about the two Ubuntu 14.04's I have at home. It's working fine on the others without the SSL=3 restriction.

I think I'm going to open this up and let the user pass the whole config_options list to the function, instead of trying to anticipate which specific options a user might want to change in the future (whcih so far is the cert location and the SSL version). Any objections or warnings? I'll start in the dev branch for a day or so before pulling into the master.

(Also, last week something was driving me batty about the examples above. It turns out that the REDCapR snippet is using uri instead of redcap_uri (and using a value that had been declared earlier in the exploratory phase). I suspect that was just pasting in the code, because I don't think that would have produced the 'handshake' error if the url variable wasn't right. I'm just saying, in case we use this thorough snippet for future debugging.)

@rparrish
Copy link
Contributor Author

rparrish commented Nov 2, 2014

No objections at all. You're correct about the uri/redcap_uri issue - they should all reference the same resource.

@wibeasley
Copy link
Member

@rparrish I liked your examples so much that I added it to the packages 'playgrounds': https://github.com/OuhscBbmc/REDCapR/blob/dev/playgrounds/SSL3Playground.R

It's a collection of files that kinda help me investigate issues, without formalizing them in the examples or unit/integration test.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants