MOD:添加首页展示
This commit is contained in:
+2
-1
@@ -35,4 +35,5 @@ build/
|
||||
|
||||
### VS Code ###
|
||||
.vscode/
|
||||
/.mvn
|
||||
/.mvn
|
||||
/dependency-reduced-pom.xml
|
||||
|
||||
@@ -90,4 +90,7 @@ maxCount:最大返回值,返回结果里面 list 最大数量。 最大值10
|
||||
### 直播MV来源:
|
||||
小武哥 :https://t.me/BoBaiBroo
|
||||
|
||||
直播文件:https://t.me/fongmi_offical/54024/244800
|
||||
直播文件:https://t.me/fongmi_offical/54024/244800
|
||||
|
||||
### 声明
|
||||
仅供学习交流,严禁用于商业用途,请于24小时内删除。
|
||||
@@ -13,6 +13,7 @@ import io.vertx.core.http.HttpServer;
|
||||
import io.vertx.core.json.Json;
|
||||
import io.vertx.ext.web.Router;
|
||||
import io.vertx.ext.web.RoutingContext;
|
||||
import io.vertx.ext.web.handler.StaticHandler;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
@@ -52,7 +53,8 @@ public class MainVerticle extends AbstractVerticle {
|
||||
Router router = Router.router(vertx);
|
||||
router.route("/mv/search").handler(this::searchMv);
|
||||
router.route("/mv/vod").handler(this::searchMvVod);
|
||||
router.route().handler(req -> req.response().putHeader("content-type", "text/plain").end("Hello from Vert.x!"));
|
||||
router.route("/*").handler(StaticHandler.create("static"));
|
||||
router.route().handler(this::home);
|
||||
httpServer.requestHandler(router);
|
||||
|
||||
httpServer.listen(7777, http -> {
|
||||
@@ -66,21 +68,36 @@ public class MainVerticle extends AbstractVerticle {
|
||||
port = httpServer.actualPort();
|
||||
}
|
||||
|
||||
/**
|
||||
* 参考 <a href="https://github.com/FongMi/TV/blob/release/app/src/main/java/com/fongmi/android/tv/model/SiteViewModel.java#L32">...</a>
|
||||
* @param req
|
||||
*/
|
||||
private void searchMvVod(RoutingContext req) {
|
||||
// 获取参数
|
||||
String wd = VertxUtils.queryParam(req, "wd");
|
||||
String ac = VertxUtils.queryParam(req, "ac");
|
||||
String ids = VertxUtils.queryParam(req, "ids");
|
||||
String maxCount = VertxUtils.queryParam(req, "maxCount");
|
||||
int max = Math.min(Math.max(NumberUtils.toInt(maxCount, 100), 10), 1000);
|
||||
String query = StringUtils.isNotEmpty(wd) ? wd : ids;
|
||||
String ac = VertxUtils.queryParam(req, "ac");
|
||||
String type = VertxUtils.queryParam(req, "t");
|
||||
//query = StringUtils.isNotEmpty(query) ? query : "我";
|
||||
String maxCount = VertxUtils.queryParam(req, "maxCount");
|
||||
int max = Math.min(Math.max(NumberUtils.toInt(maxCount, 200), 10), 1000);
|
||||
String pg = VertxUtils.queryParam(req, "pg");
|
||||
int page = NumberUtils.toInt(pg, 0);
|
||||
|
||||
// 处理结果
|
||||
VodResult vodResult = null;
|
||||
try {
|
||||
if (mvService != null) {
|
||||
// 搜索
|
||||
if (mvService != null && StringUtils.isNotEmpty(query) && page <= 0) {
|
||||
vodResult = mvService.searchVod(query, max);
|
||||
}
|
||||
|
||||
// 首页
|
||||
if (mvService != null && StringUtils.isEmpty(query)) {
|
||||
vodResult = mvService.searchVodHome(type, page);
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
@@ -95,8 +112,10 @@ public class MainVerticle extends AbstractVerticle {
|
||||
private void searchMv(RoutingContext req) {
|
||||
// 获取参数
|
||||
String query = VertxUtils.queryParam(req, "query");
|
||||
String wd = VertxUtils.queryParam(req, "wd");
|
||||
query = StringUtils.isNotEmpty(query) ? query : wd;
|
||||
String maxCount = VertxUtils.queryParam(req, "maxCount");
|
||||
int max = Math.min(Math.max(NumberUtils.toInt(maxCount, 100), 10), 1000);
|
||||
int max = Math.min(Math.max(NumberUtils.toInt(maxCount, 200), 10), 1000);
|
||||
|
||||
// 处理结果
|
||||
MvResult search = null;
|
||||
@@ -115,6 +134,12 @@ public class MainVerticle extends AbstractVerticle {
|
||||
.end(jsonString);
|
||||
}
|
||||
|
||||
private void home(RoutingContext req) {
|
||||
req.response()
|
||||
.putHeader("content-type", "text/plain;charset=utf-8")
|
||||
.end("MV搜索服务\n源码网址:https://github.com/leosam1024/tvbox-mv");
|
||||
}
|
||||
|
||||
|
||||
public static void main(String[] args) throws Exception {
|
||||
Vertx vertx = Vertx.vertx();
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
package com.leosam.tvbox.mv.data;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
public class VodClass {
|
||||
|
||||
@JsonProperty("type_id")
|
||||
private String typeId;
|
||||
|
||||
@JsonProperty("type_name")
|
||||
private String typeName;
|
||||
|
||||
public String getTypeId() {
|
||||
return typeId;
|
||||
}
|
||||
|
||||
public VodClass setTypeId(String typeId) {
|
||||
this.typeId = typeId;
|
||||
return this;
|
||||
}
|
||||
|
||||
public String getTypeName() {
|
||||
return typeName;
|
||||
}
|
||||
|
||||
public VodClass setTypeName(String typeName) {
|
||||
this.typeName = typeName;
|
||||
return this;
|
||||
}
|
||||
}
|
||||
@@ -1,5 +1,7 @@
|
||||
package com.leosam.tvbox.mv.data;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
@@ -14,6 +16,8 @@ public class VodResult {
|
||||
private int limit;
|
||||
private int total;
|
||||
private List<Vod> list;
|
||||
@JsonProperty("class")
|
||||
private List<VodClass> vodClassList;
|
||||
|
||||
public void init() {
|
||||
this.code = 1;
|
||||
@@ -76,4 +80,13 @@ public class VodResult {
|
||||
this.list = list;
|
||||
return this;
|
||||
}
|
||||
|
||||
public List<VodClass> getVodClassList() {
|
||||
return vodClassList;
|
||||
}
|
||||
|
||||
public VodResult setVodClassList(List<VodClass> vodClassList) {
|
||||
this.vodClassList = vodClassList;
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,8 +1,11 @@
|
||||
package com.leosam.tvbox.mv.service;
|
||||
|
||||
import com.fasterxml.jackson.core.type.TypeReference;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.leosam.tvbox.mv.data.MvContent;
|
||||
import com.leosam.tvbox.mv.data.MvResult;
|
||||
import com.leosam.tvbox.mv.data.Vod;
|
||||
import com.leosam.tvbox.mv.data.VodClass;
|
||||
import com.leosam.tvbox.mv.data.VodResult;
|
||||
import com.leosam.tvbox.mv.lucene.MvIndex;
|
||||
import com.leosam.tvbox.mv.lucene.MvSearcher;
|
||||
@@ -23,9 +26,12 @@ import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Path;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.atomic.AtomicInteger;
|
||||
|
||||
@@ -35,9 +41,14 @@ import java.util.concurrent.atomic.AtomicInteger;
|
||||
*/
|
||||
public class MvService {
|
||||
private static final Logger logger = LoggerFactory.getLogger(MvService.class);
|
||||
|
||||
private static final String indexDirectoryPath = "index";
|
||||
private static final String MV_FILE = "tvbox/16wMV.txt";
|
||||
private static final Map<String, List<String>> homeConfigMap = new LinkedHashMap<>();
|
||||
private static final String HOME_KEY = "HOME";
|
||||
/**
|
||||
* 最低相似分数
|
||||
*/
|
||||
private static final float MIN_QUERY_SCORE = 3.0F;
|
||||
|
||||
private MvSearcher mvSearcher;
|
||||
|
||||
@@ -56,6 +67,10 @@ public class MvService {
|
||||
result.setTotalHits(topDocs.totalHits.value);
|
||||
result.setList(new ArrayList<>(topDocs.scoreDocs.length));
|
||||
for (ScoreDoc scoreDoc : topDocs.scoreDocs) {
|
||||
// 分数太低 忽略
|
||||
if(scoreDoc.score < MIN_QUERY_SCORE){
|
||||
break;
|
||||
}
|
||||
Document document = mvSearcher.getDocument(scoreDoc.doc);
|
||||
if (document == null) {
|
||||
continue;
|
||||
@@ -97,7 +112,6 @@ public class MvService {
|
||||
vod.setVodName(wd);
|
||||
vod.setVodPlayFrom("mv");
|
||||
vod.setVodPic("http://yanxuan.nosdn.127.net/b6fb987ce79f308949e44f5129a4b51c.jpeg");
|
||||
// vod.setVodPic("http://m4.auto.itc.cn/auto/content/20230611/45d65d8a001f0c5aa008030f41c98666.jpeg");
|
||||
List<String> playUrlList = new LinkedList<>();
|
||||
Set<String> vodActorList = new LinkedHashSet<>();
|
||||
for (MvContent content : search.getList()) {
|
||||
@@ -116,7 +130,51 @@ public class MvService {
|
||||
return vodResult;
|
||||
}
|
||||
|
||||
public VodResult searchVodHome(String type, int page) throws Exception {
|
||||
if (page > 1) {
|
||||
return new VodResult();
|
||||
}
|
||||
|
||||
StopWatch stopWatch = new StopWatch();
|
||||
stopWatch.start();
|
||||
|
||||
VodResult vodResult = new VodResult();
|
||||
vodResult.init();
|
||||
vodResult.setList(new ArrayList<>()).getList();
|
||||
|
||||
// 分类
|
||||
if (StringUtils.isEmpty(type)) {
|
||||
vodResult.setVodClassList(new ArrayList<>(homeConfigMap.size()));
|
||||
Set<String> keySet = homeConfigMap.keySet();
|
||||
for (String key : keySet) {
|
||||
if (HOME_KEY.equalsIgnoreCase(key)) {
|
||||
continue;
|
||||
}
|
||||
VodClass vodClass = new VodClass().setTypeId(key).setTypeName(key);
|
||||
vodResult.getVodClassList().add(vodClass);
|
||||
}
|
||||
}
|
||||
|
||||
// 首页mv推荐
|
||||
String thisType = StringUtils.isNotEmpty(type) ? type : HOME_KEY;
|
||||
List<String> geshouList = homeConfigMap.getOrDefault(thisType, new ArrayList<>());
|
||||
for (String geshou : geshouList) {
|
||||
Vod vod = new Vod();
|
||||
vod.setVodId(geshou);
|
||||
vod.setVodName(geshou);
|
||||
vod.setVodPlayFrom("mv");
|
||||
vod.setVodPic("http://yanxuan.nosdn.127.net/b6fb987ce79f308949e44f5129a4b51c.jpeg");
|
||||
vodResult.getList().add(vod);
|
||||
}
|
||||
|
||||
stopWatch.stop();
|
||||
logger.info("加载首页成功,类型={}, 返回={}条, 耗时{}毫秒", thisType, vodResult.getList().size(), stopWatch.getTotalTimeMillis());
|
||||
return vodResult;
|
||||
}
|
||||
|
||||
public void initIndex() throws Exception {
|
||||
// 加载首页配置
|
||||
buildHomeConfig();
|
||||
|
||||
// 重建索引
|
||||
String indexAbsolutePath = new File(indexDirectoryPath).getAbsoluteFile().getAbsolutePath();
|
||||
@@ -129,6 +187,17 @@ public class MvService {
|
||||
search("五月天", 10);
|
||||
}
|
||||
|
||||
private void buildHomeConfig() {
|
||||
try {
|
||||
String content = ClassPathReaderUtils.getContent("tvbox/home.json");
|
||||
Map<String, List<String>> map = new ObjectMapper().readValue(content, new TypeReference<HashMap<String, List<String>>>() {
|
||||
});
|
||||
homeConfigMap.putAll(map);
|
||||
logger.info("加载首页配置成功");
|
||||
} catch (Exception e) {
|
||||
logger.error("buildHomeConfig error", e);
|
||||
}
|
||||
}
|
||||
|
||||
private static void reBuildIndex(String indexDirectoryPath) throws IOException {
|
||||
File file = new File(indexDirectoryPath).getAbsoluteFile();
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
"key": "MV_vod",
|
||||
"name": "👀┃MV┃视频",
|
||||
"type": 1,
|
||||
"api": "http://192.168.31.253:7777/mv/vod",
|
||||
"api": "./mv/vod",
|
||||
"searchable": 1,
|
||||
"quickSearch": 1,
|
||||
"filterable": 1
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
{
|
||||
"HOME" : [ "周杰伦", "林俊杰", "张学友", "邓紫棋", "五月天", "梁咏琪", "王菲", "张信哲", "陈奕迅", "刘德华", "林忆莲", "Beyond", "F4", "S.H.E", "蔡依林", "张惠妹", "刘若英", "方大同", "林宥嘉", "白安", "金志文", "郭富城", "韦礼安", "容祖儿", "庾澄庆", "华晨宇", "苏打绿", "任贤齐", "庄心妍", "田馥甄", "杨坤", "林忆诗筑", "TFBOYS", "EXO", "李荣浩", "范晓萱", "林玉英", "王力宏", "光良", "邓丽君", "林青霞", "杨洪基", "高慧君", "高胜美", "庞龙", "高晓松", "童丽", "枚文琪", "王菀之", "张格格", "张杰", "黄家驹", "MAX", "薛之谦", "周笔畅", "罗志祥", "林凡", "林志颖", "宋茜", "鞠婧祎", "吴亦凡", "李宇春", "朴树", "许巍", "苏运莹", "郑秀文", "张媛媛", "腾格尔", "邰正宵", "李健", "柯以敏", "叶洛洛", "宋承宪", "龙梅子", "钟汶优", "黄韵玲", "钟欣潼", "罗浩然", "林志炫", "牛奶咖啡", "王琪", "格格", "韩红", "胡夏", "申哥", "孟鹤堂", "毛阿敏", "任然", "伍佰", "信乐团", "凤凰传奇", "刀郎", "刘至佳", "动力列车", "动力火车", "半吨兄弟", "卓依婷", "单依纯", "古巨基", "叶倩文", "告五人", "周传雄", "周华健", "周深", "唐朝乐队", "孙悦", "孙楠", "孙燕姿", "宋亚轩", "宋岳庭", "小乐哥", "小虎队", "小阿七", "尹正", "张国荣", "张宇", "张涵韵", "张碧晨", "张雨生", "张靓颖", "张韶涵", "易烊千玺", "曲肖冰", "李克勤", "李字春", "李宗盛", "李玉刚", "李玟", "杨丞琳", "杨宗纬", "梁静茹", "梅艳芳", "毛不易", "毛宁", "汪佩蓉", "汪峰", "汪苏泷", "王以太", "王小帅", "王心凌", "王忻辰", "王杰", "王艺霖", "王若琳", "王贰浪", "王靖雯", "田震", "白小白", "盂庭苇", "程响", "罗大佑", "羽泉", "老于", "老狼", "胡彦斌", "花儿乐队", "莫文蔚", "萧亚轩", "萧敬腾", "蓝心羽", "街道办GDC", "许嵩", "许飞", "谢霆锋", "谭咏鳞", "谭咏麟", "费玉清", "赵雷", "邓寓君", "那英", "郑智化", "郑源", "郑钧", "郭兰英", "郭顶", "金玟岐", "队长", "阿杜", "阿肆", "阿郎", "陈一郎", "陈慧娴", "陈玉建", "陈珊妮", "陈百强", "陈绮贞", "霍尊", "韩宝仪", "音阙诗听", "风凰传奇", "飞儿乐队", "黑豹乐队", "齐秦", "齐豫", "A-Lin", "BEYOND", "MISSKO", "SHE" ],
|
||||
"A" : [ "阿杜", "阿吉仔", "阿郎", "A-Lin", "阿悄", "阿肆", "阿雅" ],
|
||||
"B" : [ "白安", "鲍勃", "半吨兄弟", "Beyond", "BEYOND", "暴林", "白雪", "白小白" ],
|
||||
"C" : [ "陈百强", "陈洪", "陈海立", "陈慧娴", "崔健", "陈洁灵", "陈洁仪", "陈雷", "草蜢", "蔡琴", "蔡秋凤", "陈绮贞", "陈瑞", "常生", "陈思安", "陈淑桦", "陈珊妮", "陈思思", "陈诗雨", "侧田", "程响", "陈贤聪", "陈晓东", "陈夏辉", "陈西洋", "陈岩", "陈玉建", "蔡依林", "陈雅森", "陈奕迅" ],
|
||||
"D" : [ "丁丁", "杜德伟", "邓鸿", "DJ", "迪克牛仔", "刀郎", "动力火车", "邓丽君", "动力列车", "丁一", "单依纯", "邓寓君", "队长", "邓紫棋" ],
|
||||
"E" : [ "EXO" ],
|
||||
"F" : [ "F4", "方大同", "飞儿乐队", "菲菲", "凤凰传奇", "范晓萱", "风雨", "费玉清" ],
|
||||
"G" : [ "郭顶", "顾峰", "郭富城", "格格", "高慧君", "宫俊", "古巨基", "光良", "郭兰英", "高胜美", "关淑怡", "告五人", "高晓松", "谷小雨", "龚月" ],
|
||||
"H" : [ "黄博", "黑豹乐队", "韩宝仪", "华晨宇", "花儿乐队", "海风", "侯刚", "韩红", "黄娟", "黄家驹", "黄凯芹", "黑龙", "黄品源", "洪荣宏", "海生", "荒山亮", "黄思婷", "镐天", "胡夏", "黄小琥", "黑羽", "胡彦斌", "黄韵玲", "黄雅珉", "何雁诗", "霍尊", "洪卓立" ],
|
||||
"J" : [ "街道办GDC", "江蕙", "蒋蒋", "鞠婧祎", "金玟岐", "江山", "蒋婴", "姜育恒", "佳仔", "甲子慧", "金志文" ],
|
||||
"K" : [ "康慷", "柯以敏" ],
|
||||
"L" : [ "龙奔", "骆超", "鲁朝阳", "刘德华", "罗大佑", "林凡", "李光", "罗桦", "罗浩然", "梁汉文", "李健", "吕继宏", "林俊杰", "刘嘉亮", "梁静茹", "李郡一", "李克勤", "老狼", "李利依", "李玟", "刘明煜", "龙梅子", "鹿乃", "李泉", "林青霞", "林沁仪", "李荣浩", "刘若英", "罗斯", "罗时丰", "李圣杰", "乐天", "李维", "刘心", "李心洁", "李行亮", "蓝心羽", "老于", "李宇春", "林一峰", "李玉刚", "柳影虹", "林宥嘉", "林忆莲", "梁咏琪", "林忆诗筑", "李研心", "林玉英", "李一哲", "李政", "李字春", "刘至佳", "李宗盛", "罗志祥", "林志颖" ],
|
||||
"M" : [ "毛阿敏", "MAX", "毛不易", "梅朵", "民歌", "孟鹤堂", "MISSKO", "孟静", "马丽", "苗苗", "毛宁", "孟庭苇", "枚文琪", "莫文蔚", "马郁", "梅艳芳" ],
|
||||
"N" : [ "牛奶咖啡", "那英" ],
|
||||
"P" : [ "庞龙", "朴树" ],
|
||||
"Q" : [ "齐霖", "齐秦", "群星", "曲肖冰", "齐豫" ],
|
||||
"R" : [ "任然", "任贤齐", "容祖儿" ],
|
||||
"S" : [ "S.H.E", "沙宝亮", "宋承宪", "苏打绿", "申哥", "SHE", "孙露", "孙楠", "SNH48", "宋茜", "孙淑媚", "司唯", "施文彬", "尚雯婕", "石修", "孙悦", "苏永康", "宋岳庭", "宋亚轩", "苏运莹", "孙燕姿", "山子华", "粟紫妍" ],
|
||||
"T" : [ "汤潮", "唐朝乐队", "TFBOYS", "田馥甄", "腾格尔", "推荐", "童丽", "TWINS", "谭维维", "覃源", "谭咏鳞", "田震", "邰正宵" ],
|
||||
"W" : [ "伍佰", "王贰浪", "王菲", "王贺", "望海高歌", "王杰", "吴建豪", "王佳佳", "王靖雯", "王麟", "韦礼安", "王力宏", "乌兰托娅", "王聆燕", "汪佩蓉", "王琪", "巫启贤", "王若琳", "吴若希", "汪苏泷", "魏什么", "王烁巽", "娃娃", "王馨", "王忻辰", "王心凌", "王小帅", "王勇", "吴亦凡", "王艺霖", "五月天", "王菀之", "王子", "王铮亮", "王子熙" ],
|
||||
"X" : [ "小阿七", "玺晨", "谢帝", "许飞", "肖环", "小虎队", "谢慧娴", "小贱", "萧敬腾", "徐佳莹", "谢雷", "小乐哥", "秀兰玛雅", "信乐团", "新奇", "许茹芸", "许嵩", "谢霆锋", "许巍", "萱萱", "徐小凤", "泫雅", "萧亚轩", "欣哲", "许志安", "薛之谦" ],
|
||||
"Y" : [ "叶蓓", "杨丞琳", "庾澄庆", "以冬", "泳儿", "岳峰", "杨光", "雨禾", "杨洪基", "俞灏明", "严爵", "杨坤", "一绫", "叶洛洛", "杨曼", "羽泉", "杨千嬅", "音阙诗听", "叶启田", "叶倩文", "于湉", "盂庭苇", "阎维文", "亦勋", "尤雅", "牙牙乐", "易烊千玺", "杨钰莹", "尹正", "杨宗纬" ],
|
||||
"Z" : [ "周笔畅", "赵传", "周传雄", "张德兰", "子芙", "张格格", "张国荣", "周蕙", "周华健", "张惠妹", "张涵韵", "张杰", "赵景春", "张津涤", "周杰伦", "张继心", "张靓颖", "赵雷", "着迷", "詹曼铃", "朱咪咪", "甄妮", "张蔷", "张蓉蓉", "周深", "张韶涵", "郑少秋", "张伟", "张文娟", "钟汶优", "张行", "周星濠", "郑兴琦", "钟欣潼", "郑秀文", "张学友", "张信哲", "张宇", "钟亚华", "郑颖杰", "张雨生", "卓依婷", "詹雅雯", "张艺兴", "张媛媛", "子子", "郑智化", "祝子杰", "张智霖", "郑紫阳" ]
|
||||
}
|
||||
Reference in New Issue
Block a user