From 707604ed166d83a5067e8425f999d60848950c94 Mon Sep 17 00:00:00 2001 From: Mariotaku Lee Date: Sat, 9 May 2015 16:28:14 +0800 Subject: [PATCH] implemented activity api --- .../twitter/api/PrivateActivityResources.java | 10 +- .../twidere/api/twitter/model/Activity.java | 4 +- .../api/twitter/model/impl/ActivityImpl.java | 221 ++++++++++++++++++ .../model/impl/TypeConverterMapper.java | 25 +- .../api/twitter/util/TwitterConverter.java | 6 +- 5 files changed, 253 insertions(+), 13 deletions(-) create mode 100644 twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/impl/ActivityImpl.java diff --git a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/api/PrivateActivityResources.java b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/api/PrivateActivityResources.java index eb23a4f98..481d81442 100644 --- a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/api/PrivateActivityResources.java +++ b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/api/PrivateActivityResources.java @@ -19,15 +19,19 @@ package org.mariotaku.twidere.api.twitter.api; +import org.mariotaku.simplerestapi.method.GET; +import org.mariotaku.simplerestapi.param.Query; +import org.mariotaku.twidere.api.twitter.TwitterException; import org.mariotaku.twidere.api.twitter.model.Activity; import org.mariotaku.twidere.api.twitter.model.Paging; import org.mariotaku.twidere.api.twitter.model.ResponseList; -import org.mariotaku.twidere.api.twitter.TwitterException; @SuppressWarnings("RedundantThrows") public interface PrivateActivityResources extends PrivateResources { - ResponseList getActivitiesAboutMe(Paging paging) throws TwitterException; + @GET("/activity/about_me.json") + ResponseList getActivitiesAboutMe(@Query Paging paging) throws TwitterException; - ResponseList getActivitiesByFriends(Paging paging) throws TwitterException; + @GET("/activity/by_friends.json") + ResponseList getActivitiesByFriends(@Query Paging paging) throws TwitterException; } diff --git a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/Activity.java b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/Activity.java index 0c6444212..14511a9fe 100644 --- a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/Activity.java +++ b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/Activity.java @@ -65,7 +65,7 @@ public interface Activity extends TwitterResponse, Comparable { private final int actionId; - private Action(final int action) { + Action(final int action) { actionId = action; } @@ -73,7 +73,7 @@ public interface Activity extends TwitterResponse, Comparable { return actionId; } - public static Action fromString(final String string) { + public static Action parse(final String string) { if ("favorite".equalsIgnoreCase(string)) return FAVORITE; if ("follow".equalsIgnoreCase(string)) return FOLLOW; if ("mention".equalsIgnoreCase(string)) return MENTION; diff --git a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/impl/ActivityImpl.java b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/impl/ActivityImpl.java new file mode 100644 index 000000000..c1a5dcc8c --- /dev/null +++ b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/impl/ActivityImpl.java @@ -0,0 +1,221 @@ +/* + * Twidere - Twitter client for Android + * + * Copyright (C) 2012-2015 Mariotaku Lee + * + * 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. + * + * 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. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +package org.mariotaku.twidere.api.twitter.model.impl; + +import android.support.annotation.NonNull; + +import com.bluelinelabs.logansquare.JsonMapper; +import com.bluelinelabs.logansquare.LoganSquare; +import com.fasterxml.jackson.core.JsonGenerator; +import com.fasterxml.jackson.core.JsonParser; +import com.fasterxml.jackson.core.JsonToken; + +import org.mariotaku.twidere.api.twitter.model.Activity; +import org.mariotaku.twidere.api.twitter.model.Status; +import org.mariotaku.twidere.api.twitter.model.User; +import org.mariotaku.twidere.api.twitter.model.UserList; + +import java.io.IOException; +import java.text.ParseException; +import java.text.SimpleDateFormat; +import java.util.Arrays; +import java.util.Date; +import java.util.Locale; + +public class ActivityImpl extends TwitterResponseImpl implements Activity { + + public static final JsonMapper MAPPER = new JsonMapper() { + @SuppressWarnings("TryWithIdenticalCatches") + @Override + public Activity parse(JsonParser jsonParser) throws IOException { + ActivityImpl instance = new ActivityImpl(); + if (jsonParser.getCurrentToken() == null) { + jsonParser.nextToken(); + } + if (jsonParser.getCurrentToken() != JsonToken.START_OBJECT) { + jsonParser.skipChildren(); + return null; + } + while (jsonParser.nextToken() != JsonToken.END_OBJECT) { + String fieldName = jsonParser.getCurrentName(); + jsonParser.nextToken(); + parseField(instance, fieldName, jsonParser); + jsonParser.skipChildren(); + } + return instance; + } + + @Override + public void serialize(Activity activity, JsonGenerator jsonGenerator, boolean writeStartAndEnd) { + throw new UnsupportedOperationException(); + } + + public void parseField(ActivityImpl instance, String fieldName, JsonParser jsonParser) throws IOException { + if ("action".equals(fieldName)) { + instance.action = Action.parse(jsonParser.getValueAsString()); + } else if ("created_at".equals(fieldName)) { + try { + instance.createdAt = DATE_FORMAT.parse(jsonParser.getValueAsString()); + } catch (ParseException e) { + throw new IOException(e); + } + } else if ("min_position".equals(fieldName)) { + instance.minPosition = jsonParser.getValueAsLong(); + } else if ("max_position".equals(fieldName)) { + instance.maxPosition = jsonParser.getValueAsLong(); + } else if ("sources_size".equals(fieldName)) { + instance.sourcesSize = jsonParser.getValueAsInt(); + } else if ("targets_size".equals(fieldName)) { + instance.targetsSize = jsonParser.getValueAsInt(); + } else if ("target_objects_size".equals(fieldName)) { + instance.targetObjectsSize = jsonParser.getValueAsInt(); + } else if ("sources".equals(fieldName)) { + instance.sources = LoganSquare.mapperFor(User.class).parseList(jsonParser).toArray(new User[instance.sourcesSize]); + } else if ("targets".equals(fieldName)) { + if (instance.action == null) throw new IOException(); + if (instance.action == Action.FOLLOW || instance.action == Action.MENTION || instance.action == Action.LIST_MEMBER_ADDED) { + instance.targetUsers = LoganSquare.mapperFor(User.class).parseList(jsonParser).toArray(new User[instance.targetsSize]); + } else if (instance.action == Action.LIST_CREATED) { + instance.targetUserLists = LoganSquare.mapperFor(UserList.class).parseList(jsonParser).toArray(new UserList[instance.targetsSize]); + } else { + instance.targetStatuses = LoganSquare.mapperFor(Status.class).parseList(jsonParser).toArray(new Status[instance.targetsSize]); + } + } else if ("target_objects".equals(fieldName)) { + if (instance.action == null) throw new IOException(); + if (instance.action == Action.LIST_MEMBER_ADDED) { + instance.targetObjectUserLists = LoganSquare.mapperFor(UserList.class).parseList(jsonParser).toArray(new UserList[instance.targetObjectsSize]); + } else { + instance.targetObjectStatuses = LoganSquare.mapperFor(Status.class).parseList(jsonParser).toArray(new Status[instance.targetObjectsSize]); + } + } + } + }; + + private Action action; + + private Date createdAt; + + private User[] sources, targetUsers; + + private Status[] targetObjectStatuses, targetStatuses; + + private UserList[] targetUserLists, targetObjectUserLists; + + private long maxPosition, minPosition; + + private int targetObjectsSize, targetsSize, sourcesSize; + + ActivityImpl() { + } + + @Override + public int compareTo(@NonNull final Activity another) { + final Date thisDate = getCreatedAt(), thatDate = another.getCreatedAt(); + if (thisDate == null || thatDate == null) return 0; + return thisDate.compareTo(thatDate); + } + + @Override + public Action getAction() { + return action; + } + + @Override + public Date getCreatedAt() { + return createdAt; + } + + @Override + public long getMaxPosition() { + return maxPosition; + } + + @Override + public long getMinPosition() { + return minPosition; + } + + @Override + public User[] getSources() { + return sources; + } + + @Override + public int getSourcesSize() { + return sourcesSize; + } + + @Override + public int getTargetObjectsSize() { + return targetObjectsSize; + } + + @Override + public Status[] getTargetObjectStatuses() { + return targetObjectStatuses; + } + + @Override + public UserList[] getTargetObjectUserLists() { + return targetObjectUserLists; + } + + @Override + public int getTargetsSize() { + return targetsSize; + } + + @Override + public Status[] getTargetStatuses() { + return targetStatuses; + } + + @Override + public UserList[] getTargetUserLists() { + return targetUserLists; + } + + @Override + public User[] getTargetUsers() { + return targetUsers; + } + + @Override + public String toString() { + return "ActivityJSONImpl{" + + "action=" + action + + ", createdAt=" + createdAt + + ", sources=" + Arrays.toString(sources) + + ", targetUsers=" + Arrays.toString(targetUsers) + + ", targetObjectStatuses=" + Arrays.toString(targetObjectStatuses) + + ", targetStatuses=" + Arrays.toString(targetStatuses) + + ", targetUserLists=" + Arrays.toString(targetUserLists) + + ", targetObjectUserLists=" + Arrays.toString(targetObjectUserLists) + + ", maxPosition=" + maxPosition + + ", minPosition=" + minPosition + + ", targetObjectsSize=" + targetObjectsSize + + ", targetsSize=" + targetsSize + + ", sourcesSize=" + sourcesSize + + '}'; + } + + private static final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("EEE MMM dd HH:mm:ss z yyyy", Locale.ENGLISH); + +} \ No newline at end of file diff --git a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/impl/TypeConverterMapper.java b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/impl/TypeConverterMapper.java index 1f8421965..01aaebff4 100644 --- a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/impl/TypeConverterMapper.java +++ b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/impl/TypeConverterMapper.java @@ -50,19 +50,14 @@ public class TypeConverterMapper implements TypeConverter { throw new UnsupportedOperationException(); } - @SuppressWarnings({"TryWithIdenticalCatches", "unchecked"}) + @SuppressWarnings({"TryWithIdenticalCatches"}) public static void register(Class cls, Class impl) { LoganSquare.registerTypeConverter(cls, new TypeConverterMapper<>(impl)); try { //noinspection unchecked - final Field objectMappersField = LoganSquare.class.getDeclaredField("OBJECT_MAPPERS"); - objectMappersField.setAccessible(true); - final Map mappers = (Map) objectMappersField.get(null); - mappers.put(cls, (JsonMapper) Class.forName(impl.getName() + "$$JsonObjectMapper").newInstance()); + register(cls, impl, (JsonMapper) Class.forName(impl.getName() + "$$JsonObjectMapper").newInstance()); } catch (IllegalAccessException e) { throw new RuntimeException(e); - } catch (NoSuchFieldException e) { - throw new RuntimeException(e); } catch (ClassNotFoundException e) { throw new RuntimeException(e); } catch (InstantiationException e) { @@ -70,5 +65,21 @@ public class TypeConverterMapper implements TypeConverter { } } + @SuppressWarnings({"TryWithIdenticalCatches"}) + public static void register(Class cls, Class impl, JsonMapper mapper) { + LoganSquare.registerTypeConverter(cls, new TypeConverterMapper<>(impl)); + try { + //noinspection unchecked + final Field objectMappersField = LoganSquare.class.getDeclaredField("OBJECT_MAPPERS"); + objectMappersField.setAccessible(true); + //noinspection unchecked + final Map mappers = (Map) objectMappersField.get(null); + mappers.put(cls, mapper); + } catch (IllegalAccessException e) { + throw new RuntimeException(e); + } catch (NoSuchFieldException e) { + throw new RuntimeException(e); + } + } } diff --git a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/util/TwitterConverter.java b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/util/TwitterConverter.java index eade56f3f..ef13b115f 100644 --- a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/util/TwitterConverter.java +++ b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/util/TwitterConverter.java @@ -30,8 +30,8 @@ import org.mariotaku.simplerestapi.http.ContentType; import org.mariotaku.simplerestapi.http.RestResponse; import org.mariotaku.simplerestapi.http.mime.TypedData; import org.mariotaku.twidere.api.twitter.TwitterException; -import org.mariotaku.twidere.api.twitter.model.UserMentionEntity; import org.mariotaku.twidere.api.twitter.auth.OAuthToken; +import org.mariotaku.twidere.api.twitter.model.Activity; import org.mariotaku.twidere.api.twitter.model.CardEntity; import org.mariotaku.twidere.api.twitter.model.DirectMessage; import org.mariotaku.twidere.api.twitter.model.ErrorInfo; @@ -50,6 +50,8 @@ import org.mariotaku.twidere.api.twitter.model.TranslationResult; import org.mariotaku.twidere.api.twitter.model.UrlEntity; import org.mariotaku.twidere.api.twitter.model.User; import org.mariotaku.twidere.api.twitter.model.UserList; +import org.mariotaku.twidere.api.twitter.model.UserMentionEntity; +import org.mariotaku.twidere.api.twitter.model.impl.ActivityImpl; import org.mariotaku.twidere.api.twitter.model.impl.CardEntityImpl; import org.mariotaku.twidere.api.twitter.model.impl.DirectMessageImpl; import org.mariotaku.twidere.api.twitter.model.impl.ErrorInfoImpl; @@ -116,11 +118,13 @@ public class TwitterConverter implements Converter { TypeConverterMapper.register(MediaUploadResponse.Image.class, MediaUploadResponseImpl.ImageImpl.class); TypeConverterMapper.register(ErrorInfo.class, ErrorInfoImpl.class); TypeConverterMapper.register(TranslationResult.class, TranslationResultImpl.class); + TypeConverterMapper.register(Activity.class, ActivityImpl.class, ActivityImpl.MAPPER); LoganSquare.registerTypeConverter(Indices.class, Indices.CONVERTER); LoganSquare.registerTypeConverter(GeoLocation.class, GeoLocation.CONVERTER); LoganSquare.registerTypeConverter(MediaEntity.Type.class, EnumConverter.get(MediaEntity.Type.class)); LoganSquare.registerTypeConverter(UserList.Mode.class, EnumConverter.get(UserList.Mode.class)); + LoganSquare.registerTypeConverter(Activity.Action.class, EnumConverter.get(Activity.Action.class)); registerWrapper(QueryResult.class, QueryResultWrapper.class); registerWrapper(PageableResponseList.class, PageableResponseListWrapper.class);