15
15
import java .io .File ;
16
16
import java .io .IOException ;
17
17
import java .util .Date ;
18
+ import java .util .HashMap ;
19
+ import java .util .List ;
20
+ import java .util .Map ;
21
+ import java .util .concurrent .atomic .AtomicBoolean ;
18
22
import java .util .concurrent .atomic .AtomicInteger ;
19
23
import java .util .concurrent .atomic .AtomicReference ;
20
24
import javax .inject .Inject ;
@@ -41,7 +45,8 @@ public class UploadClient {
41
45
private final PageContentsCreator pageContentsCreator ;
42
46
private final FileUtilsWrapper fileUtilsWrapper ;
43
47
private final Gson gson ;
44
- private boolean pauseUploads = false ;
48
+
49
+ private Map <String , Boolean > pauseUploads ;
45
50
46
51
private final CompositeDisposable compositeDisposable = new CompositeDisposable ();
47
52
@@ -55,6 +60,7 @@ public UploadClient(final UploadInterface uploadInterface,
55
60
this .pageContentsCreator = pageContentsCreator ;
56
61
this .fileUtilsWrapper = fileUtilsWrapper ;
57
62
this .gson = gson ;
63
+ this .pauseUploads = new HashMap <>();
58
64
}
59
65
60
66
/**
@@ -64,32 +70,50 @@ public UploadClient(final UploadInterface uploadInterface,
64
70
Observable <StashUploadResult > uploadFileToStash (
65
71
final Context context , final String filename , final Contribution contribution ,
66
72
final NotificationUpdateProgressListener notificationUpdater ) throws IOException {
67
- if (contribution .getChunkInfo () != null && contribution .getChunkInfo ().isLastChunkUploaded ()) {
73
+ if (contribution .getChunkInfo () != null
74
+ && contribution .getChunkInfo ().getTotalChunks () == contribution .getChunkInfo ()
75
+ .getIndexOfNextChunkToUpload ()) {
68
76
return Observable .just (new StashUploadResult (StashUploadState .SUCCESS ,
69
77
contribution .getChunkInfo ().getUploadResult ().getFilekey ()));
70
78
}
71
- pauseUploads = false ;
72
- File file = new File (contribution .getLocalUri ().getPath ());
73
- final Observable <File > fileChunks = fileUtilsWrapper .getFileChunks (context , file , CHUNK_SIZE );
79
+
80
+ pauseUploads .put (contribution .getPageId (), false );
81
+
82
+ final File file = new File (contribution .getLocalUri ().getPath ());
83
+ final List <File > fileChunks = fileUtilsWrapper .getFileChunks (context , file , CHUNK_SIZE );
84
+
85
+ final int totalChunks = fileChunks .size ();
86
+
74
87
final MediaType mediaType = MediaType
75
88
.parse (FileUtils .getMimeType (context , Uri .parse (file .getPath ())));
76
89
77
- final AtomicInteger index = new AtomicInteger ();
78
90
final AtomicReference <ChunkInfo > chunkInfo = new AtomicReference <>();
79
- Timber .d ("Chunk info" );
80
- if (contribution .getChunkInfo () != null && isStashValid (contribution )) {
91
+ if (isStashValid (contribution )) {
81
92
chunkInfo .set (contribution .getChunkInfo ());
93
+
94
+ Timber .d ("Chunk: Next Chunk: %s, Total Chunks: %s" ,
95
+ contribution .getChunkInfo ().getIndexOfNextChunkToUpload (),
96
+ contribution .getChunkInfo ().getTotalChunks ());
82
97
}
83
- compositeDisposable .add (fileChunks .forEach (chunkFile -> {
84
- if (pauseUploads ) {
98
+
99
+ final AtomicInteger index = new AtomicInteger ();
100
+ final AtomicBoolean failures = new AtomicBoolean ();
101
+
102
+ compositeDisposable .add (Observable .fromIterable (fileChunks ).forEach (chunkFile -> {
103
+ if (pauseUploads .get (contribution .getPageId ()) || failures .get ()) {
85
104
return ;
86
105
}
87
- if (chunkInfo .get () != null && index .get () < chunkInfo .get ().getLastChunkIndex ()) {
88
- index .getAndIncrement ();
106
+
107
+ if (chunkInfo .get () != null && index .get () < chunkInfo .get ().getIndexOfNextChunkToUpload ()) {
108
+ index .incrementAndGet ();
109
+ Timber .d ("Chunk: Increment and return: %s" , index .get ());
89
110
return ;
90
111
}
112
+ index .getAndIncrement ();
91
113
final int offset =
92
114
chunkInfo .get () != null ? chunkInfo .get ().getUploadResult ().getOffset () : 0 ;
115
+
116
+ Timber .d ("Chunk: Sending Chunk number: %s, offset: %s" , index .get (), offset );
93
117
final String filekey =
94
118
chunkInfo .get () != null ? chunkInfo .get ().getUploadResult ().getFilekey () : null ;
95
119
@@ -104,17 +128,20 @@ Observable<StashUploadResult> uploadFileToStash(
104
128
offset ,
105
129
filekey ,
106
130
countingRequestBody ).subscribe (uploadResult -> {
107
- chunkInfo .set (new ChunkInfo (uploadResult , index .incrementAndGet (), false ));
131
+ Timber .d ("Chunk: Received Chunk number: %s, offset: %s" , index .get (),
132
+ uploadResult .getOffset ());
133
+ chunkInfo .set (
134
+ new ChunkInfo (uploadResult , index .get (), totalChunks ));
108
135
notificationUpdater .onChunkUploaded (contribution , chunkInfo .get ());
109
136
}, throwable -> {
110
- Timber . e ( throwable , "Error occurred in uploading chunk" );
137
+ failures . set ( true );
111
138
}));
112
139
}));
113
140
114
- chunkInfo .get ().setLastChunkUploaded (true );
115
- notificationUpdater .onChunkUploaded (contribution , chunkInfo .get ());
116
- if (pauseUploads ) {
141
+ if (pauseUploads .get (contribution .getPageId ())) {
117
142
return Observable .just (new StashUploadResult (StashUploadState .PAUSED , null ));
143
+ } else if (failures .get ()) {
144
+ return Observable .just (new StashUploadResult (StashUploadState .FAILED , null ));
118
145
} else if (chunkInfo .get () != null ) {
119
146
return Observable .just (new StashUploadResult (StashUploadState .SUCCESS ,
120
147
chunkInfo .get ().getUploadResult ().getFilekey ()));
@@ -129,8 +156,9 @@ Observable<StashUploadResult> uploadFileToStash(
129
156
* @return
130
157
*/
131
158
private boolean isStashValid (Contribution contribution ) {
132
- return contribution .getDateModified ()
133
- .after (new Date (System .currentTimeMillis () - MAX_CHUNK_AGE ));
159
+ return contribution .getChunkInfo () != null &&
160
+ contribution .getDateModified ()
161
+ .after (new Date (System .currentTimeMillis () - MAX_CHUNK_AGE ));
134
162
}
135
163
136
164
/**
@@ -166,9 +194,10 @@ Observable<UploadResult> uploadChunkToStash(final String filename,
166
194
167
195
/**
168
196
* Dispose the active disposable and sets the pause variable
197
+ * @param pageId
169
198
*/
170
- public void pauseUpload () {
171
- pauseUploads = true ;
199
+ public void pauseUpload (String pageId ) {
200
+ pauseUploads . put ( pageId , true ) ;
172
201
if (!compositeDisposable .isDisposed ()) {
173
202
compositeDisposable .dispose ();
174
203
}
0 commit comments