Press "Enter" to skip to content

GitHub主题爬虫 | Python网络爬虫

GitHub主题爬虫 | Python网络爬虫 四海 第1张

网页抓取是一种从网站中提取数据的技术。它允许我们从网页上收集信息并将其用于各种目的,例如数据分析、研究或构建应用程序。

在本文中,我们将探讨一个名为“GitHub主题抓取器”的Python项目,它利用网页抓取从GitHub主题页面提取信息,并检索每个主题的存储库名称和详细信息。

介绍

GitHub是一个广泛流行的托管和协作代码存储库的平台。它提供了一个名为“主题”的功能,允许用户根据特定主题或主题对存储库进行分类。GitHub主题抓取器项目自动化了这些主题的抓取过程,并检索相关的存储库信息。

项目概述

GitHub主题抓取器使用Python实现,并利用以下库:

  • requests :用于发送HTTP请求以检索网页的HTML内容。
  • BeautifulSoup :用于解析HTML和从中提取数据的强大库。
  • pandas :用于数据操作和分析的多功能库,用于将抓取的数据组织成结构化格式。

让我们深入了解代码,并了解项目的每个组件如何工作。

Python脚本

import requestsfrom bs4 import BeautifulSoupimport pandas as pd

上面的代码片段导入了三个库:requestsBeautifulSouppandas

def topic_page_authentication(url):        topics_url = url    response = requests.get(topics_url)    page_content = response.text    doc = BeautifulSoup(page_content, 'html.parser')    return doc

定义了一个名为topic_page_authentication的函数,它以URL作为参数。

以下是代码的分解:

1. topics_url = url:此行将提供的URL分配给变量topics_url。此URL表示我们要验证和检索其内容的网页。

2. response = requests.get(topics_url):此行使用requests.get()函数发送HTTP GET请求到topics_url并将响应存储在response变量中。此请求用于获取网页的HTML内容。

3. page_content = response.text:此行从响应对象中提取HTML内容,并将其分配给page_content变量。 response.text属性检索响应的文本内容。

4. doc = BeautifulSoup(page_content, 'html.parser')
此行使用'html.parser'解析器解析page_content,从而创建一个可导航的对象,代表网页的HTML结构,从而创建一个名为doc的BeautifulSoup对象。

5. return doc:此行从函数返回BeautifulSoup对象doc。这意味着当调用topic_page_authentication函数时,它将返回解析的HTML内容作为BeautifulSoup对象。

此函数的目的是验证和检索由提供的URL指定的网页的HTML内容。它使用requests库发送HTTP GET请求检索响应内容,然后使用BeautifulSoup解析它以创建可导航对象,表示网页的HTML结构。

请注意,提供的代码片段处理网页身份验证和解析的初始步骤,但不执行任何特定的抓取或数据提取任务。

def topicSraper(doc):        # Extract title     title_class = 'f3 lh-condensed mb-0 mt-1 Link--primary'    topic_title_tags = doc.find_all('p', {'class':title_class})    # Extract description    description_class = 'f5 color-fg-muted mb-0 mt-1'    topic_desc_tags = doc.find_all('p', {'class':description_class})    # Extract link    link_class = 'no-underline flex-1 d-flex flex-column'    topic_link_tags = doc.find_all('a',{'class':link_class})    #Extract all the topic names    topic_titles = []    for tag in topic_title_tags:        topic_titles.append(tag.text)    #Extract the descrition text of the particular topic    topic_description = []    for tag in topic_desc_tags:        topic_description.append(tag.text.strip())    #Extract the urls of the particular topics    topic_urls = []    base_url = "https://github.com"    for tags in topic_link_tags:        topic_urls.append(base_url + tags['href'])    topics_dict = {    'Title':topic_titles,    'Description':topic_description,    'URL':topic_urls    }    topics_df = pd.DataFrame(topics_dict)    return topics_df

定义了一个名为 topicScraper 的函数,该函数以一个 BeautifulSoup 对象 (doc) 作为参数。

在 ChatGPT + Conversational UX + Dialogflow 中获得认证

以下是代码的详细说明:

1. title_class = 'f3 lh-condensed mb-0 mt-1 Link--primary': 此行定义了包含网页上主题标题的 HTML 元素的 CSS 类名称 (title_class)。

2. topic_title_tags = doc.find_all('p', {'class':title_class}): 此行使用 BeautifulSoup 对象的 find_all() 方法查找所有具有指定 CSS 类 (title_class) 的 HTML 元素 (<p>)。 它检索一个表示主题标题标签的 BeautifulSoup 标记对象列表。

3. description_class = 'f5 color-fg-muted mb-0 mt-1': 此行定义了包含网页上主题描述的 HTML 元素的 CSS 类名称 (description_class)。

4. topic_desc_tags = doc.find_all('p', {'class':description_class}): 此行使用 find_all() 方法查找所有具有指定 CSS 类 (description_class) 的 HTML 元素 (<p>)。 它检索一个表示主题描述标记的 BeautifulSoup 标记对象列表。

5. link_class = 'no-underline flex-1 d-flex flex-column': 此行定义了包含网页上主题链接的 HTML 元素的 CSS 类名称 (link_class)。

6. topic_link_tags = doc.find_all('a',{'class':link_class}): 此行使用 find_all() 方法查找所有具有指定 CSS 类 (link_class) 的 HTML 元素 (<a>)。 它检索一个表示主题链接标记的 BeautifulSoup 标记对象列表。

7. topic_titles = []: 此行初始化一个空列表,以存储提取的主题标题。

8. for tag in topic_title_tags: ...: 此循环遍历 topic_title_tags 列表,并将每个标记的文本内容附加到 topic_titles 列表中。

9. topic_description = []: 此行初始化一个空列表,以存储提取的主题描述。

10. for tag in topic_desc_tags: ...: 此循环遍历 topic_desc_tags 列表,并将每个标记的去除空格的文本内容附加到 topic_description 列表中。

11. topic_urls = []: 此行初始化一个空列表,以存储提取的主题 URL。

12. base_url = "https://github.com": 此行定义了网站的基本 URL。

13. for tags in topic_link_tags: ...: 此循环遍历 topic_link_tags 列表,并将每个标记的 URL (基本 URL + href 属性) 连接到 topic_urls 列表中。

14. topics_dict = {...}: 此块创建了一个包含提取数据的字典 (topics_dict): 主题标题、描述和 URL。

15. topics_df = pd.DataFrame(topics_dict): 此行将 topics_dict 字典转换为 pandas DataFrame,其中每个键都成为 DataFrame 中的一列。

16. return topics_df: 此行返回包含提取数据的 pandas DataFrame。

该函数的目的是从提供的BeautifulSoup对象(doc)中抓取和提取信息。它从网页上特定的HTML元素中检索主题标题、描述和URL,并将它们存储在一个pandas数据框中,以便进行进一步的分析或处理。

def topic_url_extractor(dataframe):        url_lst = []    for i in range(len(dataframe)):        topic_url = dataframe['URL'][i]        url_lst.append(topic_url)    return url_lst

定义了一个名为topic_url_extractor的函数,该函数将panda DataFrame(dataframe)作为参数。

以下是代码的详细说明:

1. url_lst = []:该行初始化一个空列表(url_lst),用于存储提取的URL。

2. for i in range(len(dataframe)): ...:该循环遍历DataFrame行的索引。

3. topic_url = dataframe['URL'][i]:此行检索数据框中当前行索引(i)的“URL”列的值。

4. url_lst.append(topic_url):此行将检索到的URL添加到url_lst列表中。

5. return url_lst:此行返回包含提取的URL的url_lst列表。

该函数的目的是从提供的DataFrame的“URL”列中提取URL。

它遍历DataFrame的每一行,检索每一行的URL值,并将其添加到一个列表中。最后,该函数返回提取的URL列表。

当您想要从DataFrame中提取URL进行进一步的处理或分析(如访问每个URL或对各个网页执行其他Web抓取)时,此函数可能非常有用。

def parse_star_count(stars_str):        stars_str = stars_str.strip()[6:]    if stars_str[-1] == 'k':        stars_str =  float(stars_str[:-1]) * 1000    return int(stars_str)

定义了一个名为parse_star_count的函数,该函数将字符串(stars_str)作为参数。

以下是代码的详细说明:

1. stars_str = stars_str.strip()[6:]:此行使用strip()方法从stars_str字符串中删除前导和尾随空格。然后从第6个字符开始切片该字符串,并将结果分配回stars_str。此行的目的是删除字符串中的任何不需要的字符或空格。

2. if stars_str[-1] == 'k': ...:此行检查stars_str的最后一个字符是否为“k”,表示星级计数以千为单位。

3. stars_str = float(stars_str[:-1]) * 1000:此行将字符串的数字部分(不包括“k”)转换为浮点数,然后乘以1000将其转换为实际的星级计数。

4. return int(stars_str):此行将stars_str转换为整数并返回它。

该函数的目的是将星级计数从字符串表示形式解析并转换为整数值。它处理星级计数以千为单位(“k”)的情况,通过将字符串的数字部分乘以1000来处理。该函数将解析的星级计数作为整数返回。

当您有以字符串表示的星级计数(例如“1.2k”表示1200颗星),并且需要将它们转换为数字值以进行进一步的分析或处理时,此函数可能非常有用。

def get_repo_info(h3_tags, star_tag):    base_url = 'https://github.com'    a_tags = h3_tags.find_all('a')    username = a_tags[0].text.strip()    repo_name = a_tags[1].text.strip()    repo_url = base_url + a_tags[1]['href']    stars = parse_star_count(star_tag.text.strip())    return username, repo_name, stars, repo_url

定义了一个名为get_repo_info的函数,该函数接受两个参数:h3_tagsstar_tag

以下是代码的详细说明:

1. base_url = 'https://github.com':该行定义了GitHub网站的基本URL。

2. a_tags = h3_tags.find_all('a'):该行使用h3_tags对象的find_all()方法查找其中的所有HTML元素(<a>),并检索代表锚链接的BeautifulSoup标记对象的列表。

3. username = a_tags[0].text.strip():该行提取第一个锚链接标记(a_tags[0])的文本内容并将其分配给username变量。它还使用strip()方法删除任何前导或尾随空格。

4. repo_name = a_tags[1].text.strip():该行提取第二个锚链接标记(a_tags[1])的文本内容并将其分配给repo_name变量。它还使用strip()方法删除任何前导或尾随空格。

5. repo_url = base_url + a_tags[1]['href']:该行从第二个锚链接标记(a_tags[1])检索“href”属性的值,并将其与base_url连接起来形成存储库的完整URL。生成的URL分配给repo_url变量。

6. stars = parse_star_count(star_tag.text.strip())
该行提取star_tag对象的文本内容,删除任何前导或尾随空格,并将其作为参数传递给parse_star_count函数。该函数返回解析后的星级数量作为整数,分配给stars变量。

7. return username, repo_name, stars, repo_url:该行返回一个包含提取信息的元组:usernamerepo_namestarsrepo_url

该函数的目的是从提供的h3_tagsstar_tag对象中提取有关GitHub存储库的信息。它通过浏览和提取HTML结构中的特定元素来检索用户名、存储库名称、星级计数和存储库URL。然后,该函数将此信息作为元组返回。

当您想要从包含存储库列表的网页中提取存储库信息时,该函数可能会很有用,例如在爬取GitHub主题时。

def topic_information_scraper(topic_url):    #页面身份验证    topic_doc = topic_page_authentication(topic_url)    #提取名称    h3_class = 'f3 color-fg-muted text-normal lh-condensed'    repo_tags = topic_doc.find_all('h3', {'class':h3_class})    #获取星标签    star_class = 'tooltipped tooltipped-s btn-sm btn BtnGroup-item color-bg-default'    star_tags = topic_doc.find_all('a',{'class':star_class})    #获取主题信息    topic_repos_dict = {    'username': [],    'repo_name': [],    'stars': [],    'repo_url': []    }    for i in range(len(repo_tags)):        repo_info = get_repo_info(repo_tags[i], star_tags[i])        topic_repos_dict['username'].append(repo_info[0])        topic_repos_dict['repo_name'].append(repo_info[1])        topic_repos_dict['stars'].append(repo_info[2])        topic_repos_dict['repo_url'].append(repo_info[3])                    return pd.DataFrame(topic_repos_dict)

定义了一个名为topic_information_scraper的函数,该函数以topic_url作为参数。

以下是代码的详细说明:

1. topic_doc = topic_page_authentication(topic_url)
该行调用topic_page_authentication函数以验证并检索topic_url的HTML内容。解析的HTML内容分配给topic_doc变量。

2. h3_class = 'f3 color-fg-muted text-normal lh-condensed' :这行定义了 CSS 类名(h3_class),用于包含主题页面中存储库名称的 HTML 元素。

3. repo_tags = topic_doc.find_all('h3', {'class':h3_class}):这一行使用 topic_doc 对象的 find_all() 方法查找具有指定 CSS 类(h3_class)的所有 HTML 元素(<h3>),并检索代表存储库名称标记的 BeautifulSoup 标记对象列表。

4. star_class = 'tooltipped tooltipped-s btn-sm btn BtnGroup-item color-bg-default' :这行定义了 CSS 类名(star_class),用于包含主题页面中的星标计数的 HTML 元素。

5. star_tags = topic_doc.find_all('a',{'class':star_class}):这一行使用 find_all() 方法查找具有指定 CSS 类(star_class)的所有 HTML 元素(<a>),并检索代表星标计数标记的 BeautifulSoup 标记对象列表。

6. topic_repos_dict = {...} :此块创建了一个字典(topic_repos_dict),用于存储提取的存储库信息:用户名、存储库名称、星标计数和存储库 URL。

7. for i in range(len(repo_tags)): ... :此循环遍历 repo_tags 列表的索引,假设它与 star_tags 列表具有相同的长度。

8. repo_info = get_repo_info(repo_tags[i], star_tags[i]) :此行调用 get_repo_info 函数,以提取有关特定存储库的信息。它将当前的存储库名称标记(repo_tags[i])和星标计数标记(star_tags[i])作为参数。返回的信息分配给 repo_info 变量。

9. topic_repos_dict['username'].append(repo_info[0]) :此行将从 repo_info 中提取的用户名附加到 topic_repos_dict 中的“用户名”列表中。

10. topic_repos_dict['repo_name'].append(repo_info[1]) :此行将从 repo_info 中提取的存储库名称 repo_info 附加到 topic_repos_dict 中的“repo_name”列表中。

11. topic_repos_dict['stars'].append(repo_info[2])
此行将从 repo_info 中提取的星标计数 repo_info 附加到 topic_repos_dict 中的“stars”列表中。

12. topic_repos_dict['repo_url'].append(repo_info[3]) :此行将从 repo_info 中提取的存储库 URL 附加到 topic_repos_dict 中的“repo_url”列表中。

13. return pd.DataFrame(topic_repos_dict) :此行将 topic_repos_dict 字典转换为 pandas DataFrame,其中每个键成为 DataFrame 中的一列。生成的数据框包含提取的存储库信息。

此函数的目的是在 GitHub 上特定主题内抓取和提取存储库信息。它验证并检索主题页面的 HTML 内容,然后使用特定的 CSS 类名称提取存储库名称和星标计数。

它为每个存储库调用 get_repo_info 函数,以检索用户名、存储库名称、星标计数和存储库 URL。

提取的信息存储在字典中,然后转换为 pandas DataFrame,并由该函数返回。

if __name__ == "__main__":    url = 'https://github.com/topics'    topic_dataframe = topicSraper(topic_page_authentication(url))    topic_dataframe.to_csv('GitHubtopics.csv', index=None)    # 根据主题创建其他 CSV 文件    url = topic_url_extractor(topic_dataframe)     name = topic_dataframe['Title']    for i in range(len(topic_dataframe)):        new_df = topic_information_scraper(url[i])        new_df.to_csv(f'GitHubTopic_CSV-Files/{name[i]}.csv', index=None)

代码段展示了脚本的主要执行流程。

以下是代码的详细说明:

1. if __name__ == "__main__": :这个条件语句检查脚本是否直接运行(而不是作为模块导入)。

2. url = 'https://github.com/topics' :这一行定义了GitHub主题页面的URL。

3. topic_dataframe = topicSraper(topic_page_authentication(url)) :这一行使用 topic_page_authentication 检索主题页面的HTML内容,然后将解析的HTML(doc)传递给topicSraper 函数。它将结果数据帧(topic_dataframe)分配给一个变量。

4. topic_dataframe.to_csv('GitHubtopics.csv', index=None) :这一行将topic_dataframe数据帧导出到名为“GitHubtopics.csv”的CSV文件中。参数index=None确保不包括行索引。

5. url = topic_url_extractor(topic_dataframe) :这一行调用topic_url_extractor函数,将topic_dataframe作为参数传递。它检索从数据帧中提取的URL列表(url)。

6. name = topic_dataframe['Title'] :这一行从topic_dataframe中检索“Title”列,并将其分配给变量name

7. for i in range(len(topic_dataframe)): ... :此循环遍历topic_dataframe数据帧的索引。

8. new_df = topic_information_scraper(url[i]) :这一行调用topic_information_scraper函数,将URL(url[i])作为参数传递。它检索特定主题URL的存储库信息,并将其分配给new_df数据帧。

9. new_df.to_csv(f'GitHubTopic_CSV-Files/{name[i]}.csv', index=None) :这一行将new_df数据帧导出到CSV文件中。文件名使用f-string动态生成,包含主题名称(name[i])。参数index=None确保不包括行索引。

该脚本的目的是从GitHub主题页面中抓取和提取信息,并创建包含提取数据的CSV文件。它首先抓取主题页面,将提取的信息保存在“GitHubtopics.csv”中,然后继续使用提取的URL抓取单个主题页面。

对于每个主题,它创建一个名为该主题的新CSV文件,并在其中保存存储库信息。

可以直接执行此脚本以执行抓取并生成所需的CSV文件。

最终输出

url = 'https://github.com/topics'topic_dataframe = topicSraper(topic_page_authentication(url))topic_dataframe.to_csv('GitHubtopics.csv', index=None)

一旦运行此代码,它将生成一个名为“GitHubtopics.csv”的CSV文件,该文件看起来像这样,并且该CSV文件涵盖所有主题名称,其描述和URL。

GitHubtopics.csv
url = topic_url_extractor(topic_dataframe) name = topic_dataframe['Title']for i in range(len(topic_dataframe)):    new_df = topic_information_scraper(url[i])    new_df.to_csv(f'GitHubTopic_CSV-Files/{name[i]}.csv', index=None)

然后,此代码将执行,基于我们在之前的“GitHubtopics.csv”文件中保存的主题创建特定的csv文件。然后将这些CSV文件保存在名为“GitHubTopic_CSV-Files”的目录中,每个文件都有自己特定的主题名称。这些CSV文件看起来像这样。

GitHubTopcis_CSV-Files

这些主题csv文件存储了有关主题的一些信息,例如他们的用户名、仓库名称、仓库的星级和仓库的URL。

3D.csv

注意:网站的标签可能会更改,因此在运行此Python脚本之前,请根据网站检查标签。

完整脚本访问 >> https://github.com/PrajjwalSule21/GitHub-Topic-Scraper/blob/main/RepoScraper.py

Chatathon by Chatbot Conference
Leave a Reply

Your email address will not be published. Required fields are marked *