You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何从印度铁路rbs站点抓取含隐藏数据的完整列车中间站信息

解决方案

方案1:使用支持JS渲染的爬取工具(最省心,改动最小)

纯Jsoup只能解析静态HTML,无法执行页面JavaScript,也没法模拟按钮点击触发动态请求,你可以换成轻量的无界面JS渲染工具HtmlUnit,或者自动化测试工具Selenium,完全复用你现有的表格解析逻辑:

  • 引入HtmlUnit依赖,配置开启JavaScript执行、禁用CSS渲染减少性能消耗
  • 模拟提交起点终点参数到目标页面,获取渲染后的页面对象
  • 定位到页面上所有加载隐藏站点的按钮元素,循环执行模拟点击操作,每次点击后等待1-2秒确保JS请求完成、DOM更新
  • 所有隐藏内容加载完成后,直接提取tbody元素,用你现有的行遍历逻辑解析全部站点数据即可

方案2:抓全请求参数直接调用接口(性能更高,无需渲染)

你直接调用接口失败的核心原因是缺了会话关联和正确的参数规则,按以下步骤调整即可:

  1. 第一次用Jsoup发POST请求到ShortPath.jsp时,不要直接拿Document,先获取Response对象,把返回的所有Cookie(核心是JSESSIONID)全部保存下来,同时解析返回的页面统计加载隐藏内容的按钮总数,确定需要调用StationXmlServlet的次数
  2. 调用StationXmlServlet的规则:
    • 必须携带第一次请求拿到的全部Cookie,否则服务器会判定请求非法
    • 参数为表单键值对格式,不要用逗号拼接,index参数从1开始依次递增,和按钮顺序一一对应,其余参数保持你抓包到的固定值即可
  3. 每次接口返回的JSON直接解析,提取站点信息和你之前从初始表格拿到的内容合并即可

代码调整示例(方案2核心逻辑)

private void shortestPath(String source, String destination) {
    try {
        // 第一步:先拿Cookie和初始页面
        Connection.Response initRes = Jsoup.connect(url)
                .data("srcCode", source.toUpperCase())
                .data("destCode", destination.toUpperCase())
                .data("guageType", "S")
                .data("transhipmentFlag", "false")
                .data("distance", "goods")
                .method(Connection.Method.POST)
                .execute();
        Map<String, String> cookies = initRes.cookies();
        Document doc = initRes.parse();
        
        // 你的原有初始表格解析逻辑保留
        Element table = doc.select("tbody").get(0);
        Elements rows = table.select("tr");
        stationCodeList = new String[rows.size() - 3];
        jsonPath = new JSONObject();
        for (int row = 3; row < rows.size(); row++) {
            JSONObject jsonObject = new JSONObject();
            Elements cols = rows.get(row).select("td");
            String code = cols.get(1).text();
            String name = cols.get(2).text();
            String cum_dist = cols.get(3).text();
            String inter_dist = cols.get(4).text();
            String gauge = cols.get(5).text();
            String carry_cap = cols.get(6).text();
           
            jsonObject.put("Code", code);
            jsonObject.put("Name", name);
            jsonObject.put("Cumulative Distance", cum_dist);
            jsonObject.put("inter Distance", inter_dist);
            jsonObject.put("Gauge Type", gauge);
            jsonObject.put("Carrying Capacity", carry_cap);
            jsonPath.put(code, jsonObject);
            stationCodeList[row - 3] = code;
        }
        
        // 第二步:统计按钮数,循环调用接口拿隐藏数据
        // 先定位加载隐藏内容的按钮元素,拿到总数量,选择器可根据页面实际结构调整
        Elements loadBtns = doc.select(".load-inter-btn"); 
        for (int i = 1; i <= loadBtns.size(); i++) {
            // 发请求拿隐藏数据
            String servletRes = Jsoup.connect("https://rbs.indianrail.gov.in/ShortPath/StationXmlServlet")
                    .cookies(cookies)
                    .data("route", "inter")
                    .data("index", String.valueOf(i))
                    .data("distance", "goods")
                    .data("PageName", "ShortPath")
                    .method(Connection.Method.POST)
                    .ignoreContentType(true)
                    .execute()
                    .body();
            // 解析返回的JSON,把站点数据合并到jsonPath和stationCodeList即可
            JSONObject hideData = new JSONObject(servletRes);
            // ... 补充JSON解析逻辑合并数据即可
        }
        
    } catch (Exception e) {
        e.printStackTrace();
    }
    this.destination =new Station(stationCodeList[stationCodeList.length-1]);
}

内容的提问来源于stack exchange,提问作者IronFist

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.06 04:39:03