X-Git-Url: https://git.arvados.org/arvados.git/blobdiff_plain/f15c8a8ef1af9d823030f4c6383ba2560a78a4fa..74cffe96768727e8b727cdb54358729c91bec130:/sdk/R/R/HttpRequest.R diff --git a/sdk/R/R/HttpRequest.R b/sdk/R/R/HttpRequest.R index f5c11a176f..07defca90f 100644 --- a/sdk/R/R/HttpRequest.R +++ b/sdk/R/R/HttpRequest.R @@ -1,139 +1,74 @@ +# Copyright (C) The Arvados Authors. All rights reserved. +# +# SPDX-License-Identifier: Apache-2.0 + +source("./R/util.R") + HttpRequest <- R6::R6Class( "HttrRequest", public = list( - initialize = function() - { - }, + validContentTypes = NULL, + validVerbs = NULL, - GET = function(url, headers = NULL, queryFilters = NULL, limit = NULL, offset = NULL) + initialize = function() { - headers <- httr::add_headers(unlist(headers)) - query <- private$createQuery(queryFilters, limit, offset) - url <- paste0(url, query) - - serverResponse <- httr::GET(url = url, config = headers) + self$validContentTypes <- c("text", "raw") + self$validVerbs <- c("GET", "POST", "PUT", "DELETE", "PROPFIND", "MOVE", "COPY") }, - PUT = function(url, headers = NULL, body = NULL, - queryFilters = NULL, limit = 100, offset = 0) + exec = function(verb, url, headers = NULL, body = NULL, queryParams = NULL, + retryTimes = 0) { - headers <- httr::add_headers(unlist(headers)) - query <- private$createQuery(queryFilters, limit, offset) - url <- paste0(url, query) + if(!(verb %in% self$validVerbs)) + stop("Http verb is not valid.") - serverResponse <- httr::PUT(url = url, config = headers, body = body) - }, + urlQuery <- self$createQuery(queryParams) + url <- paste0(url, urlQuery) - POST = function(url, headers = NULL, body = NULL, - queryFilters = NULL, limit = 100, offset = 0) - { - headers <- httr::add_headers(unlist(headers)) - query <- private$createQuery(queryFilters, limit, offset) - url <- paste0(url, query) + config <- httr::add_headers(unlist(headers)) + if(toString(Sys.getenv("ARVADOS_API_HOST_INSECURE") == "TRUE")) + config$options = list(ssl_verifypeer = 0L) - serverResponse <- httr::POST(url = url, config = headers, body = body) + # times = 1 regular call + numberOfRetries + response <- httr::RETRY(verb, url = url, body = body, + config = config, times = retryTimes + 1) }, - DELETE = function(url, headers = NULL, body = NULL, - queryFilters = NULL, limit = NULL, offset = NULL) - { - headers <- httr::add_headers(unlist(headers)) - query <- private$createQuery(queryFilters, limit, offset) - url <- paste0(url, query) - - serverResponse <- httr::DELETE(url = url, config = headers) - }, - - PROPFIND = function(url, headers = NULL) - { - h <- curl::new_handle() - curl::handle_setopt(h, customrequest = "PROPFIND") - curl::handle_setheaders(h, .list = headers) - - propfindResponse <- curl::curl_fetch_memory(url, h) - } - ), - - private = list( - - #Todo(Fudo): Refactor this and find a better way to build - # Python array from R list (recursion?) - createQuery = function(filters, limit, offset) + createQuery = function(queryParams) { - finalQuery <- NULL + queryParams <- Filter(Negate(is.null), queryParams) - if(!is.null(filters)) + query <- sapply(queryParams, function(param) { - filters <- sapply(filters, function(filter) - { - if(length(filter) != 3) - stop("Filter list must have exacthey 3 elements.") + if(is.list(param) || length(param) > 1) + param <- RListToPythonList(param, ",") - attributeAndOperator = filter[c(1, 2)] - filterList = filter[[3]] - filterListIsPrimitive = TRUE - if(length(filterList) > 1) - filterListIsPrimitive = FALSE + URLencode(as.character(param), reserved = T, repeated = T) - attributeAndOperator <- sapply(attributeAndOperator, function(component) { - component <- paste0("\"", component, "\"") - }) + }, USE.NAMES = TRUE) - filterList <- sapply(unlist(filterList), function(filter) { - filter <- paste0("\"", filter, "\"") - }) - - filterList <- paste(filterList, collapse = ",+") - - if(!filterListIsPrimitive) - filterList <- paste0("[", filterList, "]") - - filter <- c(attributeAndOperator, filterList) - - queryParameter <- paste(filter, collapse = ",+") - queryParameter <- paste0("[", queryParameter, "]") - - }) - - filters <- paste(filters, collapse = ",+") - filters <- paste0("[", filters, "]") - - encodedQuery <- URLencode(filters, reserved = T, repeated = T) - - #Todo(Fudo): This is a hack for now. Find a proper solution. - encodedQuery <- stringr::str_replace_all(encodedQuery, "%2B", "+") - - finalQuery <- c(finalQuery, paste0("filters=", encodedQuery)) + if(length(query) > 0) + { + query <- paste0(names(query), "=", query, collapse = "&") - finalQuery + return(paste0("/?", query)) } - if(!is.null(limit)) - { - if(!is.numeric(limit)) - stop("Limit must be a numeric type.") - - finalQuery <- c(finalQuery, paste0("limit=", limit)) - } + return("") + }, - if(!is.null(offset)) - { - if(!is.numeric(offset)) - stop("Offset must be a numeric type.") - - finalQuery <- c(finalQuery, paste0("offset=", offset)) - } + getConnection = function(url, headers, openMode) + { + h <- curl::new_handle() + curl::handle_setheaders(h, .list = headers) - if(length(finalQuery) > 1) - { - finalQuery <- paste0(finalQuery, collapse = "&") - finalQuery <- paste0("?", finalQuery) - } + if(toString(Sys.getenv("ARVADOS_API_HOST_INSECURE") == "TRUE")) + curl::handle_setopt(h, ssl_verifypeer = 0L) - finalQuery + conn <- curl::curl(url = url, open = openMode, handle = h) } ),