adding file to db after upload
[pub/Android/ownCloud.git] / src / eu / alefzero / owncloud / files / services / FileUploader.java
1 package eu.alefzero.owncloud.files.services;
2
3 import java.io.File;
4
5 import eu.alefzero.owncloud.AccountUtils;
6 import eu.alefzero.owncloud.R;
7 import eu.alefzero.owncloud.authenticator.AccountAuthenticator;
8 import eu.alefzero.owncloud.datamodel.FileDataStorageManager;
9 import eu.alefzero.owncloud.datamodel.OCFile;
10 import eu.alefzero.owncloud.files.interfaces.OnDatatransferProgressListener;
11 import eu.alefzero.owncloud.utils.OwnCloudVersion;
12 import eu.alefzero.webdav.OnUploadProgressListener;
13 import eu.alefzero.webdav.WebdavClient;
14 import android.accounts.Account;
15 import android.accounts.AccountManager;
16 import android.app.Notification;
17 import android.app.NotificationManager;
18 import android.app.Service;
19 import android.content.Intent;
20 import android.net.Uri;
21 import android.os.Handler;
22 import android.os.HandlerThread;
23 import android.os.IBinder;
24 import android.os.Looper;
25 import android.os.Message;
26 import android.os.Process;
27 import android.util.Log;
28 import android.webkit.MimeTypeMap;
29 import android.widget.RemoteViews;
30 import android.widget.Toast;
31
32 public class FileUploader extends Service implements OnDatatransferProgressListener {
33
34 public static final String KEY_LOCAL_FILE = "LOCAL_FILE";
35 public static final String KEY_REMOTE_FILE = "REMOTE_FILE";
36 public static final String KEY_ACCOUNT = "ACCOUNT";
37 public static final String KEY_UPLOAD_TYPE = "UPLOAD_TYPE";
38
39 public static final int UPLOAD_SINGLE_FILE = 0;
40 public static final int UPLOAD_MULTIPLE_FILES = 1;
41
42 private static final String TAG = "FileUploader";
43 private NotificationManager mNotificationManager;
44 private Looper mServiceLooper;
45 private ServiceHandler mServiceHandler;
46 private AccountManager mAccountManager;
47 private Account mAccount;
48 private String[] mLocalPaths, mRemotePaths;
49 private boolean mResult;
50 private int mUploadType;
51 private Notification mNotification;
52 private int mTotalDataToSend, mSendData;
53 private int mCurrentIndexUpload, mPreviousPercent;
54
55 @Override
56 public IBinder onBind(Intent arg0) {
57 return null;
58 }
59
60 private final class ServiceHandler extends Handler {
61 public ServiceHandler(Looper looper) {
62 super(looper);
63 }
64
65 @Override
66 public void handleMessage(Message msg) {
67 uploadFile();
68 stopSelf(msg.arg1);
69 }
70 }
71
72 @Override
73 public void onCreate() {
74 super.onCreate();
75 mNotificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
76 HandlerThread thread = new HandlerThread("FileUploaderThread",
77 Process.THREAD_PRIORITY_BACKGROUND);
78 thread.start();
79 mServiceLooper = thread.getLooper();
80 mServiceHandler = new ServiceHandler(mServiceLooper);
81 mAccountManager = AccountManager.get(this);
82 }
83
84 @Override
85 public int onStartCommand(Intent intent, int flags, int startId) {
86 if (!intent.hasExtra(KEY_ACCOUNT) && !intent.hasExtra(KEY_UPLOAD_TYPE)) {
87 Log.e(TAG, "Not enought data in intent provided");
88 return Service.START_NOT_STICKY;
89 }
90 mAccount = intent.getParcelableExtra(KEY_ACCOUNT);
91 mUploadType = intent.getIntExtra(KEY_UPLOAD_TYPE, -1);
92 if (mUploadType == -1) {
93 Log.e(TAG, "Incorrect upload type provided");
94 return Service.START_NOT_STICKY;
95 }
96 if (mUploadType == UPLOAD_SINGLE_FILE) {
97 mLocalPaths = new String[] { intent.getStringExtra(KEY_LOCAL_FILE) };
98 mRemotePaths = new String[] { intent
99 .getStringExtra(KEY_REMOTE_FILE) };
100 } else { // mUploadType == UPLOAD_MULTIPLE_FILES
101 mLocalPaths = intent.getStringArrayExtra(KEY_LOCAL_FILE);
102 mRemotePaths = intent.getStringArrayExtra(KEY_REMOTE_FILE);
103 }
104
105 for (int i = 0; i < mRemotePaths.length; ++i)
106 mRemotePaths[i] = mRemotePaths[i].replace(' ', '+');
107
108 if (mLocalPaths.length != mRemotePaths.length) {
109 Log.e(TAG, "Remote paths and local paths are not equal!");
110 return Service.START_NOT_STICKY;
111 }
112
113 Message msg = mServiceHandler.obtainMessage();
114 msg.arg1 = startId;
115 mServiceHandler.sendMessage(msg);
116
117 return Service.START_NOT_STICKY;
118 }
119
120 public void run() {
121 if (mResult) {
122 Toast.makeText(this, "Upload successfull", Toast.LENGTH_SHORT)
123 .show();
124 } else {
125 Toast.makeText(this, "No i kupa", Toast.LENGTH_SHORT).show();
126 }
127 }
128
129 public void uploadFile() {
130 String baseUrl = mAccountManager.getUserData(mAccount,
131 AccountAuthenticator.KEY_OC_BASE_URL), ocVerStr = mAccountManager
132 .getUserData(mAccount, AccountAuthenticator.KEY_OC_VERSION);
133 OwnCloudVersion ocVer = new OwnCloudVersion(ocVerStr);
134 String webdav_path = AccountUtils.getWebdavPath(ocVer);
135 Uri ocUri = Uri.parse(baseUrl + webdav_path);
136 String username = mAccount.name.substring(0,
137 mAccount.name.lastIndexOf('@'));
138 String password = mAccountManager.getPassword(mAccount);
139 FileDataStorageManager storageManager = new FileDataStorageManager(mAccount, getContentResolver());
140
141 mTotalDataToSend = mSendData = mPreviousPercent = 0;
142
143 mNotification = new Notification(
144 eu.alefzero.owncloud.R.drawable.icon, "Uploading...",
145 System.currentTimeMillis());
146 mNotification.flags |= Notification.FLAG_ONGOING_EVENT;
147 mNotification.contentView = new RemoteViews(getApplicationContext().getPackageName(), R.layout.progressbar_layout);
148 mNotification.contentView.setProgressBar(R.id.status_progress, 100, 0, false);
149 mNotification.contentView.setImageViewResource(R.id.status_icon, R.drawable.icon);
150
151 mNotificationManager.notify(42, mNotification);
152
153 WebdavClient wc = new WebdavClient(ocUri);
154 wc.allowSelfsignedCertificates();
155 wc.setDataTransferProgressListener(this);
156 wc.setCredentials(username, password);
157
158 for (int i = 0; i < mLocalPaths.length; ++i) {
159 File f = new File(mLocalPaths[i]);
160 mTotalDataToSend += f.length();
161 }
162
163 Log.d(TAG, "Will upload " + mTotalDataToSend + " bytes, with " + mLocalPaths.length + " files");
164
165 for (int i = 0; i < mLocalPaths.length; ++i) {
166 String mimeType = MimeTypeMap.getSingleton()
167 .getMimeTypeFromExtension(
168 mLocalPaths[i].substring(mLocalPaths[i]
169 .lastIndexOf('.') + 1));
170 mResult = false;
171 mCurrentIndexUpload = i;
172 if (wc.putFile(mLocalPaths[i], mRemotePaths[i], mimeType)) {
173 mResult |= true;
174 OCFile new_file = new OCFile(mRemotePaths[i]);
175 new_file.setMimetype(mimeType);
176 new_file.setFileLength(new File(mLocalPaths[i]).length());
177 new_file.setModificationTimestamp(System.currentTimeMillis());
178 new_file.setLastSyncDate(0);
179 new_file.setStoragePath(mLocalPaths[i]);
180 new_file.setParentId(storageManager.getFileByPath(mRemotePaths[i].substring(0, mRemotePaths[i].lastIndexOf('/')+1)).getFileId());
181 storageManager.saveFile(new_file);
182 }
183 }
184 // notification.contentView.setProgressBar(R.id.status_progress,
185 // mLocalPaths.length-1, mLocalPaths.length-1, false);
186 mNotificationManager.cancel(42);
187 run();
188 }
189
190 @Override
191 public void transferProgress(long progressRate) {
192 mSendData += progressRate;
193 int percent = (int)(100*((double)mSendData)/((double)mTotalDataToSend));
194 if (percent != mPreviousPercent) {
195 String text = String.format("%d%% Uploading %s file", percent, new File(mLocalPaths[mCurrentIndexUpload]).getName());
196 mNotification.contentView.setProgressBar(R.id.status_progress, 100, percent, false);
197 mNotification.contentView.setTextViewText(R.id.status_text, text);
198 mNotificationManager.notify(42, mNotification);
199 }
200 mPreviousPercent = percent;
201 }
202 }