Handle Redgifs links.

This commit is contained in:
Docile-Alligator 2025-08-30 12:51:18 -04:00
parent 51ec964568
commit 988c46fce2
9 changed files with 89 additions and 31 deletions

View File

@ -203,7 +203,7 @@ abstract class NetworkModule {
return new RedgifsAccessTokenAuthenticator(currentAccountSharedPreferences);
}
@Provides
/*@Provides
@Named("redgifs")
@Singleton
static Retrofit provideRedgifsRetrofit(@Named("RedgifsAccessTokenAuthenticator") Interceptor accessTokenAuthenticator,
@ -224,6 +224,27 @@ abstract class NetworkModule {
.baseUrl(APIUtils.REDGIFS_API_BASE_URI)
.client(okHttpClientBuilder.build())
.build();
}*/
@Provides
@Named("redgifs")
@Singleton
static Retrofit provideRedgifsRetrofit(@Named("base") OkHttpClient httpClient,
@Named("base") Retrofit retrofit,
ConnectionPool connectionPool) {
OkHttpClient.Builder okHttpClientBuilder = httpClient.newBuilder()
/*.addInterceptor(chain -> chain.proceed(
chain.request()
.newBuilder()
.header("User-Agent", APIUtils.USER_AGENT)
.build()
))*/
.connectionPool(connectionPool);
return retrofit.newBuilder()
.baseUrl(APIUtils.OH_MY_DL_BASE_URI)
.client(okHttpClientBuilder.build())
.build();
}
@Provides

View File

@ -684,9 +684,9 @@ public class ViewVideoActivity extends AppCompatActivity implements CustomFontRe
}
redgifsId = intent.getStringExtra(EXTRA_REDGIFS_ID);
if (redgifsId != null && redgifsId.contains("-")) {
/*if (redgifsId != null && redgifsId.contains("-")) {
redgifsId = redgifsId.substring(0, redgifsId.indexOf('-'));
}
}*/
videoFileName = "Redgifs-" + redgifsId + ".mp4";
} else if (videoType == VIDEO_TYPE_DIRECT || videoType == VIDEO_TYPE_IMGUR) {
videoDownloadUrl = mVideoUri.toString();
@ -1007,7 +1007,7 @@ public class ViewVideoActivity extends AppCompatActivity implements CustomFontRe
if (videoType != VIDEO_TYPE_NORMAL) {
PersistableBundle extras = new PersistableBundle();
if (post.getPostType() == Post.GIF_TYPE) {
if (post != null && post.getPostType() == Post.GIF_TYPE) {
extras.putString(DownloadMediaService.EXTRA_URL, post.getVideoUrl());
extras.putInt(DownloadMediaService.EXTRA_MEDIA_TYPE, DownloadMediaService.EXTRA_MEDIA_TYPE_GIF);
extras.putString(DownloadMediaService.EXTRA_FILE_NAME, post.getSubredditName()

View File

@ -87,7 +87,6 @@ import ml.docilealligator.infinityforreddit.activities.ViewRedditGalleryActivity
import ml.docilealligator.infinityforreddit.activities.ViewSubredditDetailActivity;
import ml.docilealligator.infinityforreddit.activities.ViewUserDetailActivity;
import ml.docilealligator.infinityforreddit.activities.ViewVideoActivity;
import ml.docilealligator.infinityforreddit.apis.RedgifsAPI;
import ml.docilealligator.infinityforreddit.apis.StreamableAPI;
import ml.docilealligator.infinityforreddit.asynctasks.LoadSubredditIcon;
import ml.docilealligator.infinityforreddit.asynctasks.LoadUserData;
@ -119,7 +118,6 @@ import ml.docilealligator.infinityforreddit.markdown.MarkdownUtils;
import ml.docilealligator.infinityforreddit.post.FetchStreamableVideo;
import ml.docilealligator.infinityforreddit.post.Post;
import ml.docilealligator.infinityforreddit.post.PostPagingSource;
import ml.docilealligator.infinityforreddit.thing.FetchRedgifsVideoLinks;
import ml.docilealligator.infinityforreddit.thing.SaveThing;
import ml.docilealligator.infinityforreddit.thing.StreamableVideo;
import ml.docilealligator.infinityforreddit.thing.VoteThing;
@ -727,7 +725,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
((PostDetailBaseVideoAutoplayViewHolder) holder).setVolume((mMuteAutoplayingVideos || (mPost.isNSFW() && mMuteNSFWVideo)) ? 0f : 1f);
}
if (mPost.isRedgifs() && !mPost.isLoadRedgifsOrStreamableVideoSuccess()) {
/*if (mPost.isRedgifs() && !mPost.isLoadedStreamableVideoAlready()) {
((PostDetailBaseVideoAutoplayViewHolder) holder).fetchRedgifsOrStreamableVideoCall =
mRedgifsRetrofit.create(RedgifsAPI.class)
.getRedgifsData(APIUtils.getRedgifsOAuthHeader(
@ -740,7 +738,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
public void onFetchRedgifsVideoLinkSuccess(String webm, String mp4) {
mPost.setVideoDownloadUrl(mp4);
mPost.setVideoUrl(mp4);
mPost.setLoadRedgifsOrStreamableVideoSuccess(true);
mPost.setLoadedStreamableVideoAlready(true);
((PostDetailBaseVideoAutoplayViewHolder) holder).bindVideoUri(Uri.parse(mPost.getVideoUrl()));
}
@ -749,7 +747,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
((PostDetailBaseVideoAutoplayViewHolder) holder).loadFallbackDirectVideo();
}
});
} else if(mPost.isStreamable() && !mPost.isLoadRedgifsOrStreamableVideoSuccess()) {
} else */if(mPost.isStreamable() && !mPost.isLoadedStreamableVideoAlready()) {
((PostDetailBaseVideoAutoplayViewHolder) holder).fetchRedgifsOrStreamableVideoCall =
mStreamableApiProvider.get().getStreamableData(mPost.getStreamableShortCode());
FetchStreamableVideo.fetchStreamableVideoInRecyclerViewAdapter(mExecutor, new Handler(),
@ -760,7 +758,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
StreamableVideo.Media media = streamableVideo.mp4 == null ? streamableVideo.mp4Mobile : streamableVideo.mp4;
mPost.setVideoDownloadUrl(media.url);
mPost.setVideoUrl(media.url);
mPost.setLoadRedgifsOrStreamableVideoSuccess(true);
mPost.setLoadedStreamableVideoAlready(true);
((PostDetailBaseVideoAutoplayViewHolder) holder).bindVideoUri(Uri.parse(mPost.getVideoUrl()));
}
@ -1072,7 +1070,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
} else if (post.isStreamable()) {
intent.putExtra(ViewVideoActivity.EXTRA_VIDEO_TYPE, ViewVideoActivity.VIDEO_TYPE_STREAMABLE);
intent.putExtra(ViewVideoActivity.EXTRA_STREAMABLE_SHORT_CODE, post.getStreamableShortCode());
if (post.isLoadRedgifsOrStreamableVideoSuccess()) {
if (post.isLoadedStreamableVideoAlready()) {
intent.setData(Uri.parse(post.getVideoUrl()));
intent.putExtra(ViewVideoActivity.EXTRA_VIDEO_DOWNLOAD_URL, post.getVideoDownloadUrl());
}
@ -1899,7 +1897,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
mediaUri = Uri.parse(mPost.getVideoFallBackDirectUrl());
mPost.setVideoDownloadUrl(mPost.getVideoFallBackDirectUrl());
mPost.setVideoUrl(mPost.getVideoFallBackDirectUrl());
mPost.setLoadRedgifsOrStreamableVideoSuccess(true);
mPost.setLoadedStreamableVideoAlready(true);
if (container != null) {
container.onScrollStateChanged(RecyclerView.SCROLL_STATE_IDLE);
}

View File

@ -121,7 +121,6 @@ import ml.docilealligator.infinityforreddit.post.FetchStreamableVideo;
import ml.docilealligator.infinityforreddit.post.MarkPostAsReadInterface;
import ml.docilealligator.infinityforreddit.post.Post;
import ml.docilealligator.infinityforreddit.post.PostPagingSource;
import ml.docilealligator.infinityforreddit.thing.FetchRedgifsVideoLinks;
import ml.docilealligator.infinityforreddit.thing.SaveThing;
import ml.docilealligator.infinityforreddit.thing.StreamableVideo;
import ml.docilealligator.infinityforreddit.thing.VoteThing;
@ -1835,7 +1834,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
} else if (post.isStreamable()) {
intent.putExtra(ViewVideoActivity.EXTRA_VIDEO_TYPE, ViewVideoActivity.VIDEO_TYPE_STREAMABLE);
intent.putExtra(ViewVideoActivity.EXTRA_STREAMABLE_SHORT_CODE, post.getStreamableShortCode());
if (post.isLoadRedgifsOrStreamableVideoSuccess()) {
if (post.isLoadedStreamableVideoAlready()) {
intent.setData(Uri.parse(post.getVideoUrl()));
intent.putExtra(ViewVideoActivity.EXTRA_VIDEO_DOWNLOAD_URL, post.getVideoDownloadUrl());
}
@ -2654,7 +2653,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
void loadVideo(int position) {
Post post = getPost();
if (post.isRedgifs() && !post.isLoadRedgifsOrStreamableVideoSuccess()) {
/*if (post.isRedgifs() && !post.isLoadedStreamableVideoAlready()) {
fetchRedgifsOrStreamableVideoCall =
mRedgifsRetrofit.create(RedgifsAPI.class).getRedgifsData(
APIUtils.getRedgifsOAuthHeader(mCurrentAccountSharedPreferences
@ -2667,7 +2666,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
public void onFetchRedgifsVideoLinkSuccess(String webm, String mp4) {
post.setVideoDownloadUrl(mp4);
post.setVideoUrl(mp4);
post.setLoadRedgifsOrStreamableVideoSuccess(true);
post.setLoadedStreamableVideoAlready(true);
if (position == getAdapterPosition()) {
bindVideoUri(Uri.parse(post.getVideoUrl()));
}
@ -2680,7 +2679,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
}
}
});
} else if(post.isStreamable() && !post.isLoadRedgifsOrStreamableVideoSuccess()) {
} else */if(post.isStreamable() && !post.isLoadedStreamableVideoAlready()) {
fetchRedgifsOrStreamableVideoCall =
mStreamableApiProvider.get().getStreamableData(post.getStreamableShortCode());
FetchStreamableVideo.fetchStreamableVideoInRecyclerViewAdapter(mExecutor, new Handler(),
@ -2691,7 +2690,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
StreamableVideo.Media media = streamableVideo.mp4 == null ? streamableVideo.mp4Mobile : streamableVideo.mp4;
post.setVideoDownloadUrl(media.url);
post.setVideoUrl(media.url);
post.setLoadRedgifsOrStreamableVideoSuccess(true);
post.setLoadedStreamableVideoAlready(true);
if (position == getAdapterPosition()) {
bindVideoUri(Uri.parse(post.getVideoUrl()));
}
@ -2715,7 +2714,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
mediaUri = Uri.parse(post.getVideoFallBackDirectUrl());
post.setVideoDownloadUrl(post.getVideoFallBackDirectUrl());
post.setVideoUrl(post.getVideoFallBackDirectUrl());
post.setLoadRedgifsOrStreamableVideoSuccess(true);
post.setLoadedStreamableVideoAlready(true);
if (container != null) {
container.onScrollStateChanged(RecyclerView.SCROLL_STATE_IDLE);
}

View File

@ -0,0 +1,19 @@
package ml.docilealligator.infinityforreddit.apis
import retrofit2.Call
import retrofit2.http.Body
import retrofit2.http.FieldMap
import retrofit2.http.FormUrlEncoded
import retrofit2.http.GET
import retrofit2.http.HeaderMap
import retrofit2.http.POST
import retrofit2.http.Path
import retrofit2.http.Query
interface OhMyDlAPI {
@FormUrlEncoded
@POST("/api/download")
fun getRedgifsData(
@FieldMap params: Map<String, String>
): Call<String>
}

View File

@ -50,7 +50,7 @@ public class Post implements Parcelable {
private boolean isImgur;
private boolean isRedgifs;
private boolean isStreamable;
private boolean loadRedgifsOrStreamableVideoSuccess;
private boolean loadedStreamableVideoAlready;
private final String permalink;
private String flair;
private final long postTimeMillis;
@ -195,7 +195,7 @@ public class Post implements Parcelable {
isImgur = in.readByte() != 0;
isRedgifs = in.readByte() != 0;
isStreamable = in.readByte() != 0;
loadRedgifsOrStreamableVideoSuccess = in.readByte() != 0;
loadedStreamableVideoAlready = in.readByte() != 0;
permalink = in.readString();
flair = in.readString();
postTimeMillis = in.readLong();
@ -410,12 +410,12 @@ public class Post implements Parcelable {
return postType == Post.VIDEO_TYPE && !isImgur && !isRedgifs && !isStreamable;
}
public boolean isLoadRedgifsOrStreamableVideoSuccess() {
return loadRedgifsOrStreamableVideoSuccess;
public boolean isLoadedStreamableVideoAlready() {
return loadedStreamableVideoAlready;
}
public void setLoadRedgifsOrStreamableVideoSuccess(boolean loadRedgifsOrStreamableVideoSuccess) {
this.loadRedgifsOrStreamableVideoSuccess = loadRedgifsOrStreamableVideoSuccess;
public void setLoadedStreamableVideoAlready(boolean loadedStreamableVideoAlready) {
this.loadedStreamableVideoAlready = loadedStreamableVideoAlready;
}
public String getPermalink() {
@ -540,7 +540,7 @@ public class Post implements Parcelable {
dest.writeByte((byte) (isImgur ? 1 : 0));
dest.writeByte((byte) (isRedgifs ? 1 : 0));
dest.writeByte((byte) (isStreamable ? 1 : 0));
dest.writeByte((byte) (loadRedgifsOrStreamableVideoSuccess ? 1 : 0));
dest.writeByte((byte) (loadedStreamableVideoAlready ? 1 : 0));
dest.writeString(permalink);
dest.writeString(flair);
dest.writeLong(postTimeMillis);

View File

@ -136,7 +136,7 @@ public class DownloadMediaService extends JobService {
extras.putInt(EXTRA_IS_NSFW, post.isNSFW() ? 1 : 0);
} else if (post.getPostType() == Post.VIDEO_TYPE) {
if (post.isStreamable()) {
if (post.isLoadRedgifsOrStreamableVideoSuccess()) {
if (post.isLoadedStreamableVideoAlready()) {
extras.putString(EXTRA_URL, post.getVideoUrl());
} else {
extras.putString(EXTRA_REDGIFS_ID, post.getRedgifsId());
@ -144,7 +144,7 @@ public class DownloadMediaService extends JobService {
extras.putString(EXTRA_FILE_NAME, "Streamable-" + post.getStreamableShortCode() + ".mp4");
} else if (post.isRedgifs()) {
if (post.isLoadRedgifsOrStreamableVideoSuccess()) {
if (post.isLoadedStreamableVideoAlready()) {
extras.putString(EXTRA_URL, post.getVideoUrl());
} else {
extras.putString(EXTRA_STREAMABLE_SHORT_CODE, post.getStreamableShortCode());

View File

@ -10,9 +10,12 @@ import org.json.JSONException;
import org.json.JSONObject;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.Executor;
import ml.docilealligator.infinityforreddit.FetchVideoLinkListener;
import ml.docilealligator.infinityforreddit.apis.OhMyDlAPI;
import ml.docilealligator.infinityforreddit.apis.RedgifsAPI;
import ml.docilealligator.infinityforreddit.utils.APIUtils;
import ml.docilealligator.infinityforreddit.utils.JSONUtils;
@ -28,7 +31,7 @@ public class FetchRedgifsVideoLinks {
FetchVideoLinkListener fetchVideoLinkListener) {
executor.execute(() -> {
try {
Response<String> response = redgifsRetrofit
/*Response<String> response = redgifsRetrofit
.create(RedgifsAPI.class)
.getRedgifsData(
APIUtils.getRedgifsOAuthHeader(currentAccountSharedPreferences.getString(SharedPreferencesUtils.REDGIFS_ACCESS_TOKEN, "")),
@ -38,6 +41,20 @@ public class FetchRedgifsVideoLinks {
parseRedgifsVideoLinks(handler, response.body(), fetchVideoLinkListener);
} else {
handler.post(() -> fetchVideoLinkListener.failed(null));
}*/
Map<String, String> params = new HashMap<>();
params.put(APIUtils.PLATFORM_KEY, "redgifs");
params.put(APIUtils.URL_KEY, "https://www.redgifs.com/watch/" + redgifsId);
Response<String> response = redgifsRetrofit
.create(OhMyDlAPI.class)
.getRedgifsData(params)
.execute();
if (response.isSuccessful()) {
parseRedgifsVideoLinks(handler, response.body(), fetchVideoLinkListener);
} else {
handler.post(() -> fetchVideoLinkListener.failed(null));
}
} catch (IOException e) {
e.printStackTrace();
@ -90,13 +107,16 @@ public class FetchRedgifsVideoLinks {
private static void parseRedgifsVideoLinks(Handler handler, String response,
FetchVideoLinkListener fetchVideoLinkListener) {
try {
String mp4 = new JSONObject(response).getJSONObject(JSONUtils.GIF_KEY).getJSONObject(JSONUtils.URLS_KEY)
/*String mp4 = new JSONObject(response).getJSONObject(JSONUtils.GIF_KEY).getJSONObject(JSONUtils.URLS_KEY)
.getString(JSONUtils.HD_KEY);
if (mp4.contains("-silent")) {
mp4 = mp4.substring(0, mp4.indexOf("-silent")) + ".mp4";
}
final String mp4Name = mp4;
handler.post(() -> fetchVideoLinkListener.onFetchRedgifsVideoLinkSuccess(mp4Name, mp4Name));
handler.post(() -> fetchVideoLinkListener.onFetchRedgifsVideoLinkSuccess(mp4Name, mp4Name));*/
String mp4 = new JSONObject(response).getString(JSONUtils.VIDEO_DOWNLOAD_URL);
handler.post(() -> fetchVideoLinkListener.onFetchRedgifsVideoLinkSuccess(mp4, mp4));
} catch (JSONException e) {
e.printStackTrace();
handler.post(() -> fetchVideoLinkListener.failed(null));

View File

@ -207,6 +207,7 @@ public class JSONUtils {
public static final String SPAM_KEY = "spam";
public static final String O_EMBED_KEY = "oembed";
public static final String THUMBNAIL_URL_KEY = "thumbnail_url";
public static final String VIDEO_DOWNLOAD_URL = "videoDownloadUrl";
@Nullable
public static Map<String, MediaMetadata> parseMediaMetadata(JSONObject data) {