当前位置: 首页 > 知识库问答 >
问题:

如何问Retrofit2,对我的动态URL不编码?

鲁望
2023-03-14

我正试图将我的代码库从1.9版本升级到2.0版本。我在1.9版本中上传图像没有问题。然而,我得到以下S3响应错误后,我改变到2.0版本。

这是我在Retrofit v1.9中上传图像的界面:

public interface IFileUploadAPI
{
    @PUT("/{url}")
    void uploadFile(@Path(value = "url", encode = false) String url, @Body() TypedFile file,
                    Callback<UploadFileResponse> callback);
}

我已将其更改为改装v2.0时的以下代码:

public interface IFileUploadAPI
{
    @PUT
    Call<UploadFileResponse> uploadFile(@Url String url, @Body RequestBody file);
}

我就是这样实现的。

public class MyFileUploadAPI
{
    private IFileUploadAPI mService;

    public MyFileUploadAPI()
    {
        final Retrofit adapter = new Retrofit.Builder() //
                        .baseUrl(MyAPIConstant.API_URL_BASE) // This URL will be ignored as we are using dynamic url. So no matters what it is.
                        .addConverterFactory(GsonConverterFactory.create(GsonUtils.getGson())) //
                        .client(ASDKApplication.getInstance().getOkHttpClient()) //
                        .build();

        this.mService = adapter.create(IFileUploadAPI.class);
    }

    public void uploadFile(final String url, final String filePath, final String mimeType)
    {
        RequestBody file = RequestBody.create(MediaType.parse(mimeType), filePath);
        Call<UploadFileResponse> call = mService.uploadFile(url, file);
                call.enqueue(new Callback<HitchUploadFileResponse>()
        {
            @Override
            public void onResponse(Call<UploadFileResponse> call, Response<UploadFileResponse> response)
            {
                UploadFileResponse uploadFileResponse = new UploadFileResponse();

                if (response.isSuccessful() && response.body() != null)
                {
                    uploadFileResponse = response.body();
                }

                // Rest of code...
            }

            @Override
            public void onFailure(Call<UploadFileResponse> call, Throwable t)
            {
                Logger.error(TAG, "uploadFile.onFailure(), msg: " + t.getMessage());
            }
        }
    }
}

因此,当用户单击<code>上传</code>按钮时,我调用一个API,它会返回一个我必须调用的url。回答如下:

[{"uploadSignedURL":"https://my-account.s3.amazonaws.com/license/1000_front_1464988248.jpeg?AWSAccessKeyId=MY_ID\u0026Expires=1464991848\u0026Signature=NhStdEX8RH3J0uzvVa6h%2FvN6FZQ%3D","filePath":"license/1000_front_1464988248.jpeg","target":"driving_license_front_img"}]

最后是对上述url的调用的响应(http状态代码403禁止):

<?xml version="1.0" encoding="UTF-8"?>
<Error><Code>SignatureDoesNotMatch</Code><Message>The request signature we calculated does not match the signature you provided. Check your key and signing method.</Message><AWSAccessKeyId>MY_ID</AWSAccessKeyId><StringToSign>PUT

image/jpeg; charset=utf-8
1464991848
/my-account/license/1000_front_1464988248.jpeg</StringToSign><SignatureProvided>NhStdEX8RH3J0uzvVa6h/vN6FZQ=</SignatureProvided><StringToSignBytes>50 55 54 0a 0a 69 6d 61 67 65 2f 6a 70 65 67 3b 20 63 68 61 72 73 65 74 3d 75 74 66 2d 38 0b 31 34 36 34 39 39 31 38 34 38 0a 2f 6d 79 74 65 6b 73 69 3a 67 72 61 62 68 69 45 63 68 2f 6c 69 63 65 6e 73 65 2f 31 30 30 30 5f 66 72 6f 6e 74 5f 31 34 36 34 39 38 38 32 34 38 2e 6a 70 65 67</StringToSignBytes><RequestId>2D6D08FE4E34FCE5</RequestId><HostId>tpvmJdeRxtAzPxOk2zFwMF2Ne6hmNMkcaM9D7m/I13iynYGJyqtC0U72B2t41SDYfPBjCRTVyOY=</HostId></Error>

共有1个答案

温浩大
2023-03-14

好吧,我发现出了什么问题。

okhttp正在将charset=utf-8添加到我的内容类型中。因此,我的内容类型变得像这样 contentType:image/jpeg; charset=utf-8。我在Postman上进行了测试,通过删除; charset=utf-8,我可以上传我的图像。

https://stackoverflow.com/a/25560731/513413说明添加<code>字符集</code>的原因。这是因为我正在传递图像文件的路径。你可以很容易地改变

RequestBody file=requestboid.create(MediaType.parse(mimeType),filePath)

RequestBody file = RequestBody.create(MediaType.parse(mimeType), new File(filePath));

还有一件更重要的事。一旦你上传你的图片到S3,亚马逊返回HTTP状态码200和空的正文。所以你也必须改变界面。

public interface IFileUploadAPI
{
    @PUT
    Call<Void> uploadFile(@Url String url, @Body RequestBody file);
}

 类似资料:
  • 问题内容: 我想对此进行网址编码: 我需要为此下载一个模块吗?我已经有了请求模块。 问题答案: 您可以使用JavaScript的:

  • 我是Retrofit 2的新手,正在尝试在我的应用程序中集成Google Place API。我的问题是如何在使用Retrofit 2.0的同时使用这种动态URL。 URL: 我的模型类名称为: 1)位置自动完成 位置预测 以及 我已经创建了WebServiceCall。java类进行改造,这是我的代码 我在调用URL时使用了这个接口:但我无法继续。 } 我一直在谷歌和StackOverflow中

  • 问题内容: 我正在使用jQuery DataTables,我的JavaScript代码如下所示: 我想根据选择元素的选择值过滤此dataTable: 如何设置的选项的值在该事件根据所选项目选择的元素? 问题答案: 我找到了 :

  • 我想为我的网站创建一个编码的网址。例如,对于这个URL:"http://google.com/index.html" 我想通过URL编码将此URL提供给客户端。

  • 让我们假设我有一个实数的 2D 数组。我从这个数组中的一个特定单元格开始,其中有一个特别大的数字。我想标记哪些其他单元格应该属于提到的起始单元格。规则是这样的:如果我找到从开始单元格走到另一个单元格的方法,则另一个单元格属于起始单元格。我只被允许在牢房上或下走动。我只被允许从数字较高的牢房走到数字较低的牢房。这是我从中心9开始的一个例子 我的伪算法是 现在来了第二个方面,我不仅为一个起始单元格执行

  • 问题内容: 我正在尝试使用python中的request.get()获取以下格式的URL: http://api.example.com/export/?format=json&key=site:dummy+type:example+group:wheel 但是,URL得到了百分比编码,但没有得到预期的响应。 如果我直接传递URL,则可以使用: 是否可以通过某种方式以原始格式传递参数-无需百分比编