1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 package org.waarp.http.protocol;
22
23 import org.waarp.common.database.data.AbstractDbData.UpdatedInfo;
24 import org.waarp.common.database.exception.WaarpDatabaseException;
25 import org.waarp.common.digest.FilesystemBasedDigest;
26 import org.waarp.common.digest.FilesystemBasedDigest.DigestAlgo;
27 import org.waarp.common.logging.WaarpLogger;
28 import org.waarp.common.logging.WaarpLoggerFactory;
29 import org.waarp.common.utility.WaarpSystemUtil;
30 import org.waarp.http.protocol.servlet.HttpAuthent;
31 import org.waarp.openr66.context.ErrorCode;
32 import org.waarp.openr66.context.R66BusinessInterface;
33 import org.waarp.openr66.context.R66FiniteDualStates;
34 import org.waarp.openr66.context.task.exception.OpenR66RunnerErrorException;
35 import org.waarp.openr66.database.data.DbTaskRunner;
36 import org.waarp.openr66.protocol.configuration.Configuration;
37
38 import java.io.File;
39 import java.io.FileInputStream;
40 import java.io.IOException;
41 import java.io.OutputStream;
42
43 import static org.waarp.openr66.context.R66FiniteDualStates.*;
44
45
46
47
48 public class HttpDownloadSession extends HttpSessionAbstract {
49 private static final WaarpLogger logger =
50 WaarpLoggerFactory.getLogger(HttpDownloadSession.class);
51 protected static final String HASH = "HASH";
52 private final String filename;
53 private final String rulename;
54 private final String comment;
55 private final String identifier;
56 private final String finalFilename;
57 private final long filesize;
58 private final DbTaskRunner runner;
59
60
61
62
63
64
65
66
67
68
69
70
71 public HttpDownloadSession(final String filename, final String rulename,
72 final String identifier, final String comment,
73 final HttpAuthent authent)
74 throws IllegalArgumentException {
75 super(authent);
76 this.filename = filename;
77 this.rulename = rulename;
78 this.comment = comment;
79 this.identifier = identifier;
80 if (!WaarpSystemUtil.isJunit()) {
81 final R66BusinessInterface business =
82 checkAuthentR66Business(this, session, authent);
83 runner =
84 getDbTaskRunner(authent.getUserId(), rulename, identifier, comment,
85 business);
86 final File file = session.getFile().getTrueFile();
87 this.finalFilename = identifier + "_" + file.getName();
88 filesize = file.length();
89 logger.info("START: {}", this);
90 preTasks(business, runner);
91 } else {
92 runner = null;
93 this.finalFilename = "NOID" + "_" + filename;
94 this.filesize = 0;
95 }
96 }
97
98
99
100
101
102
103
104 public HttpDownloadSession(final String identifier, final HttpAuthent authent)
105 throws WaarpDatabaseException {
106 super(authent);
107 this.filename = "nofile";
108 this.rulename = "norule";
109 this.comment = "nocomment";
110 this.identifier = identifier;
111 if (!WaarpSystemUtil.isJunit()) {
112 final R66BusinessInterface business =
113 checkAuthentR66Business(this, session, authent);
114
115 runner = getDbTaskRunner(authent.getUserId(), identifier);
116 this.finalFilename = identifier + "_" + filename;
117 } else {
118 runner = null;
119 this.finalFilename = "NOID" + "_" + filename;
120 }
121 this.filesize = 0;
122 }
123
124 public final boolean isFinished() {
125 return runner != null && runner.isFinished();
126 }
127
128 public final boolean isTransmitting() {
129 return runner != null &&
130 runner.getUpdatedInfo().equals(UpdatedInfo.RUNNING) &&
131 this.filesize == 0;
132 }
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147 private DbTaskRunner getDbTaskRunner(final String user, final String rulename,
148 final String identifier,
149 final String comment,
150 final R66BusinessInterface business)
151 throws IllegalArgumentException {
152 final long specialId = Long.parseLong(identifier);
153 return getDbTaskRunner(user, filename, rulename, specialId, comment,
154 Configuration.configuration.getBlockSize(), business,
155 false);
156 }
157
158
159
160
161
162
163
164
165
166
167
168 private DbTaskRunner getDbTaskRunner(final String user,
169 final String identifier)
170 throws IllegalArgumentException, WaarpDatabaseException {
171 final long specialId = Long.parseLong(identifier);
172 final String requested = Configuration.configuration.getHostId();
173 DbTaskRunner runner = null;
174
175
176 try {
177 logger.debug("{} {} <-> {}", specialId, user, requested);
178 runner = new DbTaskRunner(specialId, user, requested);
179 } catch (final WaarpDatabaseException e) {
180 logger.debug("{} {} {}", specialId, user, requested);
181 runner = new DbTaskRunner(specialId, requested, user);
182 }
183 runner.setSender(true);
184 try {
185 session.setRunner(runner);
186 } catch (final OpenR66RunnerErrorException e) {
187 logger.debug(e);
188 }
189 session.setReady(true);
190 return runner;
191 }
192
193
194
195
196 public final String getFinalName() {
197 return finalFilename;
198 }
199
200
201
202
203 public final long getFileSize() {
204 return filesize;
205 }
206
207
208
209
210 public final String getIdentifier() {
211 return identifier;
212 }
213
214
215
216
217 public final String getHash() {
218 final File file = session.getFile().getTrueFile();
219 final byte[] bin;
220 try {
221 bin = FilesystemBasedDigest.getHash(file, false, DigestAlgo.SHA256);
222 } catch (final IOException e) {
223 logger.warn(e);
224 return null;
225 }
226 final String hash = FilesystemBasedDigest.getHex(bin);
227 session.getRunner().addToTransferMap(HASH, hash);
228 try {
229 session.getRunner().saveStatus();
230 } catch (final OpenR66RunnerErrorException e) {
231 logger.debug(e);
232 }
233 return hash;
234 }
235
236
237
238
239 public final String getComputedHadh() {
240 final String hash = (String) session.getRunner().getFromTransferMap(HASH);
241 logger.debug("Found {}", hash);
242 return hash;
243 }
244
245 @Override
246 public final void error(final Exception e,
247 final R66BusinessInterface business)
248 throws IllegalArgumentException {
249 logger.error(e.getMessage());
250 if (business != null) {
251 business.checkAtError(session);
252 }
253 session.newState(R66FiniteDualStates.ERROR);
254 throw new IllegalArgumentException(e);
255 }
256
257
258
259
260
261
262
263
264
265
266 public final boolean tryWrite(final OutputStream stream) throws IOException {
267 if (!session.isAuthenticated() || !session.isReady()) {
268 logger.error("Not authenticated or not Ready");
269 return false;
270 }
271 write(stream);
272 return true;
273 }
274
275
276
277
278
279
280
281
282 private void write(final OutputStream stream) throws IOException {
283 startTransfer(runner);
284 final File file = session.getFile().getTrueFile();
285 final FileInputStream inputStream = new FileInputStream(file);
286 try {
287 final byte[] bytes = new byte[Configuration.configuration.getBlockSize()];
288 while (true) {
289 final int r = inputStream.read(bytes);
290 if (r < 0) {
291 break;
292 }
293 stream.write(bytes, 0, r);
294 session.getRunner().incrementRank();
295 }
296 } catch (final IOException e) {
297 session.getRunner().setErrorExecutionStatus(ErrorCode.TransferError);
298 session.getRunner().setErrorTask();
299 try {
300 session.getRunner().run();
301 session.getRunner().saveStatus();
302 } catch (final OpenR66RunnerErrorException ex) {
303 logger.info(e);
304 }
305 session.newState(R66FiniteDualStates.ERROR);
306 throw e;
307 } finally {
308 inputStream.close();
309 stream.flush();
310 stream.close();
311 }
312
313 }
314
315
316
317
318 public final void downloadFinished() {
319 if (session.getState() == CLOSEDCHANNEL) {
320 return;
321 }
322 logger.debug("Final block received! {}", session);
323 runPostTask();
324 authent.finalizeTransfer(this, session);
325 }
326
327 @Override
328 public String toString() {
329 return "DS: {" + session.toString() + ", " + filename + ", " + rulename +
330 ", " + identifier + ", " + comment + ", " + finalFilename + "}";
331 }
332 }