在REST API请求中包含URL地址时,RestTemplate存在问题

时间:2019-06-17 11:03:51

标签: java spring rest spring-boot resttemplate

我正在尝试从Botify的REST API获取数据,以在项目(也是REST API)中使用它。我正在使用Spring的RestTemplate类的实例向Botify发出实际请求,特别是.exchange方法,因为我需要将Botify的密钥作为标头参数传递。

当我需要调用将URL作为请求URI的一部分(而不是参数)的端点的方法时,就会出现我的问题。该端点的文档位于https://developers.botify.com/api/reference/#!/Analysis/getUrlDetail

基本上,请求的结构如下:

/ analyses / {用户名} / {project_slug} / {analysis_slug} / urls / {url}

该URI的最后一部分是URL地址,需要使用UTF-8进行编码,以便可以将其与实际请求分开。

问题是(我相信).exchange方法总是对请求进行编码,所以我尝试这样发送:

/analyses/myusername/myprojectname/myprojectslug/urls/https%3A%2F%2Fwww.example.com

...最终像这样:

/analyses/myusername/myprojectname/myprojectslug/urls/https%253A%252F%252Fwww.example.com'

显然不起作用。这是对Botify进行调用的方法的摘录:

public String callBotifyEndpoint(String reportType, String parameters) throws UnsupportedEncodingException {
    String request = this.baseUri + "/analyses/myusername/myprojectname/myprojectslug/urls/https%3A%2F%2Fwww.example.com"

    HttpHeaders headers = new HttpHeaders();
    headers.set("Authorization", "Token " + this.apiKey);
    HttpEntity<String> entity = new HttpEntity<>(headers);

    UriComponentsBuilder botifyQueryBuilder = UriComponentsBuilder.fromUriString(request);      
    String queryStringBuild = botifyQueryBuilder.build(true).toUriString();

    String botifyResult = null;

    try {
        System.out.println("Calling Botify API: " + queryStringBuild);
        ResponseEntity<String> response = botifyTemplate.exchange(queryStringBuild, HttpMethod.GET, entity, String.class);
        if(response.hasBody()) {
            botifyResult = response.getBody();
        }
    } catch(RestClientException ex) {
        ex.printStackTrace();
    }
    try {

    } catch (Exception e) {
        // TODO: handle exception
    }

    return botifyResult;    
}

在此行:

    botifyQueryBuilder.build(true).toUriString();

“ true”参数指示数据是否已经编码。我尝试禁用它,但是结果是一样的。

为了简化操作,我已经删除了实际的请求生成过程(以及我的用户和项目的名称),但这应该返回Botify的响应以及该URL的现有数据。

相反,它将返回400错误的请求错误(这很有意义,因为URL不正确)。

我感觉这可能是RestTemplate的.exchange方法中的错误,但也许我没有正确使用它。有什么建议吗?

1 个答案:

答案 0 :(得分:1)

不要像在这里那样过早编码:

String request = this.baseUri + "/analyses/myusername/myprojectname/myprojectslug/urls/https%3A%2F%2Fwww.example.com";

使用RestTemplate中的参数占位符功能代替文本串联。

请参阅: Spring RestTemplate GET with parameters