pull/123/head
FongMi 3 years ago
parent 1a4d14da59
commit 6a6ec6a04a
  1. 13
      app/src/main/java/com/fongmi/android/tv/api/ApiConfig.java
  2. 18
      app/src/main/java/com/fongmi/android/tv/bean/Parse.java
  3. 10
      app/src/main/java/com/fongmi/android/tv/bean/Result.java
  4. 32
      app/src/main/java/com/fongmi/android/tv/bean/Rule.java
  5. 8
      app/src/main/java/com/fongmi/android/tv/bean/Site.java
  6. 3
      app/src/main/java/com/fongmi/android/tv/impl/ParseCallback.java
  7. 10
      app/src/main/java/com/fongmi/android/tv/impl/WebCallback.java
  8. 3
      app/src/main/java/com/fongmi/android/tv/model/SiteViewModel.java
  9. 21
      app/src/main/java/com/fongmi/android/tv/player/ExoUtil.java
  10. 11
      app/src/main/java/com/fongmi/android/tv/player/Players.java
  11. 16
      app/src/main/java/com/fongmi/android/tv/player/parse/ParseJob.java
  12. 10
      app/src/main/java/com/fongmi/android/tv/ui/custom/CustomWebView.java

@ -4,6 +4,7 @@ import android.text.TextUtils;
import com.fongmi.android.tv.App;
import com.fongmi.android.tv.R;
import com.fongmi.android.tv.bean.Rule;
import com.fongmi.android.tv.bean.Config;
import com.fongmi.android.tv.bean.Depot;
import com.fongmi.android.tv.bean.Parse;
@ -31,6 +32,7 @@ public class ApiConfig {
private List<Site> sites;
private List<Parse> parses;
private List<String> flags;
private List<Rule> rules;
private JarLoader jarLoader;
private PyLoader pyLoader;
private JsLoader jsLoader;
@ -84,6 +86,7 @@ public class ApiConfig {
this.config = Config.vod();
this.sites = new ArrayList<>();
this.flags = new ArrayList<>();
this.rules = new ArrayList<>();
this.parses = new ArrayList<>();
this.jarLoader = new JarLoader();
this.pyLoader = new PyLoader();
@ -103,6 +106,7 @@ public class ApiConfig {
this.parse = null;
this.sites.clear();
this.flags.clear();
this.rules.clear();
this.parses.clear();
this.jarLoader.clear();
this.pyLoader.clear();
@ -197,6 +201,7 @@ public class ApiConfig {
if (parses.size() > 0) parses.add(0, Parse.god());
if (home == null) setHome(sites.isEmpty() ? new Site() : sites.get(0));
if (parse == null) setParse(parses.isEmpty() ? new Parse() : parses.get(0));
setRules(Rule.arrayFrom(object.getAsJsonArray("rules")));
setFlags(Json.safeListString(object, "flags"));
setWall(Json.safeString(object, "wallpaper"));
setAds(Json.safeListString(object, "ads"));
@ -285,6 +290,14 @@ public class ApiConfig {
this.flags.addAll(flags);
}
public List<Rule> getRules() {
return rules == null ? Collections.emptyList() : rules;
}
public void setRules(List<Rule> rules) {
this.rules = rules;
}
public String getAds() {
return TextUtils.isEmpty(ads) ? "" : ads;
}

@ -102,14 +102,6 @@ public class Parse {
this.activated = item.equals(this);
}
public List<String> getAds() {
return getExt().getAds();
}
public void setAds(List<String> ads) {
getExt().setAds(ads);
}
public Map<String, String> getHeaders() {
return Json.toMap(getExt().getHeader());
}
@ -142,21 +134,11 @@ public class Parse {
public static class Ext {
@SerializedName("ads")
private List<String> ads;
@SerializedName("flag")
private List<String> flag;
@SerializedName("header")
private JsonElement header;
public List<String> getAds() {
return ads == null ? Collections.emptyList() : ads;
}
public void setAds(List<String> ads) {
this.ads = ads;
}
public void setFlag(List<String> flag) {
this.flag = flag;
}

@ -56,8 +56,6 @@ public class Result {
private String key;
@SerializedName("subs")
private List<Sub> subs;
@SerializedName("ads")
private List<String> ads;
public static Result fromJson(String str) {
try {
@ -192,14 +190,6 @@ public class Result {
return subs == null ? Collections.emptyList() : subs;
}
public List<String> getAds() {
return ads == null ? Collections.emptyList() : ads;
}
public void setAds(List<String> ads) {
this.ads = ads;
}
public String getRealUrl() {
return getPlayUrl() + getUrl();
}

@ -0,0 +1,32 @@
package com.fongmi.android.tv.bean;
import com.google.gson.Gson;
import com.google.gson.JsonElement;
import com.google.gson.annotations.SerializedName;
import com.google.gson.reflect.TypeToken;
import java.lang.reflect.Type;
import java.util.Collections;
import java.util.List;
public class Rule {
@SerializedName("hosts")
private List<String> hosts;
@SerializedName("regex")
private List<String> regex;
public static List<Rule> arrayFrom(JsonElement element) {
Type listType = new TypeToken<List<Rule>>() {}.getType();
List<Rule> items = new Gson().fromJson(element, listType);
return items == null ? Collections.emptyList() : items;
}
public List<String> getHosts() {
return hosts == null ? Collections.emptyList() : hosts;
}
public List<String> getRegex() {
return regex == null ? Collections.emptyList() : regex;
}
}

@ -15,7 +15,7 @@ import com.google.gson.annotations.SerializedName;
import java.util.Collections;
import java.util.List;
@Entity(ignoredColumns = {"type", "api", "playUrl", "playerType", "ext", "jar", "categories", "ads"})
@Entity(ignoredColumns = {"type", "api", "playUrl", "playerType", "ext", "jar", "categories"})
public class Site {
@NonNull
@ -44,8 +44,6 @@ public class Site {
private String jar;
@SerializedName("categories")
private List<String> categories;
@SerializedName("ads")
private List<String> ads;
private boolean activated;
@ -150,10 +148,6 @@ public class Site {
return categories == null ? Collections.emptyList() : categories;
}
public List<String> getAds() {
return ads == null ? Collections.emptyList() : ads;
}
public boolean isActivated() {
return activated;
}

@ -1,11 +1,10 @@
package com.fongmi.android.tv.impl;
import java.util.List;
import java.util.Map;
public interface ParseCallback {
void onParseSuccess(List<String> ads, Map<String, String> headers, String url, String from);
void onParseSuccess(Map<String, String> headers, String url, String from);
void onParseError();
}

@ -1,10 +0,0 @@
package com.fongmi.android.tv.impl;
import java.util.Map;
public interface WebCallback {
void onSniffSuccess(Map<String, String> headers, String url, String from);
void onSniffError();
}

@ -142,7 +142,6 @@ public class SiteViewModel extends ViewModel {
ApiConfig.get().setJar(site.getJar());
Result result = Result.objectFrom(playerContent);
if (result.getFlag().isEmpty()) result.setFlag(flag);
if (result.getAds().isEmpty()) result.setAds(site.getAds());
result.setKey(key);
return result;
} else if (site.getType() == 4) {
@ -153,7 +152,6 @@ public class SiteViewModel extends ViewModel {
SpiderDebug.log(body);
Result result = Result.fromJson(body);
if (result.getFlag().isEmpty()) result.setFlag(flag);
if (result.getAds().isEmpty()) result.setAds(site.getAds());
return result;
} else {
String url = id;
@ -162,7 +160,6 @@ public class SiteViewModel extends ViewModel {
Result result = new Result();
result.setUrl(url);
result.setFlag(flag);
result.setAds(site.getAds());
result.setPlayUrl(site.getPlayUrl());
result.setParse(Utils.isVideoFormat(url) && result.getPlayUrl().isEmpty() ? 0 : 1);
return result;

@ -33,6 +33,8 @@ import androidx.media3.extractor.ts.TsExtractor;
import androidx.media3.ui.CaptionStyleCompat;
import com.fongmi.android.tv.App;
import com.fongmi.android.tv.api.ApiConfig;
import com.fongmi.android.tv.bean.Rule;
import com.fongmi.android.tv.bean.Result;
import com.fongmi.android.tv.bean.Sub;
import com.fongmi.android.tv.utils.FileUtil;
@ -78,26 +80,31 @@ public class ExoUtil {
}
public static MediaSource getSource(Result result, int errorCode) {
return getSource(result.getAds(), result.getHeaders(), result.getRealUrl(), result.getSubs(), errorCode);
return getSource(result.getHeaders(), result.getRealUrl(), result.getSubs(), errorCode);
}
public static MediaSource getSource(List<String> ads, Map<String, String> headers, String url, int errorCode) {
return getSource(ads, headers, url, Collections.emptyList(), errorCode);
public static MediaSource getSource(Map<String, String> headers, String url, int errorCode) {
return getSource(headers, url, Collections.emptyList(), errorCode);
}
private static MediaSource getSource(List<String> ads, Map<String, String> headers, String url, List<Sub> subs, int errorCode) {
private static MediaSource getSource(Map<String, String> headers, String url, List<Sub> subs, int errorCode) {
Uri uri = Uri.parse(url.trim().replace("\\", ""));
if (uri.getUserInfo() != null) headers.put(HttpHeaders.AUTHORIZATION, "Basic " + Base64.encodeToString(uri.getUserInfo().getBytes(), Base64.NO_WRAP));
return new DefaultMediaSourceFactory(getDataSourceFactory(headers), getExtractorsFactory()).createMediaSource(getMediaItem(ads, uri, subs, errorCode));
return new DefaultMediaSourceFactory(getDataSourceFactory(headers), getExtractorsFactory()).createMediaSource(getMediaItem(uri, subs, errorCode));
}
private static MediaItem getMediaItem(List<String> ads, Uri uri, List<Sub> subs, int errorCode) {
private static MediaItem getMediaItem(Uri uri, List<Sub> subs, int errorCode) {
MediaItem.Builder builder = new MediaItem.Builder().setUri(uri);
if (errorCode == PlaybackException.ERROR_CODE_PARSING_MANIFEST_MALFORMED) builder.setMimeType(MimeTypes.APPLICATION_OCTET);
else if (errorCode == PlaybackException.ERROR_CODE_PARSING_CONTAINER_UNSUPPORTED) builder.setMimeType(MimeTypes.APPLICATION_M3U8);
if (subs.size() > 0) builder.setSubtitleConfigurations(getSubtitles(subs));
builder.setAllowChunklessPreparation(Prefers.getDecode() == 1);
return builder.setAds(ads).build();
return builder.setAds(getRegex(uri)).build();
}
private static List<String> getRegex(Uri uri) {
for (Rule rule : ApiConfig.get().getRules()) for (String host : rule.getHosts()) if (uri.getHost().contains(host)) return rule.getRegex();
return Collections.emptyList();
}
private static List<MediaItem.SubtitleConfiguration> getSubtitles(List<Sub> subs) {

@ -25,7 +25,6 @@ import com.fongmi.android.tv.utils.ResUtil;
import com.github.catvod.crawler.SpiderDebug;
import com.google.common.collect.ImmutableList;
import java.util.Collections;
import java.util.Formatter;
import java.util.List;
import java.util.Locale;
@ -337,13 +336,9 @@ public class Players implements Player.Listener, IMediaPlayer.Listener, Analytic
}
private void setMediaSource(Map<String, String> headers, String url) {
setMediaSource(Collections.emptyList(), headers, url);
}
private void setMediaSource(List<String> ads, Map<String, String> headers, String url) {
SpiderDebug.log(errorCode + "," + url + "," + headers);
if (isIjk()) ijkPlayer.setMediaSource(url, headers);
if (isExo()) exoPlayer.setMediaSource(ExoUtil.getSource(ads, headers, url, errorCode));
if (isExo()) exoPlayer.setMediaSource(ExoUtil.getSource(headers, url, errorCode));
if (isExo()) exoPlayer.prepare();
setTimeoutCheck(url);
}
@ -379,9 +374,9 @@ public class Players implements Player.Listener, IMediaPlayer.Listener, Analytic
}
@Override
public void onParseSuccess(List<String> ads, Map<String, String> headers, String url, String from) {
public void onParseSuccess(Map<String, String> headers, String url, String from) {
if (from.length() > 0) Notify.show(ResUtil.getString(R.string.parse_from, from));
setMediaSource(ads, headers, url);
setMediaSource(headers, url);
}
@Override

@ -6,7 +6,6 @@ import com.fongmi.android.tv.api.ApiConfig;
import com.fongmi.android.tv.bean.Parse;
import com.fongmi.android.tv.bean.Result;
import com.fongmi.android.tv.impl.ParseCallback;
import com.fongmi.android.tv.impl.WebCallback;
import com.fongmi.android.tv.net.OkHttp;
import com.fongmi.android.tv.ui.custom.CustomWebView;
import com.fongmi.android.tv.utils.Json;
@ -26,7 +25,7 @@ import java.util.concurrent.TimeUnit;
import okhttp3.Headers;
public class ParseJob implements WebCallback {
public class ParseJob implements ParseCallback {
private final List<CustomWebView> webViews;
private ExecutorService executor;
@ -56,7 +55,6 @@ public class ParseJob implements WebCallback {
if (result.getPlayUrl().startsWith("json:")) parse = Parse.get(1, result.getPlayUrl().substring(5));
if (result.getPlayUrl().startsWith("parse:")) parse = ApiConfig.get().getParse(result.getPlayUrl().substring(6));
if (parse == null) parse = Parse.get(0, result.getPlayUrl(), result.getHeader());
if (parse.getAds().isEmpty()) parse.setAds(result.getAds());
}
private void execute(Result result) {
@ -186,22 +184,14 @@ public class ParseJob implements WebCallback {
}
@Override
public void onSniffSuccess(Map<String, String> headers, String url, String from) {
onParseSuccess(headers, url, from);
}
@Override
public void onSniffError() {
onParseError();
}
public void onParseSuccess(Map<String, String> headers, String url, String from) {
App.post(() -> {
if (callback != null) callback.onParseSuccess(parse.getAds(), headers, url, from);
if (callback != null) callback.onParseSuccess(headers, url, from);
stop();
});
}
@Override
public void onParseError() {
App.post(() -> {
if (callback != null) callback.onParseError();

@ -19,7 +19,7 @@ import com.fongmi.android.tv.App;
import com.fongmi.android.tv.Constant;
import com.fongmi.android.tv.api.ApiConfig;
import com.fongmi.android.tv.bean.Site;
import com.fongmi.android.tv.impl.WebCallback;
import com.fongmi.android.tv.impl.ParseCallback;
import com.fongmi.android.tv.utils.Utils;
import com.github.catvod.crawler.Spider;
@ -32,7 +32,7 @@ import java.util.Map;
public class CustomWebView extends WebView {
private WebResourceResponse empty;
private WebCallback callback;
private ParseCallback callback;
private List<String> keys;
private Runnable timer;
private String from;
@ -71,7 +71,7 @@ public class CustomWebView extends WebView {
}
}
public CustomWebView start(String key, String from, Map<String, String> headers, String url, WebCallback callback) {
public CustomWebView start(String key, String from, Map<String, String> headers, String url, ParseCallback callback) {
App.post(timer, Constant.TIMEOUT_PARSE_WEB);
this.callback = callback;
setUserAgent(headers);
@ -136,13 +136,13 @@ public class CustomWebView extends WebView {
}
private void onParseSuccess(Map<String, String> news, String url) {
if (callback != null) callback.onSniffSuccess(news, url, from);
if (callback != null) callback.onParseSuccess(news, url, from);
App.post(() -> stop(false));
callback = null;
}
private void onParseError() {
if (callback != null) callback.onSniffError();
if (callback != null) callback.onParseError();
callback = null;
}
}

Loading…
Cancel
Save