mirror of
https://github.com/qaiu/netdisk-fast-download.git
synced 2025-12-16 04:13:03 +00:00
0
This commit is contained in:
@@ -4,16 +4,16 @@ import cn.qaiu.lz.common.parser.impl.*;
|
||||
import io.vertx.core.Future;
|
||||
|
||||
public interface IPanTool {
|
||||
Future<String> parse(String data, String code);
|
||||
Future<String> parse();
|
||||
|
||||
static IPanTool typeMatching(String type) {
|
||||
static IPanTool typeMatching(String type, String key, String pwd) {
|
||||
return switch (type) {
|
||||
case "lz" -> new LzTool();
|
||||
case "cow" -> new CowTool();
|
||||
case "ec" -> new EcTool();
|
||||
case "fc" -> new FcTool();
|
||||
case "uc" -> new UcTool();
|
||||
case "ye" -> new YeTool();
|
||||
case "ye" -> new YeTool(key, pwd);
|
||||
case "fj" -> new FjTool();
|
||||
default -> {
|
||||
throw new IllegalArgumentException("未知分享类型");
|
||||
@@ -21,7 +21,7 @@ public interface IPanTool {
|
||||
};
|
||||
}
|
||||
|
||||
static IPanTool shareURLPrefixMatching(String url) {
|
||||
static IPanTool shareURLPrefixMatching(String url, String pwd) {
|
||||
|
||||
if (url.startsWith(CowTool.SHARE_URL_PREFIX)) {
|
||||
return new CowTool();
|
||||
@@ -32,7 +32,7 @@ public interface IPanTool {
|
||||
} else if (url.startsWith(UcTool.SHARE_URL_PREFIX)) {
|
||||
return new UcTool();
|
||||
} else if (url.startsWith(YeTool.SHARE_URL_PREFIX)) {
|
||||
return new YeTool();
|
||||
return new YeTool(url, pwd);
|
||||
} else if (url.startsWith(FjTool.SHARE_URL_PREFIX)) {
|
||||
return new FjTool();
|
||||
} else if (url.contains("lanzou")) {
|
||||
|
||||
@@ -0,0 +1,37 @@
|
||||
package cn.qaiu.lz.common.parser;
|
||||
|
||||
import io.vertx.core.Handler;
|
||||
import io.vertx.core.Promise;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public abstract class PanBase {
|
||||
|
||||
protected Promise<String> promise = Promise.promise();
|
||||
protected Logger log = LoggerFactory.getLogger(this.getClass());
|
||||
|
||||
protected String key;
|
||||
protected String pwd;
|
||||
|
||||
protected PanBase(String key, String pwd) {
|
||||
this.key = key;
|
||||
this.pwd = pwd;
|
||||
}
|
||||
|
||||
protected void fail(Throwable t, String errorMsg, Object... args) {
|
||||
String s = String.format(errorMsg.replaceAll("\\{}", "%s"), args);
|
||||
log.error("解析异常: " + s, t.fillInStackTrace());
|
||||
promise.fail(this.getClass().getSimpleName() + ": 解析异常: " + s + " -> " + t);
|
||||
}
|
||||
|
||||
protected void fail(String errorMsg, Object... args) {
|
||||
String s = String.format(errorMsg.replaceAll("\\{}", "%s"), args);
|
||||
log.error("解析异常: " + s);
|
||||
promise.fail(this.getClass().getSimpleName() + " - 解析异常: " + s);
|
||||
}
|
||||
|
||||
protected Handler<Throwable> handleFail(String errorMsg) {
|
||||
return t -> fail(this.getClass().getSimpleName() + " - 请求异常 {}: -> {}", errorMsg, t.fillInStackTrace());
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,22 +1,18 @@
|
||||
package cn.qaiu.lz.common.parser.impl;
|
||||
|
||||
import cn.qaiu.lz.common.parser.IPanTool;
|
||||
import cn.qaiu.lz.common.parser.PanBase;
|
||||
import cn.qaiu.lz.common.util.CommonUtils;
|
||||
import cn.qaiu.lz.common.util.JsExecUtils;
|
||||
import cn.qaiu.lz.common.util.PanExceptionUtils;
|
||||
import cn.qaiu.vx.core.util.VertxHolder;
|
||||
import io.vertx.core.Future;
|
||||
import io.vertx.core.Promise;
|
||||
import io.vertx.core.json.JsonObject;
|
||||
import io.vertx.ext.web.client.WebClient;
|
||||
import io.vertx.uritemplate.UriTemplate;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.commons.lang3.ArrayUtils;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.openjdk.nashorn.api.scripting.ScriptObjectMirror;
|
||||
|
||||
import javax.script.ScriptException;
|
||||
import java.io.IOException;
|
||||
import java.net.MalformedURLException;
|
||||
import java.util.Base64;
|
||||
import java.util.Map;
|
||||
@@ -26,8 +22,8 @@ import java.util.regex.Pattern;
|
||||
/**
|
||||
* 123网盘
|
||||
*/
|
||||
@Slf4j
|
||||
public class YeTool implements IPanTool {
|
||||
public class YeTool extends PanBase implements IPanTool {
|
||||
|
||||
public static final String SHARE_URL_PREFIX = "https://www.123pan.com/s/";
|
||||
public static final String FIRST_REQUEST_URL = SHARE_URL_PREFIX + "{key}.html";
|
||||
/*
|
||||
@@ -45,10 +41,13 @@ public class YeTool implements IPanTool {
|
||||
"&shareKey={shareKey}&SharePwd={pwd}&ParentFileId=0&Page=1&event=homeListFile&operateType=1";
|
||||
private static final String DOWNLOAD_API_URL = "https://www.123pan.com/b/api/share/download/info?{authK}={authV}";
|
||||
|
||||
public Future<String> parse(String data, String code) {
|
||||
public YeTool(String key, String pwd) {
|
||||
super(key, pwd);
|
||||
}
|
||||
|
||||
String dataKey = CommonUtils.adaptShortPaths(SHARE_URL_PREFIX, data);
|
||||
Promise<String> promise = Promise.promise();
|
||||
public Future<String> parse() {
|
||||
|
||||
String dataKey = CommonUtils.adaptShortPaths(SHARE_URL_PREFIX, key);
|
||||
WebClient client = WebClient.create(VertxHolder.getVertxInstance());
|
||||
|
||||
client.getAbs(UriTemplate.of(FIRST_REQUEST_URL)).setTemplateParam("key", dataKey).send().onSuccess(res -> {
|
||||
@@ -58,7 +57,7 @@ public class YeTool implements IPanTool {
|
||||
Matcher matcher = compile.matcher(html);
|
||||
|
||||
if (!matcher.find()) {
|
||||
promise.fail(html + "\n Ye: " + dataKey + " 正则匹配失败");
|
||||
fail(html + "\n Ye: " + dataKey + " 正则匹配失败");
|
||||
return;
|
||||
}
|
||||
String fileInfoString = matcher.group(1);
|
||||
@@ -67,45 +66,45 @@ public class YeTool implements IPanTool {
|
||||
JsonObject resListJson = fileInfoJson.getJsonObject("reslist");
|
||||
|
||||
if (resJson == null || resJson.getInteger("code") != 0) {
|
||||
promise.fail(dataKey + " 解析到异常JSON: " + resJson);
|
||||
fail(dataKey + " 解析到异常JSON: " + resJson);
|
||||
return;
|
||||
}
|
||||
String shareKey = resJson.getJsonObject("data").getString("ShareKey");
|
||||
if (resListJson == null || resListJson.getInteger("code") != 0) {
|
||||
// 加密分享
|
||||
if (StringUtils.isNotEmpty(code)) {
|
||||
if (StringUtils.isNotEmpty(pwd)) {
|
||||
client.getAbs(UriTemplate.of(GET_FILE_INFO_URL))
|
||||
.setTemplateParam("shareKey", shareKey)
|
||||
.setTemplateParam("pwd", code)
|
||||
.setTemplateParam("pwd", pwd)
|
||||
// .setTemplateParam("authKey", AESUtils.getAuthKey("/b/api/share/get"))
|
||||
.putHeader("Platform", "web")
|
||||
.putHeader("App-Version", "3")
|
||||
.send().onSuccess(res2 -> {
|
||||
JsonObject infoJson = res2.bodyAsJsonObject();
|
||||
if (infoJson.getInteger("code") != 0) {
|
||||
promise.fail("Ye: " + dataKey + " 状态码异常" + infoJson);
|
||||
fail("{} 状态码异常 {}", dataKey, infoJson);
|
||||
return;
|
||||
}
|
||||
JsonObject getFileInfoJson =
|
||||
infoJson.getJsonObject("data").getJsonArray("InfoList").getJsonObject(0);
|
||||
getFileInfoJson.put("ShareKey", shareKey);
|
||||
getDownUrl(promise, client, getFileInfoJson);
|
||||
}).onFailure(t -> promise.fail(PanExceptionUtils.fillRunTimeException("Ye", dataKey, t)));
|
||||
getDownUrl(client, getFileInfoJson);
|
||||
}).onFailure(this.handleFail("获取文件信息失败"));
|
||||
} else {
|
||||
promise.fail(dataKey + " 该分享需要密码");
|
||||
fail(dataKey + " 该分享需要密码");
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
JsonObject reqBodyJson = resListJson.getJsonObject("data").getJsonArray("InfoList").getJsonObject(0);
|
||||
reqBodyJson.put("ShareKey", shareKey);
|
||||
getDownUrl(promise, client, reqBodyJson);
|
||||
}).onFailure(t -> promise.fail(PanExceptionUtils.fillRunTimeException("Ye", dataKey, t)));
|
||||
getDownUrl(client, reqBodyJson);
|
||||
}).onFailure(this.handleFail(""));
|
||||
|
||||
return promise.future();
|
||||
}
|
||||
|
||||
private static void getDownUrl(Promise<String> promise, WebClient client, JsonObject reqBodyJson) {
|
||||
private void getDownUrl(WebClient client, JsonObject reqBodyJson) {
|
||||
log.info(reqBodyJson.encodePrettily());
|
||||
JsonObject jsonObject = new JsonObject();
|
||||
// {"ShareKey":"iaKtVv-6OECd","FileID":2193732,"S3keyFlag":"1811834632-0","Size":4203111,
|
||||
@@ -120,12 +119,8 @@ public class YeTool implements IPanTool {
|
||||
ScriptObjectMirror getSign;
|
||||
try {
|
||||
getSign = JsExecUtils.executeJs("getSign", "/b/api/share/download/info");
|
||||
} catch (ScriptException | IOException | NoSuchMethodException e) {
|
||||
promise.fail(e);
|
||||
return;
|
||||
}
|
||||
if (getSign == null) {
|
||||
promise.fail(ArrayUtils.toString(getSign));
|
||||
} catch (Exception e) {
|
||||
fail(e, "JS函数执行异常");
|
||||
return;
|
||||
}
|
||||
log.info("ye getSign: {}={}", getSign.get("0").toString(), getSign.get("1").toString());
|
||||
@@ -140,11 +135,11 @@ public class YeTool implements IPanTool {
|
||||
|
||||
try {
|
||||
if (downURLJson.getInteger("code") != 0) {
|
||||
promise.fail("Ye: downURLJson返回值异常->" + downURLJson);
|
||||
fail("Ye: downURLJson返回值异常->" + downURLJson);
|
||||
return;
|
||||
}
|
||||
} catch (Exception ignored) {
|
||||
promise.fail("Ye: downURLJson格式异常->" + downURLJson);
|
||||
fail("Ye: downURLJson格式异常->" + downURLJson);
|
||||
return;
|
||||
}
|
||||
String downURL = downURLJson.getJsonObject("data").getString("DownloadURL");
|
||||
@@ -159,23 +154,21 @@ public class YeTool implements IPanTool {
|
||||
JsonObject res3Json = res3.bodyAsJsonObject();
|
||||
try {
|
||||
if (res3Json.getInteger("code") != 0) {
|
||||
promise.fail("Ye: downUrl2返回值异常->" + res3Json);
|
||||
fail("Ye: downUrl2返回值异常->" + res3Json);
|
||||
return;
|
||||
}
|
||||
} catch (Exception ignored) {
|
||||
promise.fail("Ye: downUrl2格式异常->" + downURLJson);
|
||||
fail("Ye: downUrl2格式异常->" + downURLJson);
|
||||
return;
|
||||
}
|
||||
|
||||
promise.complete(res3Json.getJsonObject("data").getString("redirect_url"));
|
||||
|
||||
}).onFailure(t -> promise.fail(PanExceptionUtils.fillRunTimeException("Ye",
|
||||
reqBodyJson.encodePrettily(), t)));
|
||||
}).onFailure(this.handleFail("获取直链失败"));
|
||||
|
||||
} catch (MalformedURLException e) {
|
||||
promise.fail("urlParams解析异常" + e.getMessage());
|
||||
fail("urlParams解析异常" + e.getMessage());
|
||||
}
|
||||
}).onFailure(t -> promise.fail(PanExceptionUtils.fillRunTimeException("Ye",
|
||||
reqBodyJson.encodePrettily(), t)));
|
||||
}).onFailure(this::handleFail);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,6 +6,7 @@ import javax.script.Invocable;
|
||||
import javax.script.ScriptEngine;
|
||||
import javax.script.ScriptEngineManager;
|
||||
import javax.script.ScriptException;
|
||||
import java.io.FileNotFoundException;
|
||||
import java.io.FileReader;
|
||||
import java.io.IOException;
|
||||
import java.net.URL;
|
||||
@@ -17,26 +18,32 @@ import java.net.URL;
|
||||
*/
|
||||
public class JsExecUtils {
|
||||
private static final String JS_PATH = "/js/ye123.js";
|
||||
private static Invocable inv;
|
||||
|
||||
/**
|
||||
* 调用js文件
|
||||
*/
|
||||
public static ScriptObjectMirror executeJs(String functionName, Object... args) throws ScriptException,
|
||||
IOException, NoSuchMethodException {
|
||||
// 初始化脚本引擎
|
||||
static {
|
||||
ScriptEngineManager engineManager = new ScriptEngineManager();
|
||||
ScriptEngine engine = engineManager.getEngineByName("JavaScript"); // 得到脚本引擎
|
||||
//获取文件所在的相对路径
|
||||
URL resource = JsExecUtils.class.getResource("/");
|
||||
if (resource == null) {
|
||||
throw new ScriptException("js resource path is null");
|
||||
throw new RuntimeException("js resource path is null");
|
||||
}
|
||||
String path = resource.getPath();
|
||||
String reader = path + JS_PATH;
|
||||
FileReader fReader = new FileReader(reader);
|
||||
engine.eval(fReader);
|
||||
fReader.close();
|
||||
try (FileReader fReader = new FileReader(reader)){
|
||||
engine.eval(fReader);
|
||||
fReader.close();
|
||||
inv = (Invocable) engine;
|
||||
} catch (IOException | ScriptException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
|
||||
Invocable inv = (Invocable) engine;
|
||||
/**
|
||||
* 调用js文件
|
||||
*/
|
||||
public static ScriptObjectMirror executeJs(String functionName, Object... args) throws ScriptException, NoSuchMethodException {
|
||||
//调用js中的方法
|
||||
return (ScriptObjectMirror) inv.invokeFunction(functionName, args);
|
||||
}
|
||||
|
||||
@@ -91,7 +91,7 @@ GET http://127.0.0.1:6400/ye/iaKtVv-qOECd
|
||||
|
||||
### 123
|
||||
# @no-redirect
|
||||
GET http://127.0.0.1:6400/parser?url=https://www.123pan.com/s/iaKtVv-6OECd.html&pwd=DcGe
|
||||
GET http://127.0.0.1:6400/parser?url=https://www.123pan.com/s/iaKtVv-6OECd.html&pwd=DcGeasd
|
||||
|
||||
###
|
||||
POST http://127.0.0.1:6400/login1
|
||||
|
||||
Reference in New Issue
Block a user