Vincent Guyader
Vincent Guyader

Reputation: 3199

How to pass the curl -F parameter in the httr package?

Hi I try to translate this curl instruction using httr

curl -H "Authorization: Token f2210dacd9c6ccb8133606d94ff8e61d99b477fd" -F [email protected] -F filename=test.txt -F parent_dir=/ http://cloud.seafile.com:8082/upload-api/73c5d117-3bcf-48a0-aa2a-3f48d5274ae3

Without the -F parameter the instruction is :

httr::POST(
  url = "http://cloud.seafile.com:8082/upload-api/73c5d117-3bcf-48a0-aa2a-3f48d5274ae3",
  add_headers(Authorization = "Token f2210dacd9c6ccb8133606d94ff8e61d99b477fd")
  )
)

I think I have to use the httr::upload_file function but I didn't manage to use this without error.

Do you have any idea how I can do that ?

Regards

Upvotes: 1

Views: 449

Answers (1)

cderv
cderv

Reputation: 6542

Here is how to construct this curl request with httr package. I used httpbin.org to test the request sent.

You'll use POST filling the body with a list. encode argument controls how this list will be handle and by default it is the correct multipart you need.

res <- httr::POST(
  url = "http://httpbin.org/post",
  httr::add_headers(Authorization = "Token f2210dacd9c6ccb8133606d94ff8e61d99b477fd"),
  # Add the file and metadata as body using a list. Default encode is ok
  body = list(
    file = httr::upload_file("test.txt"),
    filename = "test.txt",
    parent_dir = "/"
  )
)

httr_ouput <- httr::content(res)

One way to check this is ok is to compare output with the curl command you know is working

out <- sys::exec_internal(
       'curl -H "Authorization: Token f2210dacd9c6ccb8133606d94ff8e61d99b477fd" -F [email protected] -F filename=test.txt -F parent_dir=/ http://httpbin.org/post'
    )
curl_output <- jsonlite::fromJSON(rawToChar(out$stdout))

#compare body

identical(curl_output$files, httr_ouput$files)
#> TRUE
identical(curl_output$form, httr_ouput$form)
#> TRUE

You can also do it with the crul package, another wrapper above curl; The logic is identical

con <- crul::HttpClient$new(
  url = "http://httpbin.org/post"
)

crul_req <- con$post(
  body = list(
    file = crul::upload("test.txt"),
    filename = "test.ext",
    parent_dir = "/"
  )
)

crul_output <- jsonlite::fromJSON(crul_req$parse())

Upvotes: 3

Related Questions