Эх сурвалжийг харах

add:增加IKOA影片搜索v1

tujidelv 3 жил өмнө
parent
commit
d0b61b5226

+ 21 - 0
src/main/java/top/lvzhiqiang/controller/CrawlerController.java

@@ -4,6 +4,7 @@ import org.springframework.stereotype.Controller;
 import org.springframework.web.bind.annotation.RequestMapping;
 import org.springframework.web.bind.annotation.ResponseBody;
 import top.lvzhiqiang.dto.R;
+import top.lvzhiqiang.exception.ParameterException;
 import top.lvzhiqiang.service.CrawlerService;
 import top.lvzhiqiang.util.StringUtils;
 
@@ -61,4 +62,24 @@ public class CrawlerController {
         crawlerService.jsoupXiaoeknowCourse(status, isDel, ignoreRetryCount);
         return R.ok();
     }
+
+    /**
+     * searchIkoaMovie
+     *
+     * @author lvzhiqiang
+     * 2022/9/17 12:55
+     */
+    @RequestMapping("/searchIkoaMovie")
+    @ResponseBody
+    public String searchIkoaMovie(String keywords, String movieType, String by, String page) throws Exception {
+        if (StringUtils.isEmpty(keywords)) {
+            throw new ParameterException("搜索关键词不能为空");
+        }
+
+        if (StringUtils.isEmpty(page)) {
+            page = "1";
+        }
+
+        return crawlerService.searchIkoaMovie(keywords, movieType, by, page);
+    }
 }

+ 8 - 0
src/main/java/top/lvzhiqiang/service/CrawlerService.java

@@ -23,4 +23,12 @@ public interface CrawlerService {
      * 2022/9/10 21:24
      */
     void jsoupXiaoeknowCourse(Integer status, Integer isDel, Integer ignoreRetryCount);
+
+    /**
+     * searchIkoaMovie
+     *
+     * @author lvzhiqiang
+     * 2022/9/17 12:55
+     */
+    String searchIkoaMovie(String keywords, String movieType, String by, String page) throws Exception;
 }

+ 116 - 0
src/main/java/top/lvzhiqiang/service/impl/CrawlerServiceImpl.java

@@ -4,6 +4,7 @@ import com.alibaba.fastjson.JSONArray;
 import com.alibaba.fastjson.JSONObject;
 import lombok.extern.slf4j.Slf4j;
 import org.jsoup.Connection;
+import org.jsoup.HttpStatusException;
 import org.jsoup.Jsoup;
 import org.springframework.beans.factory.annotation.Value;
 import org.springframework.stereotype.Service;
@@ -17,9 +18,12 @@ import top.lvzhiqiang.mapper.CrawlerXiaoeknowCourseMapper;
 import top.lvzhiqiang.mapper.DicCodeMapper;
 import top.lvzhiqiang.service.CrawlerService;
 import top.lvzhiqiang.util.DateUtils;
+import top.lvzhiqiang.util.StringUtils;
 
 import javax.annotation.Resource;
 import java.io.IOException;
+import java.net.InetSocketAddress;
+import java.net.Proxy;
 import java.time.LocalDate;
 import java.time.LocalDateTime;
 import java.util.*;
@@ -45,6 +49,8 @@ public class CrawlerServiceImpl implements CrawlerService {
 
     private final int defaultPageSize = 8;
 
+    private static String ikoaToken = "";
+
     /**
      * findXiaoeknowCourse
      *
@@ -245,6 +251,116 @@ public class CrawlerServiceImpl implements CrawlerService {
         log.warn("jsoupXiaoeknowCourse 结束:insertTotalNum={},耗时={}", insertTotalNum, stopWatch.getTotalTimeSeconds());
     }
 
+    /**
+     * searchIkoaMovie
+     *
+     * @author lvzhiqiang
+     * 2022/9/17 12:55
+     */
+    @Override
+    public String searchIkoaMovie(String keywords, String movieType, String by, String page) throws Exception {
+        log.warn("searchIkoaMovie 开始:keywords={},movieType={},by={},page={}", keywords, movieType, by, page);
+        StopWatch stopWatch = new StopWatch();
+        stopWatch.start();
+
+        // 获取ikoa常量MAP
+        Map<String, String> ikoaConstantMap = dicCodeMapper.findAll().stream()
+                .filter(x -> "ikoa".equals(x.getCodeDesc()) && x.getEnv().contains(env))
+                .collect(Collectors.toMap(DicCode::getCodeKey, DicCode::getCodeValue, (key1, key2) -> key1));
+
+        // 代理及TOKEN设置
+        Proxy proxy;
+        if ("dev".equals(env)) {
+            proxy = new Proxy(Proxy.Type.SOCKS, new InetSocketAddress("127.0.0.1", 1080));
+        } else {
+            proxy = Proxy.NO_PROXY;
+        }
+        if (StringUtils.isEmpty(ikoaToken)) {
+            generateIkoaToken(ikoaConstantMap, proxy);
+        }
+
+        Connection.Response response;
+        StringBuffer sb = new StringBuffer();
+        JSONObject result = null;
+        for (int i = 0; i < 2; i++) {
+            try {
+                response = Jsoup.connect(ikoaConstantMap.get("search_url"))
+                        .header("Authorization", "Token " + ikoaToken)
+                        .timeout(50000)
+                        .proxy(proxy)
+                        .data("page", page).data("keywords", keywords).data("movie_type", movieType).data("by", by)
+                        .ignoreContentType(true)
+                        .userAgent(getUserAgent())
+                        .header("referer", ikoaConstantMap.get("referer"))
+                        .method(Connection.Method.GET)
+                        .execute();
+                result = JSONObject.parseObject(response.body());
+                sb.append("total:".concat(String.valueOf(result.getInteger("result_count"))).concat("<br/>"));
+                parseIkoaSearchResult(result.getJSONArray("data"), sb);
+
+                break;
+            } catch (HttpStatusException hse) {
+                generateIkoaToken(ikoaConstantMap, proxy);
+            } catch (Exception e) {
+                log.error("IKOA搜索异常,ikoaConstantMap={},result={}", ikoaConstantMap, result.toString(), e);
+                throw new Exception("IKOA搜索异常!");
+            }
+        }
+
+        stopWatch.stop();
+        log.warn("searchIkoaMovie 结束:耗时={}", stopWatch.getTotalTimeSeconds());
+
+        return sb.toString();
+    }
+
+    private void parseIkoaSearchResult(JSONArray result, StringBuffer sb) {
+        sb.append("<table border=\"1\" cellspacing=\"0\"><tr><th>序号</th><th>影片名称</th><th>cid</th><th>pid</th><th>影片类型</th><th>码率</th><th>总分段数量</th><th>价格</th><th>是否已购</th><th>购买后有效期</th><th>封面</th></tr>");
+
+        for (int i = 0; i < result.size(); i++) {
+            JSONObject jsonObject = result.getJSONObject(i);
+            sb.append("<tr>");
+
+            sb.append("<td>").append(i + 1).append("</td>");
+            sb.append("<td>").append(jsonObject.getString("name")).append("</td>");
+            sb.append("<td>").append(jsonObject.getString("cid")).append("</td>");
+            sb.append("<td>").append(jsonObject.getString("product_id")).append("</td>");
+            sb.append("<td>").append(jsonObject.getString("movie_type")).append("</td>");
+            sb.append("<td>").append(jsonObject.getLong("bitrate")).append("</td>");
+            sb.append("<td>").append(jsonObject.getInteger("total_part")).append("</td>");
+            sb.append("<td>").append(jsonObject.getInteger("cost")).append("</td>");
+            sb.append("<td>").append(jsonObject.getBoolean("purchased") ? "已购买" : "未购买").append("</td>");
+            sb.append("<td>").append(jsonObject.getInteger("valid_period")).append("小时").append("</td>");
+            sb.append("<td>").append("<img src=\"" + jsonObject.getString("package_image") + "\" alt=\"封面\" width=\"147\" height=\"auto\">").append("</td>");
+
+            sb.append("</tr>");
+        }
+        sb.append("</table>");
+    }
+
+    private void generateIkoaToken(Map<String, String> ikoaConstantMap, Proxy proxy) throws Exception {
+        try {
+            JSONObject params = new JSONObject();
+            params.put("username", ikoaConstantMap.get("username"));
+            params.put("password", ikoaConstantMap.get("password"));
+            Connection.Response response = Jsoup.connect(ikoaConstantMap.get("login_url"))
+                    .header("Content-Type", "application/json;charset=UTF-8")
+                    .timeout(50000)
+                    .proxy(proxy)
+                    .requestBody(params.toString())
+                    .ignoreContentType(true)
+                    .userAgent(getUserAgent())
+                    .header("referer", ikoaConstantMap.get("referer"))
+                    .method(Connection.Method.POST)
+                    .execute();
+
+            JSONObject result = JSONObject.parseObject(response.body());
+            ikoaToken = result.getJSONObject("data").getString("token");
+        } catch (Exception e) {
+            log.error("IKOA登录异常,ikoaConstantMap={}", ikoaConstantMap.toString(), e);
+            throw new Exception("IKOA登录异常!");
+        }
+    }
+
     private Map<String, String> getCookies(String url) throws IOException {
         Connection.Response res1 = Jsoup.connect(url).method(Connection.Method.GET).execute();
         return res1.cookies();

+ 28 - 1
src/main/resources/static/crawler.html

@@ -53,7 +53,6 @@
             <input type="submit" value="提交">
         </form>
     </div>
-    <hr/>
     <div style="margin-right:20px;">
         <span class="font">jsoupXiaoeknowCourse</span>
         <form method="post" action="bg/crawler/jsoupXiaoeknowCourse">
@@ -66,6 +65,34 @@
             <input type="submit" value="提交">
         </form>
     </div>
+    <hr/>
+    <div style="margin-right:20px;">
+        <span class="font">searchIkoaMovie</span>
+        <form method="post" action="bg/crawler/searchIkoaMovie">
+            <span>搜索关键词</span>
+            <input type="text" name="keywords" placeholder="关键词,不可为空"/>
+            <span>影片类型</span>
+            <select name="movieType" style="height: 21.43px;">
+                <option value="*">全部</option>
+                <option value="dmm2d">dmm2d</option>
+                <option value="dmm4k">dmm4k</option>
+                <option value="dmmvr">dmmvr</option>
+                <option value="dmmvr2">dmmvr2</option>
+                <option value="mgs_dash">mgs_dash</option>
+                <option value="mgs_hls">mgs_hls</option>
+            </select>
+            <span>搜索字段</span>
+            <select name="by" style="height: 21.43px;">
+                <option value="*">自动</option>
+                <option value="cid">cid</option>
+                <option value="product_id">product_id</option>
+                <option value="name">影片名称</option>
+            </select>
+            <span>页码</span>
+            <input type="text" name="page" placeholder="可为空,默认1"/>
+            <input type="submit" value="提交">
+        </form>
+    </div>
 </div>
 </body>
 </html>