From 94ad1a659ccd0c8e95824356dfa4ddf79c10be9f Mon Sep 17 00:00:00 2001 From: Mariotaku Lee Date: Fri, 15 Jan 2016 00:15:11 +0800 Subject: [PATCH] bug fixes --- .../twitter/model/MediaUploadResponse.java | 27 +++++-- .../edu/tsinghua/hotmobi/UploadLogsTask.java | 7 +- .../hotmobi/model/UploadLogEvent.java | 71 ++++++++++++++++++- .../fragment/support/StatusFragment.java | 25 ++++--- .../support/card/CardBrowserFragment.java | 3 +- .../util/TwitterCardFragmentFactory.java | 5 +- 6 files changed, 118 insertions(+), 20 deletions(-) diff --git a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/MediaUploadResponse.java b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/MediaUploadResponse.java index 29f6f5425..d70d17082 100644 --- a/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/MediaUploadResponse.java +++ b/twidere.component.common/src/main/java/org/mariotaku/twidere/api/twitter/model/MediaUploadResponse.java @@ -28,6 +28,15 @@ import com.bluelinelabs.logansquare.annotation.JsonObject; @JsonObject public class MediaUploadResponse extends TwitterResponseObject implements TwitterResponse { + @JsonField(name = "media_id") + long mediaId; + @JsonField(name = "size") + long size; + @JsonField(name = "image") + Image image; + @JsonField(name = "video") + Video video; + public long getId() { return mediaId; } @@ -40,13 +49,19 @@ public class MediaUploadResponse extends TwitterResponseObject implements Twitte return size; } - @JsonField(name = "media_id") - long mediaId; - @JsonField(name = "size") - long size; - @JsonField(name = "image") - Image image; + public Video getVideo() { + return video; + } + @JsonObject + public static class Video { + @JsonField(name = "video_type") + String videoType; + + public String getVideoType() { + return videoType; + } + } @JsonObject public static class Image { diff --git a/twidere/src/main/java/edu/tsinghua/hotmobi/UploadLogsTask.java b/twidere/src/main/java/edu/tsinghua/hotmobi/UploadLogsTask.java index b50828d3f..ed2243b87 100644 --- a/twidere/src/main/java/edu/tsinghua/hotmobi/UploadLogsTask.java +++ b/twidere/src/main/java/edu/tsinghua/hotmobi/UploadLogsTask.java @@ -30,6 +30,7 @@ import org.mariotaku.restfu.http.RestHttpClient; import org.mariotaku.restfu.http.RestHttpRequest; import org.mariotaku.restfu.http.RestHttpResponse; import org.mariotaku.restfu.http.mime.FileTypedData; +import org.mariotaku.twidere.BuildConfig; import org.mariotaku.twidere.util.BugReporter; import org.mariotaku.twidere.util.TwitterAPIFactory; import org.mariotaku.twidere.util.Utils; @@ -40,6 +41,7 @@ import java.io.IOException; import java.util.ArrayList; import java.util.Date; import java.util.List; +import java.util.Locale; import edu.tsinghua.hotmobi.model.UploadLogEvent; @@ -103,13 +105,16 @@ public class UploadLogsTask implements Runnable { headers.add(Pair.create("X-HotMobi-UUID", uuid)); headers.add(Pair.create("X-HotMobi-Date", dayLogsDir.getName())); headers.add(Pair.create("X-HotMobi-FileName", logFile.getName())); + headers.add(Pair.create("User-Agent", String.format(Locale.ROOT, + "HotMobi (Twidere %s %d)", BuildConfig.VERSION_NAME, + BuildConfig.VERSION_CODE))); builder.headers(headers); body = new FileTypedData(logFile); builder.body(body); final UploadLogEvent uploadLogEvent = UploadLogEvent.create(context, logFile); response = client.execute(builder.build()); if (response.isSuccessful()) { - uploadLogEvent.markEnd(); + uploadLogEvent.finish(response); if (!uploadLogEvent.shouldSkip()) { HotMobiLogger.getInstance(context).log(uploadLogEvent); } diff --git a/twidere/src/main/java/edu/tsinghua/hotmobi/model/UploadLogEvent.java b/twidere/src/main/java/edu/tsinghua/hotmobi/model/UploadLogEvent.java index cb2b95557..12dda2f13 100644 --- a/twidere/src/main/java/edu/tsinghua/hotmobi/model/UploadLogEvent.java +++ b/twidere/src/main/java/edu/tsinghua/hotmobi/model/UploadLogEvent.java @@ -6,10 +6,19 @@ import android.os.Parcelable; import com.bluelinelabs.logansquare.annotation.JsonField; import com.bluelinelabs.logansquare.annotation.JsonObject; +import com.hannesdorfmann.parcelableplease.ParcelBagger; +import com.hannesdorfmann.parcelableplease.annotation.Bagger; import com.hannesdorfmann.parcelableplease.annotation.ParcelablePlease; import com.hannesdorfmann.parcelableplease.annotation.ParcelableThisPlease; +import org.apache.commons.lang3.StringUtils; +import org.apache.commons.lang3.builder.ToStringBuilder; +import org.mariotaku.restfu.Pair; +import org.mariotaku.restfu.http.RestHttpResponse; + import java.io.File; +import java.util.HashMap; +import java.util.Map; /** * Created by mariotaku on 16/1/2. @@ -33,11 +42,13 @@ public class UploadLogEvent extends BaseEvent implements Parcelable { String fileName; @ParcelableThisPlease @JsonField(name = "file_length") - long fileLength; + @ParcelableThisPlease + @Bagger(StringMapBagger.class) + @JsonField(name = "extra_headers") + Map extraHeaders; public long getFileLength() { - return fileLength; } @@ -53,6 +64,14 @@ public class UploadLogEvent extends BaseEvent implements Parcelable { this.fileName = fileName; } + public Map getExtraHeaders() { + return extraHeaders; + } + + public void setExtraHeaders(Map extraHeaders) { + this.extraHeaders = extraHeaders; + } + @Override public int describeContents() { return 0; @@ -63,6 +82,17 @@ public class UploadLogEvent extends BaseEvent implements Parcelable { UploadLogEventParcelablePlease.writeToParcel(this, dest, flags); } + public void finish(RestHttpResponse response) { + HashMap extraHeaders = new HashMap<>(); + for (Pair pair : response.getHeaders()) { + if (StringUtils.startsWithIgnoreCase(pair.first, "X-Dnext")) { + extraHeaders.put(pair.first, pair.second); + } + } + setExtraHeaders(extraHeaders); + markEnd(); + } + public static UploadLogEvent create(Context context, File file) { UploadLogEvent event = new UploadLogEvent(); event.markStart(context); @@ -71,7 +101,44 @@ public class UploadLogEvent extends BaseEvent implements Parcelable { return event; } + @Override + public String toString() { + return new ToStringBuilder(this) + .append("fileName", fileName) + .append("fileLength", fileLength) + .append("extraHeaders", extraHeaders) + .toString(); + } + public boolean shouldSkip() { return fileName.contains("upload_log"); } + + public static class StringMapBagger implements ParcelBagger> { + @Override + public void write(Map value, Parcel out, int flags) { + if (value == null) { + out.writeInt(-1); + } else { + out.writeInt(value.size()); + for (Map.Entry entry : value.entrySet()) { + out.writeString(entry.getKey()); + out.writeString(entry.getValue()); + } + } + } + + @Override + public Map read(Parcel in) { + final int size = in.readInt(); + if (size < 0) return null; + final Map map = new HashMap<>(); + for (int i = 0; i < size; i++) { + final String key = in.readString(); + final String value = in.readString(); + map.put(key, value); + } + return map; + } + } } diff --git a/twidere/src/main/java/org/mariotaku/twidere/fragment/support/StatusFragment.java b/twidere/src/main/java/org/mariotaku/twidere/fragment/support/StatusFragment.java index 2fc9e1b32..8e596975d 100644 --- a/twidere/src/main/java/org/mariotaku/twidere/fragment/support/StatusFragment.java +++ b/twidere/src/main/java/org/mariotaku/twidere/fragment/support/StatusFragment.java @@ -1399,6 +1399,7 @@ public class StatusFragment extends BaseSupportFragment implements LoaderCallbac private List mData; private CharSequence mReplyError, mConversationError; private boolean mRepliesLoading, mConversationsLoading; + private int mReplyStart; public StatusAdapter(StatusFragment fragment, boolean compact) { super(fragment.getContext()); @@ -1474,11 +1475,16 @@ public class StatusFragment extends BaseSupportFragment implements LoaderCallbac public ParcelableStatus getStatus(int position) { final int itemType = getItemType(position); switch (itemType) { - case ITEM_IDX_CONVERSATION: - case ITEM_IDX_REPLY: { + case ITEM_IDX_CONVERSATION: { if (mData == null) return null; return mData.get(position - getIndexStart(ITEM_IDX_CONVERSATION)); } + case ITEM_IDX_REPLY: { + if (mData == null || mReplyStart < 0) return null; + return mData.get(position - getIndexStart(ITEM_IDX_CONVERSATION) + - mItemCounts[ITEM_IDX_CONVERSATION] - mItemCounts[ITEM_IDX_STATUS] + + mReplyStart); + } case ITEM_IDX_STATUS: { return mStatus; } @@ -1551,24 +1557,25 @@ public class StatusFragment extends BaseSupportFragment implements LoaderCallbac if (data == null || data.isEmpty()) { setCount(ITEM_IDX_CONVERSATION, 0); setCount(ITEM_IDX_REPLY, 0); + mReplyStart = -1; } else { int conversationCount = 0, replyCount = 0; - boolean containsStatus = false; + int replyStart = -1; final long statusId = status.is_retweet ? status.retweet_id : status.id; - for (ParcelableStatus item : data) { + for (int i = 0, j = data.size(); i < j; i++) { + ParcelableStatus item = data.get(i); if (item.id < statusId) { conversationCount++; } else if (item.id > statusId) { + if (replyStart < 0) { + replyStart = i; + } replyCount++; - } else { - containsStatus = true; } } - if (!containsStatus) { - throw new IllegalArgumentException("Conversation data must contains original status"); - } setCount(ITEM_IDX_CONVERSATION, conversationCount); setCount(ITEM_IDX_REPLY, replyCount); + mReplyStart = replyStart; } notifyDataSetChanged(); updateItemDecoration(); diff --git a/twidere/src/main/java/org/mariotaku/twidere/fragment/support/card/CardBrowserFragment.java b/twidere/src/main/java/org/mariotaku/twidere/fragment/support/card/CardBrowserFragment.java index 20944cbf0..350c323c4 100644 --- a/twidere/src/main/java/org/mariotaku/twidere/fragment/support/card/CardBrowserFragment.java +++ b/twidere/src/main/java/org/mariotaku/twidere/fragment/support/card/CardBrowserFragment.java @@ -20,6 +20,7 @@ package org.mariotaku.twidere.fragment.support.card; import android.os.Bundle; +import android.support.annotation.NonNull; import android.webkit.WebSettings; import android.webkit.WebView; @@ -37,7 +38,7 @@ public class CardBrowserFragment extends SupportBrowserFragment { settings.setBuiltInZoomControls(false); } - public static CardBrowserFragment show(String uri) { + public static CardBrowserFragment show(@NonNull String uri) { final Bundle args = new Bundle(); args.putString(EXTRA_URI, uri); final CardBrowserFragment fragment = new CardBrowserFragment(); diff --git a/twidere/src/main/java/org/mariotaku/twidere/util/TwitterCardFragmentFactory.java b/twidere/src/main/java/org/mariotaku/twidere/util/TwitterCardFragmentFactory.java index 2c7eddf16..237c2af7a 100644 --- a/twidere/src/main/java/org/mariotaku/twidere/util/TwitterCardFragmentFactory.java +++ b/twidere/src/main/java/org/mariotaku/twidere/util/TwitterCardFragmentFactory.java @@ -19,6 +19,7 @@ package org.mariotaku.twidere.util; +import android.support.annotation.Nullable; import android.support.v4.app.Fragment; import org.mariotaku.twidere.fragment.support.card.CardBrowserFragment; @@ -41,7 +42,9 @@ public abstract class TwitterCardFragmentFactory { return new TwitterCardFragmentFactoryImpl(); } - public static Fragment createGenericPlayerFragment(ParcelableCardEntity card) { + @Nullable + public static Fragment createGenericPlayerFragment(@Nullable ParcelableCardEntity card) { + if (card == null) return null; final String playerUrl = card.getString("player_url"); if (playerUrl == null) return null; return CardBrowserFragment.show(playerUrl);