From dae4748674312501e44c1cccdc97a5e8cd6a7a9c Mon Sep 17 00:00:00 2001
From: fengyuecanzhu <1021300691@qq.com>
Date: Sun, 16 May 2021 13:54:30 +0800
Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E5=A4=8Dbug?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
.idea/assetWizardSettings.xml | 4 +-
app/src/main/assets/updatelog.fy | 6 +
.../xyz/fycz/myreader/application/App.java | 3 +-
.../myreader/application/CrashHandler.java | 149 ++++++++++++++++
.../xyz/fycz/myreader/base/BaseActivity.java | 1 +
.../myreader/base/BitIntentDataManager.java | 50 ++++++
.../xyz/fycz/myreader/common/APPCONST.java | 1 +
.../entity/sourceedit/EditEntityUtil.kt | 4 +
.../entity/thirdsource/ThirdSourceUtil.java | 6 +-
.../fycz/myreader/greendao/entity/Book.java | 64 ++++++-
.../greendao/entity/rule/FindRule.java | 14 +-
.../greendao/entity/rule/InfoRule.java | 25 ++-
.../sourceAnalyzer/BookSourceManager.java | 16 +-
.../third2/analyzeRule/AnalyzeByRegex.java | 33 +++-
.../model/third2/content/BookInfo.java | 101 +++++++----
.../model/third2/content/BookList.java | 168 ++++++++++--------
.../ui/activity/BookDetailedActivity.java | 51 ++++--
.../ui/activity/BookstoreActivity.java | 3 +-
.../myreader/ui/activity/ReadActivity.java | 12 ++
.../ui/activity/SearchBookActivity.java | 3 +-
.../ui/activity/SourceDebugActivity.java | 1 +
.../ui/adapter/holder/SearchBookHolder.java | 18 +-
.../fycz/myreader/util/help/JsExtensions.java | 4 +-
.../xyz/fycz/myreader/util/utils/AdUtils.java | 6 +-
.../xyz/fycz/myreader/util/utils/MD5Utils.kt | 2 +-
.../xyz/fycz/myreader/webapi/BookApi.java | 2 +
.../fycz/myreader/webapi/ThirdSourceApi.java | 31 ++--
app/src/main/res/drawable/ic_source.xml | 7 +-
app/src/main/res/layout/fragment_mine.xml | 6 +-
app/src/main/res/menu/menu_book_detail.xml | 5 +
app/src/main/res/menu/menu_read.xml | 6 +
app/src/main/res/values/strings.xml | 3 +-
app/version_code.properties | 4 +-
33 files changed, 619 insertions(+), 190 deletions(-)
create mode 100644 app/src/main/java/xyz/fycz/myreader/application/CrashHandler.java
create mode 100644 app/src/main/java/xyz/fycz/myreader/base/BitIntentDataManager.java
diff --git a/.idea/assetWizardSettings.xml b/.idea/assetWizardSettings.xml
index d748352..c0f43a2 100644
--- a/.idea/assetWizardSettings.xml
+++ b/.idea/assetWizardSettings.xml
@@ -14,8 +14,8 @@
diff --git a/app/src/main/assets/updatelog.fy b/app/src/main/assets/updatelog.fy
index adc871a..2deae15 100644
--- a/app/src/main/assets/updatelog.fy
+++ b/app/src/main/assets/updatelog.fy
@@ -1,9 +1,15 @@
+2021.05.15
+风月读书v1.9.8-beta
+更新内容:
+1、修复搜索闪退的bug
+
2021.05.15
风月读书v1.9.7-beta
更新内容:
1、优化书源结构
2、书源带cookie请求
3、第三方书源优化,修复bug
+4、书源支持登录
2021.05.14
风月读书v1.9.6-beta
diff --git a/app/src/main/java/xyz/fycz/myreader/application/App.java b/app/src/main/java/xyz/fycz/myreader/application/App.java
index 514b0ae..39ddf12 100644
--- a/app/src/main/java/xyz/fycz/myreader/application/App.java
+++ b/app/src/main/java/xyz/fycz/myreader/application/App.java
@@ -76,6 +76,7 @@ public class App extends Application {
super.onCreate();
application = this;
debug = isApkInDebug(this);
+ CrashHandler.register(this);
firstInit();
SSLSocketClient.trustAllHosts();//信任所有证书
RxJavaPlugins.setErrorHandler(Functions.emptyConsumer());
@@ -283,7 +284,7 @@ public class App extends Application {
App.getApplication().newThread(() -> {
try {
String url = "https://shimo.im/docs/cqkgjPRRydYYhQKt/read";
- if (getApplication().debug) {
+ if (debug) {
url = "https://shimo.im/docs/zfzpda7MUGskOC9v/read";
}
String html = OkHttpUtils.getHtml(url);
diff --git a/app/src/main/java/xyz/fycz/myreader/application/CrashHandler.java b/app/src/main/java/xyz/fycz/myreader/application/CrashHandler.java
new file mode 100644
index 0000000..277d1d7
--- /dev/null
+++ b/app/src/main/java/xyz/fycz/myreader/application/CrashHandler.java
@@ -0,0 +1,149 @@
+package xyz.fycz.myreader.application;
+
+import android.Manifest;
+import android.annotation.SuppressLint;
+import android.app.Application;
+import android.content.Context;
+import android.content.Intent;
+import android.content.SharedPreferences;
+import android.content.pm.PackageInfo;
+import android.content.pm.PackageManager;
+import android.content.res.Configuration;
+import android.content.res.Resources;
+import android.os.Build;
+import android.util.DisplayMetrics;
+import android.util.Log;
+
+import androidx.annotation.NonNull;
+
+import org.jetbrains.annotations.NotNull;
+
+import java.io.PrintWriter;
+import java.io.StringWriter;
+import java.net.InetAddress;
+import java.net.UnknownHostException;
+import java.text.DateFormat;
+import java.text.SimpleDateFormat;
+import java.util.Arrays;
+import java.util.Date;
+import java.util.List;
+import java.util.Locale;
+
+import xyz.fycz.myreader.common.APPCONST;
+import xyz.fycz.myreader.ui.activity.SplashActivity;
+import xyz.fycz.myreader.util.utils.FileUtils;
+
+/**
+ * @author fengyue
+ * @date 2021/5/16 11:01
+ */
+public final class CrashHandler implements Thread.UncaughtExceptionHandler {
+
+ private DateFormat formatter = new SimpleDateFormat("yyyy-MM-dd-HH-mm-ss");
+ /**
+ * 注册 Crash 监听
+ */
+ public static void register(Application application) {
+ Thread.setDefaultUncaughtExceptionHandler(new CrashHandler(application));
+ }
+
+ private final Application mApplication;
+ private final Thread.UncaughtExceptionHandler mNextHandler;
+
+ private CrashHandler(Application application) {
+ mApplication = application;
+ mNextHandler = Thread.getDefaultUncaughtExceptionHandler();
+ if (getClass().getName().equals(mNextHandler.getClass().getName())) {
+ // 请不要重复注册 Crash 监听
+ throw new IllegalStateException("are you ok?");
+ }
+ }
+
+ @SuppressLint("ApplySharedPref")
+ @Override
+ public void uncaughtException(@NonNull Thread thread, @NonNull Throwable throwable) {
+
+ saveCrashLog(throwable);
+
+ // 不去触发系统的崩溃处理(com.android.internal.os.RuntimeInit$KillApplicationHandler)
+ if (mNextHandler != null && !mNextHandler.getClass().getName().startsWith("com.android.internal.os")) {
+ mNextHandler.uncaughtException(thread, throwable);
+ }
+
+ // 杀死进程(这个事应该是系统干的,但是它会多弹出一个崩溃对话框,所以需要我们自己手动杀死进程)
+ android.os.Process.killProcess(android.os.Process.myPid());
+ System.exit(10);
+ }
+
+ private void saveCrashLog(Throwable throwable) {
+ StringWriter stringWriter = new StringWriter();
+ PrintWriter printWriter = new PrintWriter(stringWriter);
+ throwable.printStackTrace(printWriter);
+ Throwable cause = throwable.getCause();
+ if (cause != null) {
+ cause.printStackTrace(printWriter);
+ }
+ String mStackTrace = stringWriter.toString();
+
+ Resources res = mApplication.getResources();
+ DisplayMetrics displayMetrics = res.getDisplayMetrics();
+ int screenWidth = displayMetrics.widthPixels;
+ int screenHeight = displayMetrics.heightPixels;
+
+ String targetResource;
+ if (displayMetrics.densityDpi > 480) {
+ targetResource = "xxxhdpi";
+ } else if (displayMetrics.densityDpi > 320) {
+ targetResource = "xxhdpi";
+ } else if (displayMetrics.densityDpi > 240) {
+ targetResource = "xhdpi";
+ } else if (displayMetrics.densityDpi > 160) {
+ targetResource = "hdpi";
+ } else if (displayMetrics.densityDpi > 120) {
+ targetResource = "mdpi";
+ } else {
+ targetResource = "ldpi";
+ }
+
+ StringBuilder builder = new StringBuilder();
+ builder.append("设备品牌:\t").append(Build.BRAND)
+ .append("\n设备型号:\t").append(Build.MODEL)
+ .append("\n设备类型:\t").append(isTablet() ? "平板" : "手机");
+
+ builder.append("\n屏幕宽高:\t").append(screenWidth).append(" x ").append(screenHeight)
+ .append("\n屏幕密度:\t").append(displayMetrics.densityDpi)
+ .append("\n目标资源:\t").append(targetResource);
+
+ builder.append("\n安卓版本:\t").append(Build.VERSION.RELEASE)
+ .append("\nAPI 版本:\t").append(Build.VERSION.SDK_INT)
+ .append("\nCPU 架构:\t").append(Build.SUPPORTED_ABIS[0]);
+
+ builder.append("\n应用版本:\t").append(App.getStrVersionName())
+ .append("\n版本代码:\t").append(App.getVersionCode());
+
+ try {
+ SimpleDateFormat dateFormat = new SimpleDateFormat("MM-dd HH:mm", Locale.getDefault());
+ PackageInfo packageInfo = mApplication.getPackageManager().getPackageInfo(mApplication.getPackageName(), PackageManager.GET_PERMISSIONS);
+ builder.append("\n首次安装:\t").append(dateFormat.format(new Date(packageInfo.firstInstallTime)))
+ .append("\n最近安装:\t").append(dateFormat.format(new Date(packageInfo.lastUpdateTime)))
+ .append("\n崩溃时间:\t").append(dateFormat.format(new Date()));
+ } catch (PackageManager.NameNotFoundException ignored) {
+ }
+ String mPhoneInfo = builder.toString();
+
+ long timestamp = System.currentTimeMillis();
+ String time = formatter.format(new Date());
+ String fileName = "crash-" + time + "-" + timestamp + ".log";
+ String path = APPCONST.LOG_DIR + fileName;
+ FileUtils.writeText(mPhoneInfo + "\n\n" + mStackTrace, FileUtils.getFile(path));
+ }
+
+ /**
+ * 判断当前设备是否是平板
+ */
+ public boolean isTablet() {
+ return (mApplication.getResources().getConfiguration().screenLayout
+ & Configuration.SCREENLAYOUT_SIZE_MASK)
+ >= Configuration.SCREENLAYOUT_SIZE_LARGE;
+ }
+}
diff --git a/app/src/main/java/xyz/fycz/myreader/base/BaseActivity.java b/app/src/main/java/xyz/fycz/myreader/base/BaseActivity.java
index b97fddb..88876d0 100644
--- a/app/src/main/java/xyz/fycz/myreader/base/BaseActivity.java
+++ b/app/src/main/java/xyz/fycz/myreader/base/BaseActivity.java
@@ -23,6 +23,7 @@ import me.imid.swipebacklayout.lib.app.SwipeBackActivity;
import xyz.fycz.myreader.ActivityManage;
import xyz.fycz.myreader.R;
import xyz.fycz.myreader.application.App;
+import xyz.fycz.myreader.application.CrashHandler;
import xyz.fycz.myreader.application.SysManager;
import xyz.fycz.myreader.entity.Setting;
import xyz.fycz.myreader.util.StatusBarUtil;
diff --git a/app/src/main/java/xyz/fycz/myreader/base/BitIntentDataManager.java b/app/src/main/java/xyz/fycz/myreader/base/BitIntentDataManager.java
new file mode 100644
index 0000000..3926a28
--- /dev/null
+++ b/app/src/main/java/xyz/fycz/myreader/base/BitIntentDataManager.java
@@ -0,0 +1,50 @@
+package xyz.fycz.myreader.base;
+
+import android.content.Intent;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import xyz.fycz.myreader.common.APPCONST;
+
+public class BitIntentDataManager {
+ private static Map bigData;
+
+ private static BitIntentDataManager instance = null;
+
+ private BitIntentDataManager() {
+ bigData = new HashMap<>();
+ }
+
+ public static BitIntentDataManager getInstance() {
+ if (instance == null) {
+ synchronized (BitIntentDataManager.class) {
+ if (instance == null) {
+ instance = new BitIntentDataManager();
+ }
+ }
+ }
+ return instance;
+ }
+
+ public Object getData(String key) {
+ Object object = bigData.get(key);
+ bigData.remove(key);
+ return object;
+ }
+
+ public Object getData(Intent intent){
+ String dataKey = intent.getStringExtra(APPCONST.DATA_KEY);
+ return getData(dataKey);
+ }
+
+ public void putData(String key, Object data) {
+ bigData.put(key, data);
+ }
+
+ public void putData(Intent intent, Object data){
+ String dataKey = String.valueOf(System.currentTimeMillis());
+ intent.putExtra(APPCONST.DATA_KEY, dataKey);
+ putData(dataKey, data);
+ }
+}
diff --git a/app/src/main/java/xyz/fycz/myreader/common/APPCONST.java b/app/src/main/java/xyz/fycz/myreader/common/APPCONST.java
index 6e6b8c8..8392c3b 100644
--- a/app/src/main/java/xyz/fycz/myreader/common/APPCONST.java
+++ b/app/src/main/java/xyz/fycz/myreader/common/APPCONST.java
@@ -46,6 +46,7 @@ public class APPCONST {
public static final String JSON_PATH = "JsonPath";
public static final String THIRD_SOURCE = "ThirdSource";
+ public static final String DATA_KEY = "data_key";
public static final String BOOK = "book";
public static final String TITLE = "title";
public static final String FIND_CRAWLER = "findCrawler";
diff --git a/app/src/main/java/xyz/fycz/myreader/entity/sourceedit/EditEntityUtil.kt b/app/src/main/java/xyz/fycz/myreader/entity/sourceedit/EditEntityUtil.kt
index 33077a6..11b781a 100644
--- a/app/src/main/java/xyz/fycz/myreader/entity/sourceedit/EditEntityUtil.kt
+++ b/app/src/main/java/xyz/fycz/myreader/entity/sourceedit/EditEntityUtil.kt
@@ -52,6 +52,8 @@ object EditEntityUtil {
fun getInfoEntities(infoRule: InfoRule? = InfoRule()): List {
val infoEntities: ArrayList = ArrayList()
infoEntities.apply {
+ add(EditEntity("urlPattern", infoRule?.urlPattern, R.string.book_url_pattern, ""))
+ add(EditEntity("init", infoRule?.init, R.string.rule_book_info_init))
add(EditEntity("name", infoRule?.name, R.string.r_book_name))
add(EditEntity("author", infoRule?.author, R.string.r_author))
add(EditEntity("type", infoRule?.type, R.string.rule_book_type))
@@ -142,6 +144,8 @@ object EditEntityUtil {
val infoRule = InfoRule()
infoRuleEntities.forEach {
when (it.key) {
+ "urlPattern" -> infoRule.urlPattern = it.value
+ "init" -> infoRule.init = it.value
"name" -> infoRule.name = it.value
"author" -> infoRule.author = it.value
"type" -> infoRule.type = it.value
diff --git a/app/src/main/java/xyz/fycz/myreader/entity/thirdsource/ThirdSourceUtil.java b/app/src/main/java/xyz/fycz/myreader/entity/thirdsource/ThirdSourceUtil.java
index c7f2ad2..26ce800 100644
--- a/app/src/main/java/xyz/fycz/myreader/entity/thirdsource/ThirdSourceUtil.java
+++ b/app/src/main/java/xyz/fycz/myreader/entity/thirdsource/ThirdSourceUtil.java
@@ -37,11 +37,13 @@ public class ThirdSourceUtil {
searchRule.setDesc(bean.getRuleSearchIntroduce());
searchRule.setLastChapter(bean.getRuleSearchLastChapter());
searchRule.setImgUrl(bean.getRuleSearchCoverUrl());
- searchRule.setTocUrl(bean.getRuleSearchNoteUrl());
+ searchRule.setInfoUrl(bean.getRuleSearchNoteUrl());
searchRule.setRelatedWithInfo(true);
bookSource.setSearchRule(searchRule);
InfoRule infoRule = new InfoRule();
+ infoRule.setUrlPattern(bean.getRuleBookUrlPattern());
+ infoRule.setInit(bean.getRuleBookInfoInit());
infoRule.setName(bean.getRuleBookName());
infoRule.setAuthor(bean.getRuleBookAuthor());
infoRule.setType(bean.getRuleBookKind());
@@ -72,7 +74,7 @@ public class ThirdSourceUtil {
findRule.setDesc(bean.getRuleFindIntroduce());
findRule.setLastChapter(bean.getRuleFindLastChapter());
findRule.setImgUrl(bean.getRuleFindCoverUrl());
- findRule.setTocUrl(bean.getRuleFindNoteUrl());
+ findRule.setInfoUrl(bean.getRuleFindNoteUrl());
bookSource.setFindRule(findRule);
return bookSource;
}
diff --git a/app/src/main/java/xyz/fycz/myreader/greendao/entity/Book.java b/app/src/main/java/xyz/fycz/myreader/greendao/entity/Book.java
index 456f414..2d2a43d 100644
--- a/app/src/main/java/xyz/fycz/myreader/greendao/entity/Book.java
+++ b/app/src/main/java/xyz/fycz/myreader/greendao/entity/Book.java
@@ -11,6 +11,7 @@ import org.greenrobot.greendao.annotation.Entity;
import org.greenrobot.greendao.annotation.Generated;
import org.greenrobot.greendao.annotation.Id;
import org.greenrobot.greendao.annotation.Transient;
+
import xyz.fycz.myreader.greendao.service.BookService;
import xyz.fycz.myreader.util.SharedPreUtils;
import xyz.fycz.myreader.util.StringHelper;
@@ -76,17 +77,20 @@ public class Book implements Serializable {
@Transient
private Map variableMap;
+ @Transient
+ private Map catheMap;
+
@Generated(hash = 1839243756)
public Book() {
}
@Generated(hash = 1910282685)
public Book(String id, String name, String chapterUrl, String infoUrl, String imgUrl, String desc,
- String author, String type, String updateDate, String wordCount, String status,
- String newestChapterId, String newestChapterTitle, String historyChapterId, int histtoryChapterNum,
- int sortCode, int noReadNum, int chapterTotalNum, int lastReadPosition, String source,
- boolean isCloseUpdate, boolean isDownLoadAll, String groupId, int groupSort, String tag,
- Boolean replaceEnable, long lastReadTime, String variable) {
+ String author, String type, String updateDate, String wordCount, String status,
+ String newestChapterId, String newestChapterTitle, String historyChapterId, int histtoryChapterNum,
+ int sortCode, int noReadNum, int chapterTotalNum, int lastReadPosition, String source,
+ boolean isCloseUpdate, boolean isDownLoadAll, String groupId, int groupSort, String tag,
+ Boolean replaceEnable, long lastReadTime, String variable) {
this.id = id;
this.name = name;
this.chapterUrl = chapterUrl;
@@ -131,96 +135,127 @@ public class Book implements Serializable {
public String getId() {
return this.id;
}
+
public void setId(String id) {
this.id = id;
}
+
public String getName() {
return this.name;
}
+
public void setName(String name) {
this.name = name;
}
+
public String getChapterUrl() {
return this.chapterUrl;
}
+
public void setChapterUrl(String chapterUrl) {
this.chapterUrl = chapterUrl;
}
+
public String getImgUrl() {
return this.imgUrl;
}
+
public void setImgUrl(String imgUrl) {
this.imgUrl = imgUrl;
}
+
public String getDesc() {
return this.desc;
}
+
public void setDesc(String desc) {
this.desc = desc;
}
+
public String getAuthor() {
return this.author;
}
+
public void setAuthor(String author) {
this.author = BookService.formatAuthor(author);
}
+
public String getType() {
return this.type;
}
+
public void setType(String type) {
this.type = type;
}
+
public String getUpdateDate() {
return this.updateDate;
}
+
public void setUpdateDate(String updateDate) {
this.updateDate = updateDate;
}
+
public String getNewestChapterId() {
return this.newestChapterId;
}
+
public void setNewestChapterId(String newestChapterId) {
this.newestChapterId = newestChapterId;
}
+
public String getNewestChapterTitle() {
return this.newestChapterTitle;
}
+
public void setNewestChapterTitle(String newestChapterTitle) {
this.newestChapterTitle = newestChapterTitle;
}
+
public String getHistoryChapterId() {
return this.historyChapterId;
}
+
public void setHistoryChapterId(String historyChapterId) {
this.historyChapterId = historyChapterId;
}
+
public int getHisttoryChapterNum() {
return this.histtoryChapterNum;
}
+
public void setHisttoryChapterNum(int histtoryChapterNum) {
this.histtoryChapterNum = histtoryChapterNum;
}
+
public int getSortCode() {
return this.sortCode;
}
+
public void setSortCode(int sortCode) {
this.sortCode = sortCode;
}
+
public int getNoReadNum() {
return this.noReadNum;
}
+
public void setNoReadNum(int noReadNum) {
this.noReadNum = noReadNum;
}
+
public int getChapterTotalNum() {
return this.chapterTotalNum;
}
+
public void setChapterTotalNum(int chapterTotalNum) {
this.chapterTotalNum = chapterTotalNum;
}
+
public int getLastReadPosition() {
return this.lastReadPosition;
}
+
public void setLastReadPosition(int lastReadPosition) {
this.lastReadPosition = lastReadPosition;
}
@@ -249,6 +284,7 @@ public class Book implements Serializable {
public void setIsDownLoadAll(boolean isDownLoadAll) {
this.isDownLoadAll = isDownLoadAll;
}
+
public String getGroupId() {
return this.groupId;
}
@@ -283,9 +319,6 @@ public class Book implements Serializable {
}
public String getInfoUrl() {
- if (StringHelper.isEmpty(infoUrl)){
- return chapterUrl;
- }
return this.infoUrl;
}
@@ -342,6 +375,7 @@ public class Book implements Serializable {
public void setStatus(String status) {
this.status = status;
}
+
public void putVariable(String key, String value) {
if (variableMap == null) {
variableMap = new HashMap<>();
@@ -366,4 +400,18 @@ public class Book implements Serializable {
public void setVariable(String variable) {
this.variable = variable;
}
+
+ public void putCathe(String key, String value) {
+ if (catheMap == null) {
+ catheMap = new HashMap<>();
+ }
+ catheMap.put(key, value);
+ }
+
+ public String getCathe(String key){
+ if (catheMap == null){
+ return "";
+ }
+ return catheMap.get(key);
+ }
}
diff --git a/app/src/main/java/xyz/fycz/myreader/greendao/entity/rule/FindRule.java b/app/src/main/java/xyz/fycz/myreader/greendao/entity/rule/FindRule.java
index a9b21be..6e33326 100644
--- a/app/src/main/java/xyz/fycz/myreader/greendao/entity/rule/FindRule.java
+++ b/app/src/main/java/xyz/fycz/myreader/greendao/entity/rule/FindRule.java
@@ -26,6 +26,7 @@ public class FindRule implements Parcelable {
private String updateTime;
private String imgUrl;
private String tocUrl;
+ private String infoUrl;
public FindRule() {
}
@@ -43,6 +44,7 @@ public class FindRule implements Parcelable {
updateTime = in.readString();
imgUrl = in.readString();
tocUrl = in.readString();
+ infoUrl = in.readString();
}
@Override
@@ -59,6 +61,7 @@ public class FindRule implements Parcelable {
dest.writeString(updateTime);
dest.writeString(imgUrl);
dest.writeString(tocUrl);
+ dest.writeString(infoUrl);
}
@Override
@@ -174,6 +177,14 @@ public class FindRule implements Parcelable {
this.tocUrl = tocUrl;
}
+ public String getInfoUrl() {
+ return infoUrl;
+ }
+
+ public void setInfoUrl(String infoUrl) {
+ this.infoUrl = infoUrl;
+ }
+
@Override
public boolean equals(Object o) {
if (this == o) return true;
@@ -191,7 +202,8 @@ public class FindRule implements Parcelable {
stringEquals(lastChapter, findRule.lastChapter) &&
stringEquals(updateTime, findRule.updateTime) &&
stringEquals(imgUrl, findRule.imgUrl) &&
- stringEquals(tocUrl, findRule.tocUrl);
+ stringEquals(tocUrl, findRule.tocUrl) &&
+ stringEquals(infoUrl, findRule.infoUrl);
}
}
diff --git a/app/src/main/java/xyz/fycz/myreader/greendao/entity/rule/InfoRule.java b/app/src/main/java/xyz/fycz/myreader/greendao/entity/rule/InfoRule.java
index 06b7612..b8029c3 100644
--- a/app/src/main/java/xyz/fycz/myreader/greendao/entity/rule/InfoRule.java
+++ b/app/src/main/java/xyz/fycz/myreader/greendao/entity/rule/InfoRule.java
@@ -16,6 +16,8 @@ import static xyz.fycz.myreader.util.utils.StringUtils.stringEquals;
* @date 2021/2/8 17:53
*/
public class InfoRule implements Parcelable {
+ private String urlPattern;
+ private String init;
private String name;
private String author;
private String type;
@@ -31,6 +33,8 @@ public class InfoRule implements Parcelable {
}
protected InfoRule(Parcel in) {
+ urlPattern = in.readString();
+ init = in.readString();
name = in.readString();
author = in.readString();
type = in.readString();
@@ -45,6 +49,8 @@ public class InfoRule implements Parcelable {
@Override
public void writeToParcel(Parcel dest, int flags) {
+ dest.writeString(urlPattern);
+ dest.writeString(init);
dest.writeString(name);
dest.writeString(author);
dest.writeString(type);
@@ -80,7 +86,9 @@ public class InfoRule implements Parcelable {
if (o == null) o = new InfoRule();
if (getClass() != o.getClass()) return false;
InfoRule infoRule = (InfoRule) o;
- return stringEquals(name, infoRule.name) &&
+ return stringEquals(urlPattern, infoRule.urlPattern) &&
+ stringEquals(init, infoRule.init) &&
+ stringEquals(name, infoRule.name) &&
stringEquals(author, infoRule.author) &&
stringEquals(type, infoRule.type) &&
stringEquals(desc, infoRule.desc) &&
@@ -92,6 +100,21 @@ public class InfoRule implements Parcelable {
stringEquals(tocUrl, infoRule.tocUrl);
}
+ public String getUrlPattern() {
+ return urlPattern;
+ }
+
+ public void setUrlPattern(String urlPattern) {
+ this.urlPattern = urlPattern;
+ }
+
+ public String getInit() {
+ return init;
+ }
+
+ public void setInit(String init) {
+ this.init = init;
+ }
public String getName() {
return name;
diff --git a/app/src/main/java/xyz/fycz/myreader/model/sourceAnalyzer/BookSourceManager.java b/app/src/main/java/xyz/fycz/myreader/model/sourceAnalyzer/BookSourceManager.java
index 9dfcc8e..9c80f5e 100644
--- a/app/src/main/java/xyz/fycz/myreader/model/sourceAnalyzer/BookSourceManager.java
+++ b/app/src/main/java/xyz/fycz/myreader/model/sourceAnalyzer/BookSourceManager.java
@@ -81,11 +81,9 @@ public class BookSourceManager {
* @return
*/
public static BookSource getBookSourceByStr(String str) {
- if (NetworkUtils.isUrl(str)) {
- return getBookSourceByUrl(str);
- } else {
- return getBookSourceByEName(str);
- }
+ BookSource source = getBookSourceByEName(str);
+ if (source == null) source = getBookSourceByUrl(str);
+ return source;
}
/**
@@ -94,7 +92,7 @@ public class BookSourceManager {
* @param url
* @return
*/
- public static BookSource getBookSourceByUrl(String url) {
+ private static BookSource getBookSourceByUrl(String url) {
if (url == null) return getDefaultSource();
BookSource source = DbManager.getDaoSession().getBookSourceDao().load(url);
if (source == null) return getDefaultSource();
@@ -107,15 +105,13 @@ public class BookSourceManager {
* @param ename
* @return
*/
- @Nullable
- public static BookSource getBookSourceByEName(String ename) {
- if (ename == null) return getDefaultSource();
+ private static BookSource getBookSourceByEName(String ename) {
+ if (ename == null) return null;
if ("local".equals(ename)) return getLocalSource();
BookSource source = DbManager.getDaoSession().getBookSourceDao().
queryBuilder()
.where(BookSourceDao.Properties.SourceEName.eq(ename))
.unique();
- if (source == null) return getDefaultSource();
return source;
}
diff --git a/app/src/main/java/xyz/fycz/myreader/model/third2/analyzeRule/AnalyzeByRegex.java b/app/src/main/java/xyz/fycz/myreader/model/third2/analyzeRule/AnalyzeByRegex.java
index 5484626..922d9fc 100644
--- a/app/src/main/java/xyz/fycz/myreader/model/third2/analyzeRule/AnalyzeByRegex.java
+++ b/app/src/main/java/xyz/fycz/myreader/model/third2/analyzeRule/AnalyzeByRegex.java
@@ -2,6 +2,7 @@ package xyz.fycz.myreader.model.third2.analyzeRule;
import android.os.Build;
import android.text.TextUtils;
+import android.util.Log;
import java.util.ArrayList;
import java.util.HashMap;
@@ -21,11 +22,16 @@ public class AnalyzeByRegex {
// 纯java模式正则表达式获取书籍详情信息
public static void getInfoOfRegex(String res, String[] regs, int index,
- Book book, AnalyzeRule analyzer, BookSource source, String baseUrl, String tag) throws Exception {
+ Book book, AnalyzeRule analyzer, BookSource source, String tag) throws Exception {
Matcher resM = Pattern.compile(regs[index]).matcher(res);
+ String baseUrl = book.getInfoUrl();
// 判断规则是否有效,当搜索列表规则无效时跳过详情页处理
if (!resM.find()) {
+ Log.d(tag, "└详情预处理失败,跳过详情页解析");
+ Log.d(tag, "┌获取目录网址");
book.setChapterUrl(baseUrl);
+ book.putCathe("ChapterListHtml", res);
+ Log.d(tag, "└" + baseUrl);
return;
}
// 判断索引的规则是最后一个规则
@@ -78,18 +84,37 @@ public class AnalyzeByRegex {
book.setName(StringUtils.formatHtml(ruleVal.get("BookName")));
if (!isEmpty(ruleVal.get("BookAuthor")))
book.setAuthor(StringUtils.formatHtml(ruleVal.get("BookAuthor")));
- if (!isEmpty(ruleVal.get("LastChapter"))) book.setNewestChapterTitle(ruleVal.get("LastChapter"));
+ if (!isEmpty(ruleVal.get("LastChapter")))
+ book.setNewestChapterTitle(ruleVal.get("LastChapter"));
if (!isEmpty(ruleVal.get("Introduce")))
book.setDesc(StringUtils.formatHtml(ruleVal.get("Introduce")));
if (!isEmpty(ruleVal.get("CoverUrl"))) book.setImgUrl(ruleVal.get("CoverUrl"));
- if (!isEmpty(ruleVal.get("ChapterUrl"))) book.setChapterUrl(NetworkUtils.getAbsoluteURL(baseUrl, ruleVal.get("ChapterUrl")));
+ if (!isEmpty(ruleVal.get("ChapterUrl")))
+ book.setChapterUrl(NetworkUtils.getAbsoluteURL(baseUrl, ruleVal.get("ChapterUrl")));
else book.setChapterUrl(baseUrl);
+ //如果目录页和详情页相同,暂存页面内容供获取目录用
+ if (book.getChapterUrl().equals(baseUrl)) book.putCathe("ChapterListHtml", res);
+ // 输出调试信息
+ Log.d(tag, "└详情预处理完成");
+ Log.d(tag, "┌获取书籍名称");
+ Log.d(tag, "└" + book.getName());
+ Log.d(tag, "┌获取作者名称");
+ Log.d(tag, "└" + book.getAuthor());
+ Log.d(tag, "┌获取最新章节");
+ Log.d(tag, "└" + book.getNewestChapterTitle());
+ Log.d(tag, "┌获取简介内容");
+ Log.d(tag, "└" + book.getDesc());
+ Log.d(tag, "┌获取封面网址");
+ Log.d(tag, "└" + book.getImgUrl());
+ Log.d(tag, "┌获取目录网址");
+ Log.d(tag, "└" + book.getChapterUrl());
+ Log.d(tag, "-详情页解析完成");
} else {
StringBuilder result = new StringBuilder();
do {
result.append(resM.group());
} while (resM.find());
- getInfoOfRegex(result.toString(), regs, ++index, book, analyzer, source, baseUrl, tag);
+ getInfoOfRegex(result.toString(), regs, ++index, book, analyzer, source, tag);
}
}
diff --git a/app/src/main/java/xyz/fycz/myreader/model/third2/content/BookInfo.java b/app/src/main/java/xyz/fycz/myreader/model/third2/content/BookInfo.java
index 99d8437..a01a2c7 100644
--- a/app/src/main/java/xyz/fycz/myreader/model/third2/content/BookInfo.java
+++ b/app/src/main/java/xyz/fycz/myreader/model/third2/content/BookInfo.java
@@ -8,6 +8,7 @@ import io.reactivex.Observable;
import xyz.fycz.myreader.greendao.entity.Book;
import xyz.fycz.myreader.greendao.entity.rule.BookSource;
import xyz.fycz.myreader.greendao.entity.rule.InfoRule;
+import xyz.fycz.myreader.model.third2.analyzeRule.AnalyzeByRegex;
import xyz.fycz.myreader.model.third2.analyzeRule.AnalyzeRule;
import xyz.fycz.myreader.util.utils.StringUtils;
@@ -27,7 +28,7 @@ public class BookInfo {
public Observable analyzeBookInfo(String s, final Book book) {
return Observable.create(e -> {
String baseUrl = book.getInfoUrl();
- book.setInfoUrl(baseUrl);
+
InfoRule infoRule = source.getInfoRule();
if (TextUtils.isEmpty(s)) {
e.onError(new Throwable("书籍信息获取失败" + baseUrl));
@@ -42,43 +43,67 @@ public class BookInfo {
AnalyzeRule analyzer = new AnalyzeRule(book);
analyzer.setContent(s, baseUrl);
- Log.d(tag, "┌获取书名");
- String bookName = StringUtils.formatHtml(analyzer.getString(infoRule.getName()));
- if (!isEmpty(bookName)) book.setName(bookName);
- Log.d(tag, "└" + bookName);
-
- Log.d(tag, "┌获取作者");
- String bookAuthor = StringUtils.formatHtml(analyzer.getString(infoRule.getAuthor()));
- if (!isEmpty(bookAuthor)) book.setAuthor(bookAuthor);
- Log.d(tag, "└" + bookAuthor);
-
- Log.d(tag, "┌获取分类");
- String bookKind = analyzer.getString(infoRule.getType());
- Log.d(tag, "└" + bookKind);
-
- Log.d(tag, "┌获取最新章节");
- String bookLastChapter = analyzer.getString(infoRule.getLastChapter());
- if (!isEmpty(bookLastChapter)) book.setNewestChapterTitle(bookLastChapter);
- Log.d(tag, "└" + bookLastChapter);
-
- Log.d(tag, "┌获取简介");
- String bookIntroduce = analyzer.getString(infoRule.getDesc());
- if (!isEmpty(bookIntroduce)) book.setDesc(bookIntroduce);
- Log.d(tag, "└" + bookIntroduce);
-
- Log.d(tag, "┌获取封面");
- String bookCoverUrl = analyzer.getString(infoRule.getImgUrl(), true);
- if (!isEmpty(bookCoverUrl)) book.setImgUrl(bookCoverUrl);
- Log.d(tag, "└" + bookCoverUrl);
-
- Log.d(tag, "┌获取目录网址");
- String bookCatalogUrl = analyzer.getString(infoRule.getTocUrl(), true);
- if (isEmpty(bookCatalogUrl)) bookCatalogUrl = baseUrl;
- book.setChapterUrl(bookCatalogUrl);
- //如果目录页和详情页相同,暂存页面内容供获取目录用
- //if (bookCatalogUrl.equals(baseUrl)) bookInfoBean.setChapterListHtml(s);
- Log.d(tag, "└" + book.getChapterUrl());
- Log.d(tag, "-详情页解析完成");
+ // 获取详情页预处理规则
+ String ruleInfoInit = infoRule.getInit();
+ boolean isRegex = false;
+ if (!isEmpty(ruleInfoInit)) {
+ // 仅使用java正则表达式提取书籍详情
+ if (ruleInfoInit.startsWith(":")) {
+ isRegex = true;
+ ruleInfoInit = ruleInfoInit.substring(1);
+ Log.d(tag, "┌详情信息预处理");
+ AnalyzeByRegex.getInfoOfRegex(s, ruleInfoInit.split("&&"), 0, book, analyzer, source, tag);
+ } else {
+ Object object = analyzer.getElement(ruleInfoInit);
+ if (object != null) {
+ analyzer.setContent(object);
+ }
+ }
+ }
+ if (!isRegex) {
+ Log.d(tag, "┌详情信息预处理");
+ Object object = analyzer.getElement(ruleInfoInit);
+ if (object != null) analyzer.setContent(object);
+ Log.d(tag, "└详情预处理完成");
+
+ Log.d(tag, "┌获取书名");
+ String bookName = StringUtils.formatHtml(analyzer.getString(infoRule.getName()));
+ if (!isEmpty(bookName)) book.setName(bookName);
+ Log.d(tag, "└" + bookName);
+
+ Log.d(tag, "┌获取作者");
+ String bookAuthor = StringUtils.formatHtml(analyzer.getString(infoRule.getAuthor()));
+ if (!isEmpty(bookAuthor)) book.setAuthor(bookAuthor);
+ Log.d(tag, "└" + bookAuthor);
+
+ Log.d(tag, "┌获取分类");
+ String bookKind = analyzer.getString(infoRule.getType());
+ Log.d(tag, "└" + bookKind);
+
+ Log.d(tag, "┌获取最新章节");
+ String bookLastChapter = analyzer.getString(infoRule.getLastChapter());
+ if (!isEmpty(bookLastChapter)) book.setNewestChapterTitle(bookLastChapter);
+ Log.d(tag, "└" + bookLastChapter);
+
+ Log.d(tag, "┌获取简介");
+ String bookIntroduce = analyzer.getString(infoRule.getDesc());
+ if (!isEmpty(bookIntroduce)) book.setDesc(bookIntroduce);
+ Log.d(tag, "└" + bookIntroduce);
+
+ Log.d(tag, "┌获取封面");
+ String bookCoverUrl = analyzer.getString(infoRule.getImgUrl(), true);
+ if (!isEmpty(bookCoverUrl)) book.setImgUrl(bookCoverUrl);
+ Log.d(tag, "└" + bookCoverUrl);
+
+ Log.d(tag, "┌获取目录网址");
+ String bookCatalogUrl = analyzer.getString(infoRule.getTocUrl(), true);
+ if (isEmpty(bookCatalogUrl)) bookCatalogUrl = baseUrl;
+ book.setChapterUrl(bookCatalogUrl);
+ //如果目录页和详情页相同,暂存页面内容供获取目录用
+ if (bookCatalogUrl.equals(baseUrl)) book.putCathe("ChapterListHtml", s);
+ Log.d(tag, "└" + book.getChapterUrl());
+ Log.d(tag, "-详情页解析完成");
+ }
e.onNext(book);
e.onComplete();
});
diff --git a/app/src/main/java/xyz/fycz/myreader/model/third2/content/BookList.java b/app/src/main/java/xyz/fycz/myreader/model/third2/content/BookList.java
index fd9286d..dff9157 100644
--- a/app/src/main/java/xyz/fycz/myreader/model/third2/content/BookList.java
+++ b/app/src/main/java/xyz/fycz/myreader/model/third2/content/BookList.java
@@ -65,67 +65,76 @@ public class BookList {
AnalyzeRule analyzer = new AnalyzeRule(null);
analyzer.setContent(body, baseUrl);
//如果符合详情页url规则
-
- initRule();
- List