当前位置: 首页 > 知识库问答 >
问题:

使用jsoup获取具有类的div元素

程成天
2023-03-14

我是Jsoup解析的新手,我想获得这个页面上所有公司的列表:https://angel.co/companies?company_types[]=startup现在,一种实现这一点的方法实际上是使用与我需要的相关的div标记来检查页面。但是,当我调用该方法时:

Document doc = Jsoup.connect("https://angel.co/companies?company_types[]=Startup").get();
System.out.println(doc.html());

首先,我甚至无法在我的consol html输出中找到那些DIV标记(这些标记应该给出公司的列表);其次,即使我找到了它,我如何才能找到具有class name的某个DIV元素:

div class=" dc59 frw44 _a _jm"  

请原谅我的行话,我不知道该怎么做。

共有1个答案

仲孙俊贤
2023-03-14

这些数据不嵌入到页面中,但使用后续API调用检索:

  • 发布https://angel.co/company_filters/search_data以获取ids数组和名为hexdigest
  • 的令牌
  • 获取https://angel.co/companies/startups以使用前一个请求的输出检索公司数据

对每个页面重复上述操作(因此每个页面都需要一个新的令牌&一个ID列表)。可以使用Chrome dev console在“网络”选项卡中看到此过程。

第一个post请求提供JSON输出,但第二个请求(get)提供JSON对象属性中的HTML数据。

以下内容提取了公司筛选器:

private static CompanyFilter getCompanyFilter(final String filter, final int page) throws IOException {

    String response = Jsoup.connect("https://angel.co/company_filters/search_data")
            .header("Content-Type", "application/x-www-form-urlencoded;charset=UTF-8")
            .header("X-Requested-With", "XMLHttpRequest")
            .data("filter_data[company_types][]=", filter)
            .data("sort", "signal")
            .data("page", String.valueOf(page))
            .userAgent("Mozilla")
            .ignoreContentType(true)
            .post().body().text();

    GsonBuilder gsonBuilder = new GsonBuilder();
    Gson gson = gsonBuilder.create();
    return gson.fromJson(response, CompanyFilter.class);
}

那么下面摘录公司:

private static List<Company> getCompanies(final CompanyFilter companyFilter) throws IOException {

    List<Company> companies = new ArrayList<>();

    URLConnection urlConn = new URL("https://angel.co/companies/startups?" + companyFilter.buildRequest()).openConnection();
    urlConn.setRequestProperty("User-Agent", "Mozilla");
    urlConn.connect();
    BufferedReader reader = new BufferedReader(new InputStreamReader(urlConn.getInputStream(), "UTF-8"));
    HtmlContainer htmlObj = new Gson().fromJson(reader, HtmlContainer.class);

    Element doc = Jsoup.parse(htmlObj.getHtml());
    Elements data = doc.select("div[data-_tn]");

    if (data.size() > 0) {
        for (int i = 2; i < data.size(); i++) {
            companies.add(new Company(data.get(i).select("a").first().attr("title"),
                    data.get(i).select("a").first().attr("href"),
                    data.get(i).select("div.pitch").first().text()));
        }

    } else {
        System.out.println("no data");
    }
    return companies;
}

主要功能

public static void main(String[] args) throws IOException {

    int pageCount = 1;
    List<Company> companies = new ArrayList<>();

    for (int i = 0; i < 10; i++) {

        System.out.println("get page n°" + pageCount);
        CompanyFilter companyFilter = getCompanyFilter("Startup", pageCount);
        pageCount++;
        System.out.println("digest     : " + companyFilter.getDigest());
        System.out.println("count      : " + companyFilter.getTotalCount());
        System.out.println("array size : " + companyFilter.getIds().size());
        System.out.println("page       : " + companyFilter.getpage());

        companies.addAll(getCompanies(companyFilter));

        if (companies.size() == 0) {
            break;
        } else {
            System.out.println("size     : " + companies.size());
        }
    }
}

CompanyCompanyFilter&HTMLContainer是模型类:

class CompanyFilter {

    @SerializedName("ids")
    private List<Integer> mIds;

    @SerializedName("hexdigest")
    private String mDigest;

    @SerializedName("total")
    private String mTotalCount;

    @SerializedName("page")
    private int mPage;

    @SerializedName("sort")
    private String mSort;

    @SerializedName("new")
    private boolean mNew;

    public List<Integer> getIds() {
        return mIds;
    }

    public String getDigest() {
        return mDigest;
    }

    public String getTotalCount() {
        return mTotalCount;
    }

    public int getpage() {
        return mPage;
    }

    private String buildRequest() {
        String out = "total=" + mTotalCount + "&";
        out += "sort=" + mSort + "&";
        out += "page=" + mPage + "&";
        out += "new=" + mNew + "&";
        for (int i = 0; i < mIds.size(); i++) {
            out += "ids[]=" + mIds.get(i) + "&";
        }
        out += "hexdigest=" + mDigest + "&";
        return out;
    }
}

private static class Company {

    private String mLink;
    private String mName;
    private String mDescription;

    public Company(String name, String link, String description) {
        mLink = link;
        mName = name;
        mDescription = description;
    }

    public String getLink() {
        return mLink;
    }

    public String getName() {
        return mName;
    }

    public String getDescription() {
        return mDescription;
    }
} 

private static class HtmlContainer {

    @SerializedName("html")
    private String mHtml;

    public String getHtml() {
        return mHtml;
    }
}

完整的代码也可以在这里获得

 类似资料:
  • 我正在尝试从网站获取一些数据。它看起来像这样 我只需要得到div标签中的时间值。这是我的Java代码。 它没有给出任何错误,但在日志上 "D/NetworkSecurityConfig:未指定网络安全配置,使用平台默认设置" 我看到也许这可以帮助你解决问题。提前感谢您,任何回应将不胜感激。

  • 我有一个HTML,比如, 这里有两个“tel”类元素,如何提取这两个元素?如果程序不知道这些名为“tel”的类的数量,如何提取?请帮忙。 最终目标是获取tel类元素中的所有文本。 我已经试着用下一个兄弟元素来解决这个问题。但是那里没有运气。不过我可能试错了。请纠正我或帮助我实现我在这里尝试的目标。 提前谢谢。

  • 这是我试图解析的html: 我想得到

  • 我有一个分页div,其中我有一个html,我不能配置为添加类或ID。我得用我现有的工作。 我有一个问题,当页面被选中时,它会丢失。自动的页面编号是文本:“1”或它也可以是“2”,我想知道一种方法,通过css或javascript我可以得到这个元素“1”或“2”或“3”...并自定义它。 代码如下: null null 有人能帮帮我吗?

  • 我想从这个网站上提取红色标记的信息。 本站的html文本由以下图片呈现。我要提取的信息再次被红色标记。 问题是我找不到带有class属性“find-元素”的div元素。我的代码看起来像这样 如果有人能帮我,那就太好了。 谢谢。