Niedzielski has uploaded a new change for review.

  https://gerrit.wikimedia.org/r/270246

Change subject: Add user option data client
......................................................................

Add user option data client

No functional changes intended at this time. This code is exercised by a
subsequent patch.

Change-Id: I7a3f3663dcd9c383d84bf2ca16eafb8a1469e491
---
A app/src/main/java/org/wikipedia/dataclient/mwapi/MwQueryResponse.java
A app/src/main/java/org/wikipedia/useroption/UserInfo.java
A app/src/main/java/org/wikipedia/useroption/UserOption.java
A 
app/src/main/java/org/wikipedia/useroption/dataclient/DefaultUserOptionDataClient.java
A 
app/src/main/java/org/wikipedia/useroption/dataclient/UserInfoDataClientSingleton.java
A 
app/src/main/java/org/wikipedia/useroption/dataclient/UserOptionDataClient.java
6 files changed, 269 insertions(+), 0 deletions(-)


  git pull ssh://gerrit.wikimedia.org:29418/apps/android/wikipedia 
refs/changes/46/270246/1

diff --git 
a/app/src/main/java/org/wikipedia/dataclient/mwapi/MwQueryResponse.java 
b/app/src/main/java/org/wikipedia/dataclient/mwapi/MwQueryResponse.java
new file mode 100644
index 0000000..1982a82
--- /dev/null
+++ b/app/src/main/java/org/wikipedia/dataclient/mwapi/MwQueryResponse.java
@@ -0,0 +1,17 @@
+package org.wikipedia.dataclient.mwapi;
+
+import com.google.gson.annotations.SerializedName;
+
+public class MwQueryResponse<T> {
+    @SerializedName("batchcomplete")
+    private boolean batchComplete;
+    private T query;
+
+    public boolean batchComplete() {
+        return batchComplete;
+    }
+
+    public T query() {
+        return query;
+    }
+}
\ No newline at end of file
diff --git a/app/src/main/java/org/wikipedia/useroption/UserInfo.java 
b/app/src/main/java/org/wikipedia/useroption/UserInfo.java
new file mode 100644
index 0000000..48ad343
--- /dev/null
+++ b/app/src/main/java/org/wikipedia/useroption/UserInfo.java
@@ -0,0 +1,46 @@
+package org.wikipedia.useroption;
+
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+
+import com.google.gson.annotations.SerializedName;
+
+import java.util.Map;
+
+public class UserInfo {
+    @SerializedName("name")
+    private String username;
+    private int id;
+
+    // Object type is a JSON primitive.
+    @NonNull private Map<String, Object> options;
+
+    public int id() {
+        return id;
+    }
+
+    @NonNull
+    public String username() {
+        return username;
+    }
+
+    public boolean hasOption(String key) {
+        return options.containsKey(key);
+    }
+
+    @Nullable
+    public <T> T option(String key) {
+        //noinspection unchecked
+        return (T) options.get(key);
+    }
+
+    // Auto-generated
+    @Override
+    public String toString() {
+        return "UserInfo{"
+                + "username='" + username + '\''
+                + ", id=" + id
+                + ", options=" + options
+                + '}';
+    }
+}
\ No newline at end of file
diff --git a/app/src/main/java/org/wikipedia/useroption/UserOption.java 
b/app/src/main/java/org/wikipedia/useroption/UserOption.java
new file mode 100644
index 0000000..be537ba
--- /dev/null
+++ b/app/src/main/java/org/wikipedia/useroption/UserOption.java
@@ -0,0 +1,30 @@
+package org.wikipedia.useroption;
+
+import android.support.annotation.NonNull;
+
+public class UserOption {
+    @NonNull private final String key;
+    private final boolean enabled;
+
+    public UserOption(@NonNull String key, boolean enabled) {
+        this.key = key;
+        this.enabled = enabled;
+    }
+
+    @NonNull public String key() {
+        return key;
+    }
+
+    public boolean enabled() {
+        return enabled;
+    }
+
+    // Auto-generated
+    @Override
+    public String toString() {
+        return "UserOption{"
+                + "key='" + key + '\''
+                + ", enabled=" + enabled
+                + '}';
+    }
+}
\ No newline at end of file
diff --git 
a/app/src/main/java/org/wikipedia/useroption/dataclient/DefaultUserOptionDataClient.java
 
b/app/src/main/java/org/wikipedia/useroption/dataclient/DefaultUserOptionDataClient.java
new file mode 100644
index 0000000..007371d
--- /dev/null
+++ 
b/app/src/main/java/org/wikipedia/useroption/dataclient/DefaultUserOptionDataClient.java
@@ -0,0 +1,143 @@
+package org.wikipedia.useroption.dataclient;
+
+import android.support.annotation.NonNull;
+
+import com.google.gson.annotations.SerializedName;
+
+import org.wikipedia.Site;
+import org.wikipedia.WikipediaApp;
+import org.wikipedia.dataclient.RestAdapterFactory;
+import org.wikipedia.dataclient.mwapi.MwQueryResponse;
+import org.wikipedia.editing.EditTokenStorage;
+import org.wikipedia.useroption.UserInfo;
+import org.wikipedia.useroption.UserOption;
+
+import java.io.IOException;
+
+import retrofit.Callback;
+import retrofit.RetrofitError;
+import retrofit.client.Response;
+import retrofit.http.Field;
+import retrofit.http.FormUrlEncoded;
+import retrofit.http.GET;
+import retrofit.http.POST;
+import retrofit.http.Query;
+
+public class DefaultUserOptionDataClient implements UserOptionDataClient {
+    @NonNull private final Site site;
+    @NonNull private final Client client;
+
+    public DefaultUserOptionDataClient(@NonNull Site site) {
+        this.site = site;
+        client = RestAdapterFactory.newInstance(site).create(Client.class);
+    }
+
+    @Override
+    public void get(@NonNull Callback<UserInfo> callback) {
+        client.get(new GetCallback(callback));
+    }
+
+    @Override
+    public void post(@NonNull UserOption option, @NonNull Callback<Void> 
callback) {
+        getToken(new TokenCallback(option, callback));
+    }
+
+    private void getToken(@NonNull TokenCallback callback) {
+        WikipediaApp.getInstance().getEditTokenStorage().get(site, callback);
+    }
+
+    private interface Client {
+        String ACTION = "/w/api.php?format=json&formatversion=2&action=";
+
+        @GET(ACTION + "query&meta=userinfo&uiprop=options")
+        void get(@NonNull Callback<MwQueryResponse<QueryUserInfo>> callback);
+
+        @FormUrlEncoded
+        @POST(ACTION + "options")
+        void post(@Field("token") @NonNull String token,
+                  @Query("optionname") @NonNull String key,
+                  @Query("optionvalue") @NonNull String value,
+                  @NonNull Callback<PostResponse> callback);
+    }
+
+    private static class PostResponse {
+        private String options;
+
+        public boolean success() {
+            return "success".equals(options);
+        }
+    }
+
+    private static class QueryUserInfo {
+        @SerializedName("userinfo")
+        private UserInfo userInfo;
+
+        public UserInfo userInfo() {
+            return userInfo;
+        }
+    }
+
+    private class TokenCallback implements 
EditTokenStorage.TokenRetrievedCallback {
+        @NonNull private final UserOption option;
+        @NonNull private final PostCallback callback;
+
+        TokenCallback(@NonNull UserOption option, @NonNull Callback<Void> 
callback) {
+            this.option = option;
+            this.callback = new PostCallback(callback);
+        }
+
+        @Override
+        public void onTokenRetrieved(String token) {
+            client.post(token, option.key(), String.valueOf(option.enabled()), 
callback);
+        }
+
+        @Override
+        public void onTokenFailed(Throwable caught) {
+            // TODO: pass actual URL.
+            callback.failure(RetrofitError.unexpectedError(option.key(), 
caught));
+        }
+    }
+
+    private static class PostCallback extends CallbackWrapper<PostResponse, 
Void> {
+        PostCallback(@NonNull Callback<Void> callback) {
+            super(callback);
+        }
+
+        @Override
+        public void success(PostResponse result, Response response) {
+            if (result.success()) {
+                callback().success(null, response);
+            } else {
+                failure(RetrofitError.networkError(response.getUrl(), new 
IOException()));
+            }
+        }
+    }
+
+    private static class GetCallback extends 
CallbackWrapper<MwQueryResponse<QueryUserInfo>, UserInfo> {
+        GetCallback(@NonNull Callback<UserInfo> callback) {
+            super(callback);
+        }
+
+        @Override
+        public void success(MwQueryResponse<QueryUserInfo> result, Response 
response) {
+            callback().success(result.query().userInfo(), response);
+        }
+    }
+
+    private abstract static class CallbackWrapper<Wrapper, Wrapped> implements 
Callback<Wrapper> {
+        @NonNull private final Callback<Wrapped> callback;
+
+        CallbackWrapper(@NonNull Callback<Wrapped> callback) {
+            this.callback = callback;
+        }
+
+        @Override
+        public void failure(RetrofitError error) {
+            callback.failure(error);
+        }
+
+        protected Callback<Wrapped> callback() {
+            return callback;
+        }
+    }
+}
\ No newline at end of file
diff --git 
a/app/src/main/java/org/wikipedia/useroption/dataclient/UserInfoDataClientSingleton.java
 
b/app/src/main/java/org/wikipedia/useroption/dataclient/UserInfoDataClientSingleton.java
new file mode 100644
index 0000000..ec13e04
--- /dev/null
+++ 
b/app/src/main/java/org/wikipedia/useroption/dataclient/UserInfoDataClientSingleton.java
@@ -0,0 +1,20 @@
+package org.wikipedia.useroption.dataclient;
+
+import org.wikipedia.Site;
+
+public final class UserInfoDataClientSingleton {
+    public static UserOptionDataClient instance() {
+        return LazyHolder.INSTANCE;
+    }
+
+    private UserInfoDataClientSingleton() { }
+
+    private static class LazyHolder {
+        private static final UserOptionDataClient INSTANCE = instance();
+
+        private static UserOptionDataClient instance() {
+            Site site = new Site("meta.wikimedia.org");
+            return new DefaultUserOptionDataClient(site);
+        }
+    }
+}
\ No newline at end of file
diff --git 
a/app/src/main/java/org/wikipedia/useroption/dataclient/UserOptionDataClient.java
 
b/app/src/main/java/org/wikipedia/useroption/dataclient/UserOptionDataClient.java
new file mode 100644
index 0000000..f9347ac
--- /dev/null
+++ 
b/app/src/main/java/org/wikipedia/useroption/dataclient/UserOptionDataClient.java
@@ -0,0 +1,13 @@
+package org.wikipedia.useroption.dataclient;
+
+import android.support.annotation.NonNull;
+
+import org.wikipedia.useroption.UserInfo;
+import org.wikipedia.useroption.UserOption;
+
+import retrofit.Callback;
+
+public interface UserOptionDataClient {
+    void get(@NonNull Callback<UserInfo> callback);
+    void post(@NonNull UserOption option, @NonNull Callback<Void> callback);
+}
\ No newline at end of file

-- 
To view, visit https://gerrit.wikimedia.org/r/270246
To unsubscribe, visit https://gerrit.wikimedia.org/r/settings

Gerrit-MessageType: newchange
Gerrit-Change-Id: I7a3f3663dcd9c383d84bf2ca16eafb8a1469e491
Gerrit-PatchSet: 1
Gerrit-Project: apps/android/wikipedia
Gerrit-Branch: master
Gerrit-Owner: Niedzielski <[email protected]>

_______________________________________________
MediaWiki-commits mailing list
[email protected]
https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits

Reply via email to