b0a8bd5489da6bdb444d6f44116fa37a9b0ea274
[pub/Android/ownCloud.git] / oc_framework / src / com / owncloud / android / oc_framework / operations / remote / ReadRemoteFolderOperation.java
1 /* ownCloud Android client application
2 * Copyright (C) 2012-2013 ownCloud Inc.
3 *
4 * This program is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License version 2,
6 * as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 *
16 */
17
18 package com.owncloud.android.oc_framework.operations.remote;
19
20 import java.util.ArrayList;
21
22 import org.apache.http.HttpStatus;
23 import org.apache.jackrabbit.webdav.DavConstants;
24 import org.apache.jackrabbit.webdav.MultiStatus;
25 import org.apache.jackrabbit.webdav.client.methods.PropFindMethod;
26
27 import android.util.Log;
28
29 import com.owncloud.android.oc_framework.network.webdav.WebdavClient;
30 import com.owncloud.android.oc_framework.network.webdav.WebdavEntry;
31 import com.owncloud.android.oc_framework.network.webdav.WebdavUtils;
32 import com.owncloud.android.oc_framework.operations.RemoteFile;
33 import com.owncloud.android.oc_framework.operations.RemoteOperation;
34 import com.owncloud.android.oc_framework.operations.RemoteOperationResult;
35
36 /**
37 * Remote operation performing the read of remote file or folder in the ownCloud server.
38 *
39 * @author David A. Velasco
40 * @author masensio
41 */
42
43 public class ReadRemoteFolderOperation extends RemoteOperation {
44
45 private static final String TAG = ReadRemoteFolderOperation.class.getSimpleName();
46
47 private String mRemotePath;
48 private ArrayList<RemoteFile> mFolderAndFiles;
49
50 /**
51 * Constructor
52 *
53 * @param remotePath Remote path of the file.
54 */
55 public ReadRemoteFolderOperation(String remotePath) {
56 mRemotePath = remotePath;
57 }
58
59 /**
60 * Performs the read operation.
61 *
62 * @param client Client object to communicate with the remote ownCloud server.
63 */
64 @Override
65 protected RemoteOperationResult run(WebdavClient client) {
66 RemoteOperationResult result = null;
67 PropFindMethod query = null;
68
69 try {
70 // remote request
71 query = new PropFindMethod(client.getBaseUri() + WebdavUtils.encodePath(mRemotePath),
72 DavConstants.PROPFIND_ALL_PROP,
73 DavConstants.DEPTH_1);
74 int status = client.executeMethod(query);
75
76 // check and process response
77 if (isMultiStatus(status)) {
78 // get data from remote folder
79 MultiStatus dataInServer = query.getResponseBodyAsMultiStatus();
80 readData(dataInServer, client);
81
82 // Result of the operation
83 result = new RemoteOperationResult(true, status, query.getResponseHeaders());
84 // Add data to the result
85 if (result.isSuccess()) {
86 result.setData(mFolderAndFiles);
87 }
88 } else {
89 // synchronization failed
90 client.exhaustResponse(query.getResponseBodyAsStream());
91 result = new RemoteOperationResult(false, status, query.getResponseHeaders());
92 }
93
94 } catch (Exception e) {
95 result = new RemoteOperationResult(e);
96
97
98 } finally {
99 if (query != null)
100 query.releaseConnection(); // let the connection available for other methods
101 if (result.isSuccess()) {
102 Log.i(TAG, "Synchronized " + mRemotePath + ": " + result.getLogMessage());
103 } else {
104 if (result.isException()) {
105 Log.e(TAG, "Synchronized " + mRemotePath + ": " + result.getLogMessage(), result.getException());
106 } else {
107 Log.e(TAG, "Synchronized " + mRemotePath + ": " + result.getLogMessage());
108 }
109 }
110
111 }
112 return result;
113 }
114
115 public boolean isMultiStatus(int status) {
116 return (status == HttpStatus.SC_MULTI_STATUS);
117 }
118
119 /**
120 * Read the data retrieved from the server about the contents of the target folder
121 *
122 *
123 * @param dataInServer Full response got from the server with the data of the target
124 * folder and its direct children.
125 * @param client Client instance to the remote server where the data were
126 * retrieved.
127 * @return
128 */
129 private void readData(MultiStatus dataInServer, WebdavClient client) {
130 mFolderAndFiles = new ArrayList<RemoteFile>();
131
132 // parse data from remote folder
133 WebdavEntry we = new WebdavEntry(dataInServer.getResponses()[0], client.getBaseUri().getPath());
134 mFolderAndFiles.add(fillOCFile(we));
135
136 // loop to update every child
137 RemoteFile remoteFile = null;
138 for (int i = 1; i < dataInServer.getResponses().length; ++i) {
139 /// new OCFile instance with the data from the server
140 we = new WebdavEntry(dataInServer.getResponses()[i], client.getBaseUri().getPath());
141 remoteFile = fillOCFile(we);
142 mFolderAndFiles.add(remoteFile);
143 }
144
145 }
146
147 /**
148 * Creates and populates a new {@link RemoteFile} object with the data read from the server.
149 *
150 * @param we WebDAV entry read from the server for a WebDAV resource (remote file or folder).
151 * @return New OCFile instance representing the remote resource described by we.
152 */
153 private RemoteFile fillOCFile(WebdavEntry we) {
154 RemoteFile file = new RemoteFile(we.decodedPath());
155 file.setCreationTimestamp(we.createTimestamp());
156 file.setLength(we.contentLength());
157 file.setMimeType(we.contentType());
158 file.setModifiedTimestamp(we.modifiedTimestamp());
159 file.setEtag(we.etag());
160 return file;
161 }
162 }