diff --git a/app/build.gradle b/app/build.gradle
index 4c9120fe5..556ea79e3 100644
--- a/app/build.gradle
+++ b/app/build.gradle
@@ -38,9 +38,9 @@ repositories {
// Version number
def versionMajor = 5 // Major UI overhauls
-def versionMinor = 6 // Some new functionality
+def versionMinor = 7 // Some new functionality
def versionPatch = 0 // Bug fixes
-def versionBuild = 0 // Bump for dogfood builds, public betas, etc.
+def versionBuild = 1 // Bump for dogfood builds, public betas, etc.
// Version name from git
def getVersionName = { ->
@@ -64,6 +64,11 @@ android {
abortOnError false
}
+ packagingOptions {
+ exclude 'META-INF/LICENSE.txt'
+ exclude 'META-INF/NOTICE.txt'
+ }
+
defaultConfig {
applicationId "com.nononsenseapps.notepad"
minSdkVersion 14
@@ -129,20 +134,6 @@ apt {
}
}
-// Dropbox
-task nativeLibsToJar(type: Zip) {
- destinationDir file("$buildDir/native-libs")
- baseName 'native-libs'
- extension 'jar'
- from fileTree(dir: 'src/play/libs', include: '**/*.so')
- into 'lib/'
-}
-
-// If non-free, depend on dropbox
-tasks.withType(JavaCompile) {
- compileTask -> if (compileTask.toString().contains("Play")) compileTask.dependsOn(nativeLibsToJar)
-}
-
dependencies {
//compile fileTree(dir: 'libs', include: '*.jar')
compile 'com.android.support:support-v4:19.0.1'
@@ -164,9 +155,7 @@ dependencies {
// Dropbox and non-free stuff
playCompile fileTree(dir: 'src/play/libs', include: '*.jar')
playBetaCompile fileTree(dir: 'src/play/libs', include: '*.jar')
- playCompile fileTree(dir: "$buildDir/native-libs", include: "*.jar")
playCompile 'com.google.android.gms:play-services:5.0.89'
- playBetaCompile fileTree(dir: "$buildDir/native-libs", include: "*.jar")
playBetaCompile 'com.google.android.gms:play-services:5.0.89'
// Tests
androidTestCompile 'com.squareup.spoon:spoon-client:1.1.1'
diff --git a/app/src/androidTest/java/com/nononsenseapps/notepad/test/ConfigTest.java b/app/src/androidTest/java/com/nononsenseapps/notepad/test/ConfigTest.java
index 7611c7c0e..1317c4e2d 100644
--- a/app/src/androidTest/java/com/nononsenseapps/notepad/test/ConfigTest.java
+++ b/app/src/androidTest/java/com/nononsenseapps/notepad/test/ConfigTest.java
@@ -56,10 +56,10 @@ public void testProps() {
assertNotNull(Config.getGtasksApiKey(context));
assertFalse(Config.getGtasksApiKey(context).isEmpty());
- assertNotNull(Config.getKeyDropboxSyncPublic(context));
- assertFalse(Config.getKeyDropboxSyncPublic(context).isEmpty());
+ assertNotNull(Config.getKeyDropboxAPI(context));
+ assertFalse(Config.getKeyDropboxAPI(context).isEmpty());
- assertNotNull(Config.getKeyDropboxSyncSecret(context));
- assertFalse(Config.getKeyDropboxSyncSecret(context).isEmpty());
+ assertNotNull(Config.getKeyDropboxAPISecret(context));
+ assertFalse(Config.getKeyDropboxAPISecret(context).isEmpty());
}
}
diff --git a/app/src/free/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSyncHelper.java b/app/src/free/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSyncHelper.java
index 2574da52f..7180c7bd2 100644
--- a/app/src/free/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSyncHelper.java
+++ b/app/src/free/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSyncHelper.java
@@ -1,17 +1,18 @@
/*
- * Copyright (c) 2014 Jonas Kalderstam.
+ * Copyright (c) 2015 Jonas Kalderstam.
*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
*
- * http://www.apache.org/licenses/LICENSE-2.0
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
*
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see .
*/
package com.nononsenseapps.notepad.sync.orgsync;
@@ -22,11 +23,24 @@
* Dummy file, see play flavor.
*/
public class DropboxSyncHelper {
- public static boolean hasSynced(Activity activity) {
+
+ public DropboxSyncHelper(Activity activity) {
+
+ }
+
+ public boolean isLinked() {
return false;
}
- public static void doFirstSync(Activity activity) {
+ public void linkAccount() {
+
+ }
+
+ public void unlinkAccount() {
}
+
+ public boolean handleLinkResult() {
+ return false;
+ }
}
diff --git a/app/src/main/java/com/nononsenseapps/build/Config.java b/app/src/main/java/com/nononsenseapps/build/Config.java
index c07980877..ec9dc4e7e 100644
--- a/app/src/main/java/com/nononsenseapps/build/Config.java
+++ b/app/src/main/java/com/nononsenseapps/build/Config.java
@@ -32,8 +32,8 @@ public class Config {
public final static boolean LOGGING = true;
public static final String KEY_GTASKS_API_KEY = "gtasks_api_key";
- public static final String KEY_DROPBOX_SYNC_PUBLIC = "dropbox_sync_public";
- public static final String KEY_DROPBOX_SYNC_SECRET = "dropbox_sync_secret";
+ public static final String KEY_DROPBOX_API = "dropbox_api";
+ public static final String KEY_DROPBOX_API_SECRET = "dropbox_api_secret";
private static final String propFile = "secretkeys.properties";
private static Properties props;
@@ -59,11 +59,11 @@ public static String getGtasksApiKey(final Context context) {
"AIzaSyCAjRk2GfPARlIU3JsaEiExLMtj_rdN2i4");
}
- public static String getKeyDropboxSyncPublic(final Context context) {
- return getProperties(context).getProperty(KEY_DROPBOX_SYNC_PUBLIC);
+ public static String getKeyDropboxAPI(final Context context) {
+ return getProperties(context).getProperty(KEY_DROPBOX_API);
}
- public static String getKeyDropboxSyncSecret(final Context context) {
- return getProperties(context).getProperty(KEY_DROPBOX_SYNC_SECRET);
+ public static String getKeyDropboxAPISecret(final Context context) {
+ return getProperties(context).getProperty(KEY_DROPBOX_API_SECRET);
}
}
diff --git a/app/src/main/java/com/nononsenseapps/notepad/prefs/SyncPrefs.java b/app/src/main/java/com/nononsenseapps/notepad/prefs/SyncPrefs.java
index 4310d6aea..9e9f6a89d 100644
--- a/app/src/main/java/com/nononsenseapps/notepad/prefs/SyncPrefs.java
+++ b/app/src/main/java/com/nononsenseapps/notepad/prefs/SyncPrefs.java
@@ -79,7 +79,6 @@ public class SyncPrefs extends PreferenceFragment implements
public static final String KEY_DROPBOX_ENABLE = "pref_sync_dropbox_enabled";
public static final String KEY_DROPBOX_DIR = "pref_sync_dropbox_dir";
private static final int PICK_SD_DIR_CODE = 1;
- private static final int DROPBOX_LINK_CODE = 3895;
private static final int PICK_DROPBOX_DIR_CODE = 2;
@@ -88,6 +87,7 @@ public class SyncPrefs extends PreferenceFragment implements
private Preference prefAccount;
private Preference prefSdDir;
private Preference prefDropboxDir;
+ private DropboxSyncHelper mDropboxHelper = null;
// private Preference prefSyncFreq;
@@ -200,9 +200,9 @@ public boolean onPreferenceClick(final Preference preference) {
// Dropbox, disable if no key present
findPreference(KEY_DROPBOX_ENABLE)
.setEnabled(BuildConfig.DROPBOX_ENABLED &&
- Config.getKeyDropboxSyncSecret(getActivity()) !=
+ Config.getKeyDropboxAPI(getActivity()) !=
null &&
- !Config.getKeyDropboxSyncSecret(getActivity())
+ !Config.getKeyDropboxAPISecret(getActivity())
.contains(" "));
prefDropboxDir = findPreference(KEY_DROPBOX_DIR);
prefDropboxDir.setEnabled(BuildConfig.DROPBOX_ENABLED);
@@ -213,7 +213,10 @@ public boolean onPreferenceClick(final Preference preference) {
public boolean onPreferenceClick(
final Preference preference) {
// See if initial sync is complete
- if (DropboxSyncHelper.hasSynced(getActivity())) {
+ if (mDropboxHelper == null) {
+ mDropboxHelper = new DropboxSyncHelper(getActivity());
+ }
+ if (mDropboxHelper.isLinked()) {
// Start the filepicker
Intent i = new Intent(getActivity(),
DropboxFilePickerActivity.class);
@@ -232,13 +235,6 @@ public boolean onPreferenceClick(
startActivityForResult(i,
PICK_DROPBOX_DIR_CODE);
- } else {
- // Start first sync
- DropboxSyncHelper.doFirstSync(getActivity());
- // Notify the user to wait
- Toast.makeText(getActivity(),
- R.string.wait_for_dropbox,
- Toast.LENGTH_SHORT).show();
}
return true;
@@ -292,11 +288,18 @@ public void onSharedPreferenceChanged(SharedPreferences prefs,
} else if (KEY_SD_DIR.equals(key)) {
setSdDirSummary(prefs);
} else if (KEY_DROPBOX_ENABLE.equals(key)) {
+ // TODO
+ if (mDropboxHelper == null) {
+ mDropboxHelper = new DropboxSyncHelper(getActivity());
+ }
if (prefs.getBoolean(key, false)) {
- DropboxSynchronizer.linkAccount(this,
- DROPBOX_LINK_CODE);
+ // authorize the user
+ mDropboxHelper.linkAccount();
+// DropboxSynchronizer.linkAccount(this,
+// DROPBOX_LINK_CODE);
} else {
- DropboxSynchronizer.unlink(getActivity());
+ mDropboxHelper.unlinkAccount();
+// DropboxSynchronizer.unlink(getActivity());
}
// Restart sync service
OrgSyncService.stop(getActivity());
@@ -315,17 +318,23 @@ public void onSharedPreferenceChanged(SharedPreferences prefs,
}
@Override
- public void onActivityResult(int requestCode, int resultCode, Intent data) {
- if (requestCode == DROPBOX_LINK_CODE) {
- if (resultCode == Activity.RESULT_OK) {
- // Start first sync
- DropboxSyncHelper.doFirstSync(getActivity());
+ public void onResume() {
+ super.onResume();
+
+ if (mDropboxHelper != null) {
+ if (mDropboxHelper.handleLinkResult()) {
+ // Success
} else {
- // ... Link failed or was cancelled by the user.
+ // Link failed or was cancelled by the user.
PreferenceManager.getDefaultSharedPreferences(getActivity()).edit()
.putBoolean(KEY_DROPBOX_ENABLE, false).commit();
}
- } else if (requestCode == PICK_DROPBOX_DIR_CODE) {
+ }
+ }
+
+ @Override
+ public void onActivityResult(int requestCode, int resultCode, Intent data) {
+ if (requestCode == PICK_DROPBOX_DIR_CODE) {
if (resultCode == Activity.RESULT_OK) {
PreferenceManager.getDefaultSharedPreferences(getActivity
()).edit().putString(KEY_DROPBOX_DIR,
diff --git a/app/src/main/java/com/nononsenseapps/notepad/sync/orgsync/OrgSyncService.java b/app/src/main/java/com/nononsenseapps/notepad/sync/orgsync/OrgSyncService.java
index 9e1aa77de..6a4f75fa0 100644
--- a/app/src/main/java/com/nononsenseapps/notepad/sync/orgsync/OrgSyncService.java
+++ b/app/src/main/java/com/nononsenseapps/notepad/sync/orgsync/OrgSyncService.java
@@ -284,6 +284,7 @@ public void handleMessage(Message msg) {
}
} catch (IOException ignored) {
+ Log.e(TAG, ignored.getMessage());
} catch (ParseException ignored) {
}
}
diff --git a/app/src/main/java/com/nononsenseapps/notepad/sync/orgsync/SynchronizerInterface.java b/app/src/main/java/com/nononsenseapps/notepad/sync/orgsync/SynchronizerInterface.java
index 8d08aa91b..4c4a17632 100644
--- a/app/src/main/java/com/nononsenseapps/notepad/sync/orgsync/SynchronizerInterface.java
+++ b/app/src/main/java/com/nononsenseapps/notepad/sync/orgsync/SynchronizerInterface.java
@@ -78,7 +78,7 @@ public OrgFile getNewFile(final String desiredName) throws IOException,
* @param orgFile
* The file to delete.
*/
- public void deleteRemoteFile(final OrgFile orgFile);
+ public void deleteRemoteFile(final OrgFile orgFile) throws IOException;
/**
* Rename the file on the remote end.
@@ -88,7 +88,7 @@ public OrgFile getNewFile(final String desiredName) throws IOException,
* @param orgFile
* This contains the new name.
*/
- public void renameRemoteFile(final String oldName, final OrgFile orgFile);
+ public void renameRemoteFile(final String oldName, final OrgFile orgFile) throws IOException;
/**
* Returns a BufferedReader to the remote file. Null if it doesn't exist.
@@ -96,13 +96,13 @@ public OrgFile getNewFile(final String desiredName) throws IOException,
* @param filename
* Name of the file, without path
*/
- public BufferedReader getRemoteFile(final String filename);
+ public BufferedReader getRemoteFile(final String filename) throws IOException;
/**
*
* @return a set of all remote files.
*/
- public HashSet getRemoteFilenames();
+ public HashSet getRemoteFilenames() throws IOException;
/**
* Do a full 2-way sync.
diff --git a/app/src/play/AndroidManifest.xml b/app/src/play/AndroidManifest.xml
index 22012ce3a..c79bf2671 100644
--- a/app/src/play/AndroidManifest.xml
+++ b/app/src/play/AndroidManifest.xml
@@ -98,30 +98,19 @@
android:label="@string/app_name"
android:theme="@style/FilePicker.Theme">
-
-
+ android:launchMode="singleTask"
+ android:configChanges="orientation|keyboard" >
-
-
-
diff --git a/app/src/play/java/com/nononsenseapps/filepicker/DropboxFilePickerActivity.java b/app/src/play/java/com/nononsenseapps/filepicker/DropboxFilePickerActivity.java
index f80c23303..2ae42c440 100644
--- a/app/src/play/java/com/nononsenseapps/filepicker/DropboxFilePickerActivity.java
+++ b/app/src/play/java/com/nononsenseapps/filepicker/DropboxFilePickerActivity.java
@@ -18,30 +18,21 @@
import android.os.Bundle;
-import com.dropbox.sync.android.DbxAccountManager;
-import com.dropbox.sync.android.DbxException;
-import com.dropbox.sync.android.DbxFileSystem;
-import com.dropbox.sync.android.DbxPath;
-import com.nononsenseapps.build.Config;
+import com.dropbox.client2.DropboxAPI;
+import com.dropbox.client2.android.AndroidAuthSession;
+import com.nononsenseapps.notepad.sync.orgsync.DropboxSyncHelper;
public class DropboxFilePickerActivity extends
- AbstractFilePickerActivity {
+ AbstractFilePickerActivity {
- private DbxFileSystem fs;
+ // In the class declaration section:
+ private DropboxAPI mDBApi;
@Override
- public void onCreate(Bundle b) {// Make sure we are linked
- DbxAccountManager accountManager = DbxAccountManager.getInstance(getApplicationContext(),
- Config.getKeyDropboxSyncPublic(this),
- Config.getKeyDropboxSyncSecret(this));
-
- if (accountManager.hasLinkedAccount()) {
- try {
- fs = DbxFileSystem.forAccount(accountManager.getLinkedAccount());
- } catch (DbxException.Unauthorized unauthorized) {
- finish();
- }
- } else {
+ public void onCreate(Bundle b) {
+ mDBApi = DropboxSyncHelper.getDBApi(this);
+ if (!mDBApi.getSession().isLinked()) {
+ // No valid authentication
finish();
}
@@ -49,12 +40,19 @@ public void onCreate(Bundle b) {// Make sure we are linked
}
@Override
- protected AbstractFilePickerFragment getFragment(final String startPath,
- final int mode,
- final boolean allowMultiple,
- final boolean allowCreateDir) {
- DropboxFilePickerFragment fragment = new DropboxFilePickerFragment(fs);
+ protected AbstractFilePickerFragment getFragment(
+ final String startPath, final int mode, final boolean allowMultiple,
+ final boolean allowCreateDir) {
+ if (mDBApi == null || !mDBApi.getSession().isLinked()) {
+ // No valid authentication
+ finish();
+ return null;
+ }
+
+ DropboxFilePickerFragment fragment =
+ new DropboxFilePickerFragment(mDBApi);
fragment.setArgs(startPath, mode, allowMultiple, allowCreateDir);
return fragment;
}
+
}
diff --git a/app/src/play/java/com/nononsenseapps/filepicker/DropboxFilePickerFragment.java b/app/src/play/java/com/nononsenseapps/filepicker/DropboxFilePickerFragment.java
index 40598f301..0171ac388 100644
--- a/app/src/play/java/com/nononsenseapps/filepicker/DropboxFilePickerFragment.java
+++ b/app/src/play/java/com/nononsenseapps/filepicker/DropboxFilePickerFragment.java
@@ -20,114 +20,160 @@
import android.content.AsyncTaskLoader;
import android.content.Loader;
import android.net.Uri;
+import android.os.AsyncTask;
import android.widget.Toast;
-import com.dropbox.sync.android.DbxException;
-import com.dropbox.sync.android.DbxFileInfo;
-import com.dropbox.sync.android.DbxFileSystem;
-import com.dropbox.sync.android.DbxPath;
+import com.dropbox.client2.DropboxAPI;
+import com.dropbox.client2.android.AndroidAuthSession;
+import com.dropbox.client2.exception.DropboxException;
import com.nononsenseapps.notepad.R;
+import java.io.File;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
@SuppressLint("ValidFragment")
-public class DropboxFilePickerFragment extends
- AbstractFilePickerFragment {
+public class DropboxFilePickerFragment
+ extends AbstractFilePickerFragment {
- private final DbxFileSystem fs;
+ private final DropboxAPI dbApi;
+ private FolderCreator folderCreator;
@SuppressLint("ValidFragment")
- public DropboxFilePickerFragment(final DbxFileSystem fs) {
+ public DropboxFilePickerFragment(final DropboxAPI api) {
super();
- if (fs == null) {
+ if (api == null) {
throw new NullPointerException("FileSystem may not be null");
+ } else if (!api.getSession().isLinked()) {
+ throw new IllegalArgumentException("Must be linked with Dropbox");
}
- this.fs = fs;
+
+ this.dbApi = api;
}
- @Override
- protected boolean isDir(final DbxPath dbxPath) {
- try {
- return fs.isFolder(dbxPath);
- } catch (DbxException e) {
- return false;
+ public void onNewFolder(final String name) {
+ File folder = new File(currentPath.path, name);
+
+ if (folderCreator == null) {
+ folderCreator = new FolderCreator();
+ }
+
+ folderCreator.execute(folder.getPath());
+ }
+
+ private class FolderCreator extends AsyncTask {
+
+ @Override
+ protected Void doInBackground(final String... paths) {
+ for (String path : paths) {
+ try {
+ dbApi.createFolder(path);
+ currentPath = dbApi.metadata(path, 1, null, false, null);
+ refresh();
+ } catch (DropboxException e) {
+ Toast.makeText(getActivity(), R.string.create_folder_error,
+ Toast.LENGTH_SHORT).show();
+ }
+ }
+ return null;
}
}
@Override
- protected DbxPath getParent(final DbxPath dbxPath) {
- DbxPath parent = dbxPath.getParent();
- if (parent == null) {
- parent = dbxPath;
+ protected boolean isDir(final DropboxAPI.Entry file) {
+ return file.isDir;
+ }
+
+ @Override
+ protected DropboxAPI.Entry getParent(final DropboxAPI.Entry from) {
+ // Take care of a slight limitation in Dropbox code:
+ if (from.path.length() > 1 && from.path.endsWith("/")) {
+ from.path = from.path.substring(0, from.path.length() - 1);
}
+ String parent = from.parentPath();
+ if (parent.isEmpty()) {
+ parent = "/";
+ }
+
+ return getPath(parent);
- return parent;
}
@Override
- protected DbxPath getPath(final String s) {
- return new DbxPath(s);
+ protected DropboxAPI.Entry getPath(final String path) {
+ final DropboxAPI.Entry entry = new DropboxAPI.Entry();
+ entry.path = path;
+ entry.isDir = true;
+ return entry;
+
}
@Override
- protected String getFullPath(final DbxPath dbxPath) {
- return dbxPath.toString();
+ protected String getFullPath(final DropboxAPI.Entry file) {
+ return file.path;
}
@Override
- protected String getName(final DbxPath dbxPath) {
- return dbxPath.getName();
+ protected String getName(final DropboxAPI.Entry file) {
+ return file.fileName();
}
@Override
- protected DbxPath getRoot() {
- return new DbxPath("/");
+ protected DropboxAPI.Entry getRoot() {
+ return getPath("/");
}
@Override
- protected Uri toUri(final DbxPath dbxPath) {
- return new Uri.Builder().scheme("dropbox")
- .path(dbxPath.toString()).build();
+ protected Uri toUri(final DropboxAPI.Entry file) {
+ return new Uri.Builder().scheme("dropbox").path(file.path).build();
}
@Override
- protected Comparator getComparator() {
- return new Comparator() {
+ protected Comparator getComparator() {
+ return new Comparator() {
@Override
- public int compare(final DbxPath lhs, final DbxPath rhs) {
+ public int compare(final DropboxAPI.Entry lhs,
+ final DropboxAPI.Entry rhs) {
if (isDir(lhs) && !isDir(rhs)) {
return -1;
} else if (isDir(rhs) && !isDir(lhs)) {
return 1;
} else {
- return lhs.getName().toLowerCase().compareTo(rhs.getName()
- .toLowerCase());
+ return lhs.fileName().toLowerCase()
+ .compareTo(rhs.fileName().toLowerCase());
}
}
};
}
@Override
- protected Loader> getLoader() {
- return new AsyncTaskLoader>(getActivity()) {
- DbxPath listenPath;
- public DbxFileSystem.PathListener pathListener;
+ protected Loader> getLoader() {
+ return new AsyncTaskLoader>(getActivity()) {
@Override
- public List loadInBackground() {
- ArrayList files = new ArrayList();
+ public List loadInBackground() {
+ ArrayList files =
+ new ArrayList();
try {
- for (DbxFileInfo fileInfo : fs.listFolder(currentPath)) {
- if ((mode == MODE_FILE || mode == MODE_FILE_AND_DIR)
- || fileInfo.isFolder) {
- files.add(fileInfo.path);
+
+ if (!dbApi.metadata(currentPath.path, 1, null, false,
+ null).isDir) {
+ currentPath = getRoot();
+ }
+
+ DropboxAPI.Entry dirEntry =
+ dbApi.metadata(currentPath.path, 0, null, true,
+ null);
+ for (DropboxAPI.Entry entry : dirEntry.contents) {
+ if ((mode == MODE_FILE || mode == MODE_FILE_AND_DIR) ||
+ entry.isDir) {
+ files.add(entry);
}
}
- } catch (DbxException e) {
- // e.printStackTrace();
+ } catch (DropboxException e) {
}
+
return files;
}
@@ -138,30 +184,10 @@ public List loadInBackground() {
protected void onStartLoading() {
super.onStartLoading();
- if (pathListener == null) {
- pathListener = new DbxFileSystem.PathListener() {
- @Override
- public void onPathChange(final DbxFileSystem dbxFileSystem, final DbxPath dbxPath, final Mode mode) {
- // Reload
- onContentChanged();
- }
- };
- }
-
- // Make sure it's valid
- try {
- if (!fs.exists(currentPath)) {
- currentPath = getRoot();
- }
- } catch (DbxException e) {
+ if (currentPath == null || !currentPath.isDir) {
currentPath = getRoot();
}
- // Start watching for changes
- listenPath = currentPath;
- fs.addPathListener(pathListener, listenPath,
- DbxFileSystem.PathListener.Mode.PATH_OR_CHILD);
-
forceLoad();
}
@@ -171,28 +197,9 @@ public void onPathChange(final DbxFileSystem dbxFileSystem, final DbxPath dbxPat
@Override
protected void onReset() {
super.onReset();
-
- // Stop watching
- if (listenPath != null) {
- fs.removePathListener(pathListener, listenPath,
- DbxFileSystem.PathListener.Mode.PATH_OR_CHILD);
- listenPath = null;
- }
}
};
}
- @Override
- public void onNewFolder(final String s) {
- DbxPath path = new DbxPath(s);
-
- try {
- fs.createFolder(path);
- currentPath = path;
- refresh();
- } catch (DbxException e) {
- Toast.makeText(getActivity(), R.string.create_folder_error,
- Toast.LENGTH_SHORT).show();
- }
- }
+
}
\ No newline at end of file
diff --git a/app/src/play/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSyncHelper.java b/app/src/play/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSyncHelper.java
index 52bda3fcf..7ed0b25ba 100644
--- a/app/src/play/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSyncHelper.java
+++ b/app/src/play/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSyncHelper.java
@@ -1,107 +1,146 @@
/*
- * Copyright (c) 2014 Jonas Kalderstam.
+ * Copyright (c) 2015 Jonas Kalderstam
*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
*
- * http://www.apache.org/licenses/LICENSE-2.0
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License for more details.
*
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program. If not, see .
*/
package com.nononsenseapps.notepad.sync.orgsync;
-import android.app.IntentService;
-import android.content.Intent;
+import android.app.Activity;
import android.content.Context;
+import android.preference.PreferenceManager;
-import com.dropbox.sync.android.DbxAccountManager;
-import com.dropbox.sync.android.DbxException;
-import com.dropbox.sync.android.DbxFileSystem;
+import com.dropbox.client2.DropboxAPI;
+import com.dropbox.client2.android.AndroidAuthSession;
+import com.dropbox.client2.session.AppKeyPair;
import com.nononsenseapps.build.Config;
/**
- * An {@link IntentService} subclass that synchronizes the Dropbox Cache in
- * the background
+ * This class has some utility functions for dealing with Dropbox. You need
+ * to input your API keys below.
+ * See Dropbox for more information:
+ * https://www.dropbox.com/developers/core/start/android
+ *
+ * You also need to drop your APP_KEY in the manifest in
+ * com.dropbox.client2.android.AuthActivity
+ * See here for info:
+ * https://www.dropbox.com/developers/core/sdks/android
*/
-public class DropboxSyncHelper extends IntentService {
+public class DropboxSyncHelper {
- public final static String ACTION_SYNC_FULL = "ACTION_SYNC_FULL";
- public final static String ACTION_SYNC_FIRST = "ACTION_SYNC_FIRST";
+ public static final String PREF_DROPBOX_TOKEN = "dropboxtoken";
+ private final Context mActivity;
+
+ public DropboxAPI mDBApi = null;
+
+ public DropboxSyncHelper(Activity activity) {
+ mActivity = activity;
+ // TODO
+ }
+
+ public static DropboxAPI getDBApi(
+ final Context context) {
+ final DropboxAPI mDBApi;
+
+ final AppKeyPair appKeys = new AppKeyPair(Config.getKeyDropboxAPI(context), Config.getKeyDropboxAPISecret(context));
+ final AndroidAuthSession session;
+
+ if (PreferenceManager.getDefaultSharedPreferences(context)
+ .contains(PREF_DROPBOX_TOKEN)) {
+ session = new AndroidAuthSession(appKeys,
+ PreferenceManager.getDefaultSharedPreferences(context)
+ .getString(PREF_DROPBOX_TOKEN, ""));
+ } else {
+ session = new AndroidAuthSession(appKeys);
+ }
+ mDBApi = new DropboxAPI(session);
+ return mDBApi;
+ }
/**
- * Execute first sync. If first sync has been completed,
- * this method does nothing.
+ * Save the dropbox oauth token so we can reuse the session without
+ * logging in again.
+ * @param context
+ * @param token
*/
- public static void doFirstSync(final Context context) {
- Intent intent = new Intent(context, DropboxSyncHelper.class);
- intent.setAction(ACTION_SYNC_FIRST);
- context.startService(intent);
+ public static void saveToken(final Context context, final String token) {
+ PreferenceManager.getDefaultSharedPreferences(context).edit()
+ .putString(PREF_DROPBOX_TOKEN, token).apply();
}
/**
- * Do a full sync regardless of state.
+ * Must add a call to handleLinkResult in your onResume method.
+ *
+ * @return true if already linked, else false (and opens auth-window)
*/
- public static void doFullSync(final Context context) {
- Intent intent = new Intent(context, DropboxSyncHelper.class);
- intent.setAction(ACTION_SYNC_FULL);
- context.startService(intent);
+ public boolean linkAccount() {
+ if (mDBApi == null) {
+ mDBApi = getDBApi(mActivity);
+ }
+
+ // If not authorized, then ask user for login/permission
+ if (!mDBApi.getSession().isLinked()) {
+ mDBApi.getSession().startOAuth2Authentication(mActivity);
+ return false;
+ } else {
+ return true;
+ }
}
/**
*
- * @param context
- * @return true if we have synced and it's ok to bring up the file picker.
+ * @return true if user has authorized connection to dropbox
*/
- public static boolean hasSynced(final Context context) {
- final DbxAccountManager accountManager = DbxAccountManager.getInstance
- (context.getApplicationContext(),
- Config.getKeyDropboxSyncPublic(context),
- Config.getKeyDropboxSyncSecret(context));
+ public boolean isLinked() {
+ if (mDBApi == null) {
+ mDBApi = getDBApi(mActivity);
+ }
+
+ // If not authorized, then ask user for login/permission
+ return mDBApi.getSession().isLinked();
+ }
- if (accountManager.hasLinkedAccount()) {
+ /**
+ *
+ * @return true if successfully linked, and token saved. False otherwise.
+ */
+ public boolean handleLinkResult() {
+ if (mDBApi != null && mDBApi.getSession().authenticationSuccessful()) {
try {
- final DbxFileSystem fs = DbxFileSystem.forAccount(accountManager
- .getLinkedAccount());
- return fs.hasSynced();
- } catch (DbxException.Unauthorized ignored) {
- } catch (DbxException ignored) {
+ // Required to complete auth, sets the access token on the session
+ mDBApi.getSession().finishAuthentication();
+
+ String accessToken = mDBApi.getSession().getOAuth2AccessToken();
+ saveToken(mActivity, accessToken);
+ return true;
+ } catch (IllegalStateException e) {
+ //Log.i("DbAuthLog", "Error authenticating", e);
}
}
return false;
}
- public DropboxSyncHelper() {
- super("DropboxSyncHelper");
- }
-
- @Override
- protected void onHandleIntent(Intent intent) {
- final DbxAccountManager accountManager = DbxAccountManager.getInstance
- (getApplicationContext(),
- Config.getKeyDropboxSyncPublic(this),
- Config.getKeyDropboxSyncSecret(this));
+ /**
+ * Does nothing is already unlinked.
+ */
+ public void unlinkAccount() {
+ if (mDBApi == null) {
+ mDBApi = getDBApi(mActivity);
+ }
- if (accountManager.hasLinkedAccount()) {
- try {
- final DbxFileSystem fs = DbxFileSystem.forAccount(accountManager
- .getLinkedAccount());
-
- if (ACTION_SYNC_FULL.equals(intent.getAction())) {
- fs.syncNowAndWait();
- } else if (ACTION_SYNC_FIRST.equals(intent.getAction()) &&
- !fs.hasSynced()) {
- fs.syncNowAndWait();
- }
-
- } catch (DbxException.Unauthorized ignored) {
- } catch (DbxException ignored) {
- }
+ if (mDBApi.getSession().isLinked()) {
+ mDBApi.getSession().unlink();
}
}
}
diff --git a/app/src/play/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSynchronizer.java b/app/src/play/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSynchronizer.java
index 9d3323b90..f4f73f8ac 100644
--- a/app/src/play/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSynchronizer.java
+++ b/app/src/play/java/com/nononsenseapps/notepad/sync/orgsync/DropboxSynchronizer.java
@@ -23,24 +23,24 @@
import android.preference.PreferenceManager;
import android.util.Log;
-import com.dropbox.sync.android.DbxAccount;
-import com.dropbox.sync.android.DbxAccountManager;
-import com.dropbox.sync.android.DbxException;
-import com.dropbox.sync.android.DbxFile;
-import com.dropbox.sync.android.DbxFileInfo;
-import com.dropbox.sync.android.DbxFileStatus;
-import com.dropbox.sync.android.DbxFileSystem;
-import com.dropbox.sync.android.DbxPath;
+import com.dropbox.client2.DropboxAPI;
+import com.dropbox.client2.android.AndroidAuthSession;
+import com.dropbox.client2.exception.DropboxException;
+import com.dropbox.client2.exception.DropboxServerException;
import com.nononsenseapps.build.Config;
import com.nononsenseapps.notepad.prefs.SyncPrefs;
import org.cowboyprogrammer.org.OrgFile;
import java.io.BufferedReader;
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
import java.io.IOException;
+import java.io.InputStream;
import java.io.StringReader;
+import java.io.UnsupportedEncodingException;
+import java.nio.charset.StandardCharsets;
import java.util.HashSet;
-import java.util.List;
public class DropboxSynchronizer extends Synchronizer implements
@@ -52,64 +52,21 @@ public class DropboxSynchronizer extends Synchronizer implements
public static final String PREF_ENABLED = SyncPrefs.KEY_DROPBOX_ENABLE;
public final static String SERVICENAME = "DROPBOXORG";
protected final boolean enabled;
- protected DbxPath DIR;
- private DbxAccountManager accountManager = null;
- private DbxAccount account = null;
- private DbxFileSystem fs = null;
+ private final DropboxAPI mDBApi;
+ private final String folderpath;
+ protected DropboxAPI.Entry DIR;
+ private DropboxAPI dbApi = null;
public DropboxSynchronizer(final Context context) {
super(context);
final SharedPreferences prefs = PreferenceManager
.getDefaultSharedPreferences(context);
enabled = prefs.getBoolean(PREF_ENABLED, false);
- DIR = new DbxPath(prefs.getString(PREF_DIR, DEFAULT_DIR));
+ mDBApi = DropboxSyncHelper.getDBApi(context);
+ folderpath = prefs.getString(PREF_DIR, DEFAULT_DIR);
}
- /**
- * Link a DropboxAccount. Must be called from a GUI. Activity
- * receives result in OnActivityResult with the specific code. Returns
- * RESULT_OK if all is good.
- *
- * @param activity
- * @param requestCode
- */
- public static void linkAccount(final Activity activity,
- final int requestCode) {
- final String APP_KEY = Config.getKeyDropboxSyncPublic(activity);
- final String APP_SECRET = Config.getKeyDropboxSyncSecret(activity);
- DbxAccountManager.getInstance(activity.getApplicationContext(),
- APP_KEY, APP_SECRET).startLink(activity, requestCode);
- }
-
- /**
- * Link a DropboxAccount. Must be called from a GUI. Activity
- * receives result in OnActivityResult with the specific code. Returns
- * RESULT_OK if all is good.
- *
- * @param fragment
- * @param requestCode
- */
- public static void linkAccount(final Fragment fragment,
- final int requestCode) {
- final String APP_KEY = Config.getKeyDropboxSyncPublic(fragment.getActivity());
- final String APP_SECRET = Config.getKeyDropboxSyncSecret(fragment.getActivity());
- DbxAccountManager.getInstance(fragment.getActivity().getApplicationContext(),
- APP_KEY, APP_SECRET).startLink(fragment, requestCode);
- }
-
- /**
- * Unlink a Dropbox Connection.
- *
- * @param activity
- */
- public static void unlink(final Activity activity) {
- final String APP_KEY = Config.getKeyDropboxSyncPublic(activity);
- final String APP_SECRET = Config.getKeyDropboxSyncSecret(activity);
- DbxAccountManager.getInstance(activity.getApplicationContext(),
- APP_KEY, APP_SECRET).unlink();
- }
-
/**
* @return A unique name for this service. Should be descriptive, like
* DropboxOrg, SDOrg or SSHOrg.
@@ -124,7 +81,11 @@ public String getServiceName() {
*/
@Override
public String getAccountName() {
- return accountManager.getLinkedAccount().getUserId();
+ try {
+ return mDBApi.accountInfo().email;
+ } catch (DropboxException e) {
+ return "ERROR";
+ }
}
/**
@@ -137,36 +98,27 @@ public boolean isConfigured() {
if (!enabled) return false;
// Need to ask dropbox if we are linked.
- if (accountManager == null) {
- final String APP_KEY = Config.getKeyDropboxSyncPublic(context);
- final String APP_SECRET = Config.getKeyDropboxSyncSecret(context);
-
- if (APP_KEY.contains(" ") || APP_SECRET.contains(" ")) {
- return false;
- }
-
- accountManager = DbxAccountManager.getInstance(context
- .getApplicationContext(), APP_KEY, APP_SECRET);
-
- if (accountManager.hasLinkedAccount()) {
- account = accountManager.getLinkedAccount();
- try {
- fs = DbxFileSystem.forAccount(account);
-
- fs.syncNowAndWait();
-
- if (!fs.isFolder(DIR)) {
- fs.createFolder(DIR);
+ if (mDBApi.getSession().isLinked()) {
+ // Create default dir if necessary
+ try {
+ DIR = mDBApi.metadata(folderpath, 1, null, false, null);
+ return DIR.isDir;
+ } catch (DropboxServerException e) {
+ if (e.error == 404) {
+ try {
+ DIR = mDBApi.createFolder(folderpath);
+ return DIR.isDir;
+ } catch (DropboxException e1) {
+ Log.e(TAG, "isConfigured: " + e.reason);
}
- } catch (DbxException.Unauthorized unauthorized) {
- return false;
- } catch (DbxException e) {
- return false;
+ } else {
+ Log.e(TAG, "isConfigured: " + e.reason);
}
+ } catch (DropboxException e) {
+ Log.e(TAG, "isConfigured catchall");
}
}
-
- return accountManager.hasLinkedAccount();
+ return false;
}
/**
@@ -194,16 +146,46 @@ public OrgFile getNewFile(final String desiredName) throws IOException, IllegalA
} else {
filename = desiredName + i + ".org";
}
- if (!fs.exists(new DbxPath(DIR, filename))) {
- return new OrgFile(filename);
+ try {
+ DropboxAPI.Entry entry = mDBApi.metadata(join(folderpath, filename), 1, null, false, null);
+ // If entry is returned, it exists, move to next iteration step
+ } catch (DropboxServerException e) {
+ if (404 == e.error) {
+ // No such file exists, great!
+ return new OrgFile(filename);
+ } else {
+ throw e;
+ }
}
}
- } catch (DbxPath.InvalidPathException e) {
- throw new IOException(e);
+ } catch (DropboxServerException e) {
+ throw new IOException("" + e.reason);
+ } catch (DropboxException e) {
+ throw new IOException();
}
throw new IllegalArgumentException("Filename not accessible");
}
+ private String join(String folderpath, String filename) {
+ if (folderpath == null || filename == null) {
+ throw new NullPointerException();
+ }
+
+ if (folderpath.endsWith("/")) {
+ if (filename.startsWith("/")) {
+ return folderpath + filename.substring(1);
+ } else {
+ return folderpath + filename;
+ }
+ } else {
+ if (filename.startsWith("/")) {
+ return folderpath + filename;
+ } else {
+ return folderpath + "/" + filename;
+ }
+ }
+ }
+
/**
* Replaces the file on the remote end with the given content.
*
@@ -211,19 +193,14 @@ public OrgFile getNewFile(final String desiredName) throws IOException, IllegalA
*/
@Override
public void putRemoteFile(final OrgFile orgFile) throws IOException {
- DbxPath path = new DbxPath(DIR, orgFile.getFilename());
try {
- DbxFile file;
- try {
- file = fs.open(path);
- waitUntilSynced(file);
- } catch (DbxException.NotFound e) {
- file = fs.create(path);
- }
- file.writeString(orgFile.treeToString());
- file.close();
- } catch (DbxException e) {
- throw new IOException(e);
+ byte[] bytes = orgFile.treeToString().getBytes(StandardCharsets.UTF_8);
+ InputStream stream = new ByteArrayInputStream(orgFile.treeToString().getBytes(StandardCharsets.UTF_8));
+ mDBApi.putFileOverwrite(join(folderpath, orgFile.getFilename()), stream, bytes.length, null);
+ } catch (DropboxServerException e) {
+ throw new IOException("" + e.reason);
+ } catch (DropboxException e) {
+ throw new IOException("" + e.getMessage());
}
}
@@ -233,22 +210,22 @@ public void putRemoteFile(final OrgFile orgFile) throws IOException {
* @param orgFile The file to delete.
*/
@Override
- public void deleteRemoteFile(final OrgFile orgFile) {
+ public void deleteRemoteFile(final OrgFile orgFile) throws IOException {
if (orgFile == null || orgFile.getFilename() == null) {
// Nothing to do
return;
}
- DbxPath path = new DbxPath(DIR, orgFile.getFilename());
try {
- // Get latest version
- DbxFile file = fs.open(path);
- waitUntilSynced(file);
- // Can close it again now
- file.close();
- // Now remove the updated file
- fs.delete(path);
- } catch (DbxException e) {
- //e.printStackTrace();
+ mDBApi.delete(join(folderpath, orgFile.getFilename()));
+ } catch (DropboxServerException e) {
+ if (404 == e.error) {
+ // This is ok, already deleted
+ // ignore
+ } else {
+ throw new IOException("" + e.reason);
+ }
+ } catch (DropboxException e) {
+ throw new IOException("" + e.getMessage());
}
}
@@ -259,18 +236,17 @@ public void deleteRemoteFile(final OrgFile orgFile) {
* @param orgFile
*/
@Override
- public void renameRemoteFile(final String oldName, final OrgFile orgFile) {
+ public void renameRemoteFile(final String oldName, final OrgFile orgFile) throws IOException {
if (orgFile == null || orgFile.getFilename() == null) {
throw new NullPointerException("No new filename");
}
- DbxPath newPath = new DbxPath(DIR, orgFile.getFilename());
- DbxPath oldPath = new DbxPath(DIR, oldName);
-
try {
- fs.move(oldPath, newPath);
- } catch (DbxException e) {
- //e.printStackTrace();
+ mDBApi.move(join(folderpath, oldName), join(folderpath, orgFile.getFilename()));
+ } catch (DropboxServerException e) {
+ throw new IOException("" + e.reason);
+ } catch (DropboxException e) {
+ throw new IOException("" + e.getMessage());
}
}
@@ -280,60 +256,17 @@ public void renameRemoteFile(final String oldName, final OrgFile orgFile) {
* @param filename Name of the file, without path
*/
@Override
- public BufferedReader getRemoteFile(final String filename) {
- DbxPath path = new DbxPath(DIR, filename);
- BufferedReader br = null;
+ public BufferedReader getRemoteFile(final String filename) throws IOException {
+ ByteArrayOutputStream baos = new ByteArrayOutputStream();
try {
- if (fs.isFile(path)) {
- DbxFile file = fs.open(path);
- // Get latest version
- waitUntilSynced(file);
- // Read it
- br = new BufferedReader(new StringReader(file.readString()));
- file.close();
- }
- // In case of errors, throw null pointers. Trying to see if this
- // the place that deletes files.
- } catch (DbxException e) {
- Log.d(TAG, e.getLocalizedMessage());
- //br = null;
- throw new NullPointerException(e.getLocalizedMessage());
- } catch (IOException e) {
- Log.d(TAG, e.getLocalizedMessage());
- //br = null;
- throw new NullPointerException(e.getLocalizedMessage());
- }
-
- return br;
- }
-
- /**
- * Wait until the file has been synced to the newest state. Will wait a
- * maximum of 30s.
- * @param file
- */
- private void waitUntilSynced(final DbxFile file) {
- final long MAXTIME = 30*1000;
- final long STARTTIME = System.currentTimeMillis();
- try {
- DbxFileStatus status = file.getNewerStatus();
-
- while (MAXTIME > (System.currentTimeMillis() - STARTTIME) &&
- status != null && !status.isCached && !status.isLatest) {
- Log.d(TAG, "Waiting on latest version: " + status
- .bytesTransferred + " / " + status.bytesTotal);
- try {
- Thread.sleep(1000);
- } catch (InterruptedException ignored) {
- }
- // Check latest
- file.update();
- status = file.getNewerStatus();
- }
- // Update
- file.update();
- } catch (DbxException e) {
- e.printStackTrace();
+ mDBApi.getFile(join(folderpath, filename), null, baos, null);
+ return new BufferedReader(new StringReader(baos.toString("UTF-8")));
+ } catch (DropboxServerException e) {
+ throw new IOException("" + e.reason);
+ } catch (DropboxException e) {
+ throw new IOException("" + e.getMessage());
+ } catch (UnsupportedEncodingException e) {
+ throw new IOException("" + e.getMessage());
}
}
@@ -341,35 +274,20 @@ private void waitUntilSynced(final DbxFile file) {
* @return a set of all remote files.
*/
@Override
- public HashSet getRemoteFilenames() {
+ public HashSet getRemoteFilenames() throws IOException {
final HashSet filenames = new HashSet();
try {
- while (fs.getSyncStatus().download.inProgress) {
- Log.d(TAG, "Waiting on Dropbox sync...");
- try {
- Thread.sleep(1000);
- } catch (InterruptedException e) {
- //e.printStackTrace();
- }
- }
- List fileInfos = fs.listFolder(DIR);
- for (DbxFileInfo fileInfo : fileInfos) {
- if (fileInfo.path.getName().toLowerCase().endsWith((".org"))) {
- if (fs.isFile(fileInfo.path)) {
- Log.d(TAG, "Adding: " + fileInfo.path.getName());
- filenames.add(fileInfo.path.getName());
- } else {
- Log.d(TAG, "Caught invalid file: " + fileInfo.path
- .getName());
- }
+ DropboxAPI.Entry entry = mDBApi.metadata(folderpath, -1, null, true, null);
+
+ for (DropboxAPI.Entry file: entry.contents) {
+ if (!file.isDir && file.fileName().toLowerCase().endsWith(".org")) {
+ filenames.add(file.fileName());
}
}
- } catch (DbxException e) {
- Log.d(TAG, e.getLocalizedMessage());
- // In case of errors, throw null pointers. Trying to see if this
- // the place that deletes files.
- throw new NullPointerException(e.getLocalizedMessage());
- //e.printStackTrace();
+ } catch (DropboxServerException e) {
+ throw new IOException("" + e.reason);
+ } catch (DropboxException e) {
+ throw new IOException("" + e.getMessage());
}
return filenames;
}
@@ -382,50 +300,11 @@ public void postSynchronize() {
}
+ /**
+ * @return a Monitor for this source. May be null.
+ */
@Override
public Monitor getMonitor() {
- return new DropboxMonitor(fs, DIR);
- }
-
- public final class DropboxMonitor implements Monitor,
- DbxFileSystem.PathListener {
-
- private DbxFileSystem fs;
- private final DbxPath dir;
- private OrgSyncService.SyncHandler handler;
-
- public DropboxMonitor(final DbxFileSystem fs, final DbxPath dir) {
- this.fs = fs;
- this.dir = dir;
- }
-
- @Override
- public void startMonitor(final OrgSyncService.SyncHandler handler) {
- this.handler = handler;
- if (fs != null) {
- fs.addPathListener(this, dir, DbxFileSystem.PathListener.Mode.PATH_OR_CHILD);
- }
- }
-
- @Override
- public void pauseMonitor() {
- if (fs != null) {
- fs.removePathListenerForAll(this);
- }
- }
-
- @Override
- public void terminate() {
- pauseMonitor();
- fs = null;
- }
-
- @Override
- public void onPathChange(final DbxFileSystem dbxFileSystem,
- final DbxPath dbxPath, final Mode mode) {
- if (handler != null) {
- handler.onMonitorChange();
- }
- }
+ return null;
}
}
diff --git a/app/src/play/libs/ALL_LIBS_ARE_FOR_DROPBOX b/app/src/play/libs/ALL_LIBS_ARE_FOR_DROPBOX
new file mode 100644
index 000000000..e69de29bb
diff --git a/app/src/play/libs/HTTPCOMPONENTS-LICENSE.txt b/app/src/play/libs/HTTPCOMPONENTS-LICENSE.txt
new file mode 100644
index 000000000..2c41ec88f
--- /dev/null
+++ b/app/src/play/libs/HTTPCOMPONENTS-LICENSE.txt
@@ -0,0 +1,182 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+This project contains annotations derived from JCIP-ANNOTATIONS
+Copyright (c) 2005 Brian Goetz and Tim Peierls.
+See http://www.jcip.net and the Creative Commons Attribution License
+(http://creativecommons.org/licenses/by/2.5)
+
diff --git a/app/src/play/libs/JSON-SIMPLE-LICENSE.txt b/app/src/play/libs/JSON-SIMPLE-LICENSE.txt
new file mode 100644
index 000000000..57bc88a15
--- /dev/null
+++ b/app/src/play/libs/JSON-SIMPLE-LICENSE.txt
@@ -0,0 +1,202 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+
diff --git a/app/src/play/libs/armeabi-v7 b/app/src/play/libs/armeabi-v7
deleted file mode 120000
index fb2068a19..000000000
--- a/app/src/play/libs/armeabi-v7
+++ /dev/null
@@ -1 +0,0 @@
-armeabi
\ No newline at end of file
diff --git a/app/src/play/libs/armeabi-v7a b/app/src/play/libs/armeabi-v7a
deleted file mode 120000
index fb2068a19..000000000
--- a/app/src/play/libs/armeabi-v7a
+++ /dev/null
@@ -1 +0,0 @@
-armeabi
\ No newline at end of file
diff --git a/app/src/play/libs/armeabi/libDropboxSync.so b/app/src/play/libs/armeabi/libDropboxSync.so
deleted file mode 100755
index 587d81554..000000000
Binary files a/app/src/play/libs/armeabi/libDropboxSync.so and /dev/null differ
diff --git a/app/src/play/libs/dropbox-android-sdk-1.6.3.jar b/app/src/play/libs/dropbox-android-sdk-1.6.3.jar
new file mode 100644
index 000000000..1a0ee3686
Binary files /dev/null and b/app/src/play/libs/dropbox-android-sdk-1.6.3.jar differ
diff --git a/app/src/play/libs/dropbox-sync-sdk-android.jar b/app/src/play/libs/dropbox-sync-sdk-android.jar
deleted file mode 100644
index 807aaa1f7..000000000
Binary files a/app/src/play/libs/dropbox-sync-sdk-android.jar and /dev/null differ
diff --git a/app/src/play/libs/httpmime-4.0.3.jar b/app/src/play/libs/httpmime-4.0.3.jar
new file mode 100644
index 000000000..0dfd33128
Binary files /dev/null and b/app/src/play/libs/httpmime-4.0.3.jar differ
diff --git a/app/src/play/libs/json_simple-1.1.jar b/app/src/play/libs/json_simple-1.1.jar
new file mode 100644
index 000000000..f395f4147
Binary files /dev/null and b/app/src/play/libs/json_simple-1.1.jar differ
diff --git a/app/src/play/libs/mips/libDropboxSync.so b/app/src/play/libs/mips/libDropboxSync.so
deleted file mode 100755
index fcfeb2986..000000000
Binary files a/app/src/play/libs/mips/libDropboxSync.so and /dev/null differ
diff --git a/app/src/play/libs/x86/libDropboxSync.so b/app/src/play/libs/x86/libDropboxSync.so
deleted file mode 100755
index 54cd33d9a..000000000
Binary files a/app/src/play/libs/x86/libDropboxSync.so and /dev/null differ