我对RxJava很新,虽然我看到了与我要问的问题有关的多个问题,但我似乎无法将它们完全分开。
我有一个包含以下数据的PostPatrol对象:
public class PostPatrol {
String checkpoint_name;
String status;
int user;
String detail;
List<String> photos;
public PostPatrol(int cpId, String checkpoint_name, String detail, List<String> photos, String detail) {
this.cpId = cpId;
this.checkpoint_name = checkpoint_name;
this.detail = detail;
this.photos = photos;
this.status = status;
}
//getters and setters
}
我现在要做的是将本地照片列表保存到此PostPatrol记录中,但在此之前我必须逐个上传照片并进行改造,取回网址并将其保存到列表中然后我设置为PostPatrol记录的照片。
一旦我保存了某个PostPatrol记录所需的所有详细信息,我就会通过改造再次发送。
目前,我这样做:
功能如下:
private void uploadImage(List<String> photos, String folder, long requestId) {
final int size = photos.size();
final long reqId = requestId;
for (String path : photos) {
File file = new File(path);
RequestBody requestBody = RequestBody.create(MediaType.parse("image/*"), file);
MultipartBody.Part body = MultipartBody.Part.createFormData("image", file.getName(), requestBody);
RequestBody folderName = RequestBody.create(MediaType.parse("text/plain"), folder);
ApiEndpointInterface apiEndpointInterface = RetrofitManager.getApiInterface();
Call<FileInfo> call4File = apiEndpointInterface.postFile(body, folderName);
call4File.enqueue(new ApiCallback<FileInfo>() {
@Override
protected void do4Failure(Throwable t) {
Log.d(TAG, t.toString());
snackbar = Snackbar.make(viewPendingRequestLayout, R.string.sb_image_upload_error, Snackbar.LENGTH_SHORT);
snackbar.show();
position++;
}
@Override
protected void do4PositiveResponse(Response<FileInfo> response) {
Log.d(TAG, "Uploaded Image");
FileInfo fileDetails = response.body();
listUrls.add(fileDetails.getImage());
position++;
if (position == size) {
postRequest(reqId);
position = 0;
}
}
@Override
protected void do4NegativeResponse(Response<FileInfo> response) {
String bodyMsg = "";
try {
bodyMsg = new String(response.errorBody().bytes());
} catch (IOException e) {
e.printStackTrace();
}
Log.d(TAG, bodyMsg);
snackbar = Snackbar.make(viewPendingRequestLayout, R.string.sb_image_upload_error, Snackbar.LENGTH_SHORT);
snackbar.show();
position++;
}
});
}
}
在do4PositiveResponse
中,我使用局部变量来跟踪我是否已将所有照片上传到将列表保存到PostPatrol记录的功能之前。但有时候,我会发现照片根本没有上传的问题,因为它太晚或太早都没有上传。
这是我在postRequest()
private void postRequest(long requestId) {
if(mapIdPatrol.containsKey(requestId)){
PostPatrol postPatrol = mapIdPatrol.get(requestId);
postPatrol.setPhotos(listUrls);
postPatrolRequest(postPatrol, requestId);
}
listUrls = new ArrayList<>();
}
最后我的代码在postPatrolRequest()
private void postPatrolRequest(final PostPatrol postPatrol, final long requestId){
ApiEndpointInterface apiEndpointInterface = RetrofitManager.getApiInterface();
Call<ResponseId> call4Handle = apiEndpointInterface.handleCheckpoint(postPatrol);
call4Handle.enqueue(new ApiCallback<ResponseId>() {
@Override
protected void do4Failure(Throwable t) {
finishUploading();
Log.d(TAG, t.toString());
}
@Override
protected void do4PositiveResponse(Response<ResponseId> response) {
RequestsDataSource.removeRequest(getApplication(),requestId);
finishUploading();
}
@Override
protected void do4NegativeResponse(Response<ResponseId> response) {
finishUploading();
String bodyMsg = "";
try {
bodyMsg = new String(response.errorBody().bytes());
} catch (IOException e) {
e.printStackTrace();
}
Log.d(TAG, bodyMsg);
snackbar = Snackbar.make(viewPendingRequestLayout, getResources().getText(R.string.sb_negative_response), Snackbar.LENGTH_SHORT);
snackbar.show();
}
});
}
我知道这是非常低效的,所以我希望你的帮助,所以我可以尝试使用RxJava找到解决方法。谢谢。
答案 0 :(得分:1)
操作是原子的吗?即如果通过Retrofit保存一些照片失败,你还需要继续吗?
无论如何,大致解决方案将是类似的(伪代码):
Observable<String> urls = Observable.from(listOfPhotoFilePaths)
.flatMapDelayError(path -> { return retrofit.save(readFile(path))})
.toList()
Observable<PostPatrol> pp = urls
.map(list -> { return new PostPatrol(list)})