使用Python和FastAPI构建网站爬虫:Oncolo医疗文章抓取实战

使用Python和FastAPI构建网站爬虫:Oncolo医疗文章抓取实战

    • 前言
    • 项目概述
    • 技术栈
    • 代码分析
      • 1. 导入必要的库
      • 2. 初始化FastAPI应用
      • 3. 定义请求模型
      • 4. 核心爬虫功能
        • 4.1 URL验证和准备
        • 4.2 设置HTTP请求
        • 4.3 发送请求和解析HTML
        • 4.4 提取文章内容
        • 4.5 保存结果和返回数据
      • 5. API端点定义
      • 6. 启动服务器
    • 爬虫技术要点分析
      • 1. 请求头和会话管理
      • 2. 重试机制
      • 3. HTML解析技巧
      • 4. 递归内容提取
      • 5. 错误处理和异常管理
    • 爬虫开发的最佳实践
    • 改进建议
    • 总结
    • 注意事项

前言

在数据分析和信息收集的时代,网络爬虫技术已成为获取互联网数据的重要手段。本文将通过分析一个实际的爬虫项目,帮助大家了解如何使用Python构建一个功能完善的网站爬虫API,特别是针对医疗类网站的内容抓取。

项目概述

这个项目是一个基于FastAPI的Web服务,专门用于抓取日本医疗网站Oncolo的文章内容。该API可以接收文章URL,然后抓取并解析文章的各个部分,包括标题、副标题、发布日期、正文内容、标签和作者信息等,最后将结果保存为文本文件并返回JSON格式的响应。

技术栈

  • Python:编程语言
  • FastAPI:构建API服务
  • BeautifulSoup:HTML解析
  • Requests:HTTP请求处理
  • Pydantic:数据验证

代码分析

1. 导入必要的库

import requests
from bs4 import BeautifulSoup
import os
import time
import re
from fastapi import FastAPI, HTTPException
from pydantic import BaseModel
from typing import Optionalfrom bs4.element import NavigableString, Tag
from requests.adapters import HTTPAdapter
from requests.packages.urllib3.util.retry import Retry
from requests.packages.urllib3.exceptions import InsecureRequestWarning

这部分导入了项目所需的所有库,包括HTTP请求、HTML解析、文件操作和API构建等功能模块。

2. 初始化FastAPI应用

# 安全でないリクエストの警告を無効化
requests.packages.urllib3.disable_warnings(InsecureRequestWarning)app = FastAPI(title="Oncoloの記事スクレイピングAPI", description="Oncoloウェブサイトの記事内容をスクレイピングするAPI")

这里初始化了FastAPI应用,并禁用了不安全请求的警告(因为代码中使用了verify=False选项)。

3. 定义请求模型

class ScrapeRequest(BaseModel):url: str

使用Pydantic定义了一个简单的请求模型,只包含一个URL字段。

4. 核心爬虫功能

scrape_oncolo_article函数是整个项目的核心,它完成了以下任务:

4.1 URL验证和准备
def scrape_oncolo_article(url: str):# URL验证if not url.startswith('https://oncolo.jp/news/'):raise ValueError("URLはoncolo.jp/news/形式である必要があります")# 从URL提取文件名file_id = url.split('/news/')[1]output_filename = f"{file_id}.txt"

这部分代码验证URL是否符合要求的格式,并从URL中提取文章ID作为保存文件的名称。

4.2 设置HTTP请求
    # HTTP请求头设置headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36','Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8','Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8','Connection': 'keep-alive','Upgrade-Insecure-Requests': '1',}# 创建会话对象session = requests.Session()# 设置重试策略retry_strategy = Retry(total=5,backoff_factor=1,status_forcelist=[429, 500, 502, 503, 504],)adapter = HTTPAdapter(max_retries=retry_strategy)session.mount("https://", adapter)session.mount("http://", adapter)

这部分代码设置了HTTP请求头,创建了一个会话对象,并配置了重试策略。这是爬虫开发中的重要步骤,因为:

  1. 自定义User-Agent可以模拟浏览器行为,避免被网站识别为爬虫
  2. 设置重试策略可以处理临时网络问题和服务器错误
  3. 使用会话对象可以在多次请求之间保持Cookie等状态
4.3 发送请求和解析HTML
    try:# 禁用SSL验证response = session.get(url, headers=headers, verify=False, timeout=30)response.raise_for_status()  # 如果请求失败则抛出异常# 使用BeautifulSoup解析HTMLsoup = BeautifulSoup(response.text, 'html.parser')

这部分代码发送HTTP请求并使用BeautifulSoup解析返回的HTML内容。注意这里禁用了SSL验证(verify=False),这在开发阶段可能有用,但在生产环境中应该避免。

4.4 提取文章内容

代码使用BeautifulSoup的选择器功能,根据网站的HTML结构提取各种信息:

  • 主标题和副标题
  • 发布日期和更新日期
  • 文章正文内容
  • 标签信息
  • 作者信息和简介

例如,提取标题的代码:

# 提取标题和副标题
h1_element = main_section.find('h1')
main_title = ""
subtitle = ""if h1_element:subtitle_element = h1_element.find('span', class_='subtitle')if subtitle_element:subtitle = subtitle_element.get_text(strip=True)# 创建h1的副本以避免修改原始souptitle_copy = BeautifulSoup(str(h1_element), 'html.parser').h1subtitle_in_copy = title_copy.find('span', class_='subtitle')if subtitle_in_copy:subtitle_in_copy.decompose()  # 从副本中删除副标题元素main_title = title_copy.get_text(strip=True)else:main_title = h1_element.get_text(strip=True)
4.5 保存结果和返回数据
# 保存为纯文本文件
output_path = os.path.join('scraped_data', output_filename)
with open(output_path, 'w', encoding='utf-8') as f:f.write(f"メインタイトル: {main_title}\n")f.write(f"サブタイトル: {subtitle}\n")# ...其他内容...# 返回包含所有内容的响应
return {"success": True,"message": f"記事は {output_path} に保存されました","filename": output_filename,"title": main_title,# ...其他字段...
}

这部分代码将提取的内容保存到文本文件中,并返回一个包含所有数据的JSON响应。

5. API端点定义

@app.post("/scrape/", summary="Oncolo記事のスクレイピング", description="oncolo.jpの記事URLを提供し、コンテンツをスクレイピングして保存します")
async def scrape_article(request: ScrapeRequest):try:result = scrape_oncolo_article(request.url)return resultexcept ValueError as e:raise HTTPException(status_code=400, detail=str(e))except HTTPException as e:raise eexcept Exception as e:raise HTTPException(status_code=500, detail=f"サーバーエラー: {str(e)}")@app.get("/", summary="APIルートパス", description="APIの基本情報を返します")
async def root():return {"message": "Oncolo記事スクレイピングAPIへようこそ", "usage": "/scrape/エンドポイントにPOSTリクエストを送信し、oncolo.jpの記事URLを提供してください"}

这部分代码定义了两个API端点:

  • /scrape/:接收POST请求,包含要抓取的URL
  • /:根路径,返回API的基本信息

6. 启动服务器

if __name__ == "__main__":import uvicornuvicorn.run(app, host="0.0.0.0", port=8000)

这部分代码使用uvicorn启动FastAPI服务器,监听所有网络接口的8000端口。

爬虫技术要点分析

1. 请求头和会话管理

headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36',# ...其他头信息...
}
session = requests.Session()

要点

  • 设置User-Agent模拟真实浏览器,避免被网站拦截
  • 使用Session对象维护会话状态,提高效率并保持登录状态

2. 重试机制

retry_strategy = Retry(total=5,backoff_factor=1,status_forcelist=[429, 500, 502, 503, 504],
)
adapter = HTTPAdapter(max_retries=retry_strategy)
session.mount("https://", adapter)

要点

  • 实现自动重试机制,处理临时网络问题
  • 使用指数退避策略(backoff_factor)避免频繁请求
  • 针对特定HTTP错误码(如429太多请求、500服务器错误等)进行重试

3. HTML解析技巧

soup = BeautifulSoup(response.text, 'html.parser')
main_section = soup.find('section', class_='main')

要点

  • 使用BeautifulSoup进行HTML解析,比正则表达式更可靠
  • 根据HTML结构和CSS选择器定位元素
  • 处理复杂的嵌套结构和不同类型的内容

4. 递归内容提取

for content in content_div.contents:if isinstance(content, NavigableString):# 处理文本节点elif isinstance(content, Tag):# 处理标签节点# 递归处理子节点

要点

  • 区分处理文本节点和标签节点
  • 递归遍历复杂的DOM结构
  • 保持原始格式和链接信息

5. 错误处理和异常管理

try:# 爬虫代码
except requests.exceptions.RequestException as e:raise HTTPException(status_code=500, detail=f"リクエストエラー: {str(e)}")
except Exception as e:raise HTTPException(status_code=500, detail=f"処理エラー: {str(e)}")

要点

  • 区分不同类型的异常(请求错误、解析错误等)
  • 提供有意义的错误信息
  • 将内部错误转换为适当的HTTP状态码

爬虫开发的最佳实践

  1. 尊重robots.txt:虽然本例中没有显示,但在实际开发中应该检查目标网站的robots.txt文件,遵守其访问规则。

  2. 控制请求频率:使用time.sleep()或更复杂的限速机制,避免对目标服务器造成过大负担。

  3. 异常处理:全面的异常处理确保爬虫能够稳定运行,即使遇到意外情况。

  4. 模块化设计:将爬虫功能拆分为多个模块,如请求发送、内容解析、数据存储等,便于维护和扩展。

  5. 数据验证:使用Pydantic等工具验证输入和输出数据,确保数据的完整性和一致性。

改进建议

  1. 添加请求延迟:在代码中添加time.sleep(),控制请求频率,避免被目标网站封禁。

  2. 启用SSL验证:在生产环境中应启用SSL验证(删除verify=False),提高安全性。

  3. 使用代理池:对于大规模爬虫,可以实现代理IP轮换机制,避免IP被封。

  4. 添加日志系统:记录爬虫运行状态和错误信息,便于调试和监控。

  5. 实现增量爬取:检查已爬取的内容,只抓取新内容,提高效率。

总结

这个项目展示了如何使用Python构建一个功能完善的网站爬虫API,涵盖了HTTP请求、HTML解析、内容提取、数据存储和API服务等多个方面。通过分析这个实例,我们可以学习到网络爬虫开发的核心技术和最佳实践。

爬虫开发是一个需要不断学习和适应的过程,因为网站结构经常变化,反爬虫技术也在不断升级。希望这篇文章能够帮助你理解爬虫开发的基本原理和技术要点,为你的爬虫项目提供参考。

注意事项

在使用爬虫技术时,请务必遵守以下原则:

  1. 遵守网站的robots.txt规则和使用条款
  2. 控制爬取频率,不对目标网站造成过大负担
  3. 尊重版权,不将抓取的内容用于商业用途(除非得到授权)
  4. 保护个人隐私数据,不抓取和存储敏感信息

只有合法、合理地使用爬虫技术,才能发挥其真正的价值,并避免不必要的法律风险。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/80568.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

YoloV8改进策略:卷积篇|风车卷积|即插即用

文章目录 论文信息论文翻译摘要引言相关研究红外搜索与跟踪检测和分割网络红外搜索与跟踪数据集的损失函数红外搜索与跟踪数据集方法风车形卷积(PConv)基于尺度的动态损失SIRST - UAVB数据集实验实验设置与其他方法的比较多模型上的消融实验结论致谢代码改进方法测试结果总结…

【NLP】36. 从指令微调到人类偏好:构建更有用的大语言模型

从指令微调到人类偏好:构建更有用的大语言模型 大语言模型(LLMs)已经成为现代自然语言处理系统的核心,但单纯依赖传统语言建模目标,往往难以满足实际应用的“人类意图”。从 Instruction Tuning(指令微调&…

基于Transformers与深度学习的微博评论情感分析及AI自动回复系统

前言 这个项目存在cookie没有自动更新问题,后续可能会发出来解决教程,还有微博网页版的话最多看到300条评论,而且回复别人信息的话最多回复15条就要休息5分钟左右才能评论 1. 项目概述 本项目实现了一个微博评论自动化处理系统&#xff0c…

详解 Zephyr RTOS:架构、功能与开发指南

目录 Zephyr RTOS 的核心特性 1. 轻量级和可扩展性 2. 实时性能 3. 多平台支持 4. 安全性 5. 社区和生态系统 Zephyr 的架构 1. 内核 2. 驱动模型 3. 网络栈 4. 文件系统 开发环境和工具链 安装和配置 开发流程 1. 应用程序开发 2. 调试和测试 3. 部署 实际应…

人工智能重塑医疗健康:从辅助诊断到个性化治疗的全方位变革

人工智能正在以前所未有的速度改变着医疗健康领域,从影像诊断到药物研发,从医院管理到远程医疗,AI 技术已渗透到医疗服务的各个环节。本文将深入探讨人工智能如何赋能医疗健康产业,分析其在医学影像、临床决策、药物研发、个性化医…

Linux笔记---内核态与用户态

用户态(User Mode) 权限级别:较低,限制应用程序直接访问硬件或关键系统资源。 适用场景:普通应用程序的运行环境。 限制:无法执行特权指令(如操作I/O端口、修改内存管理单元配置等&#xff09…

Spring 代理与 Redis 分布式锁冲突:一次锁释放异常的分析与解决

Spring 代理与 Redis 分布式锁冲突:一次锁释放异常的分析与解决 Spring 代理与 Redis 分布式锁冲突:一次锁释放异常的分析与解决1. 问题现象与初步分析2 . 原因探究:代理机制对分布式锁生命周期的干扰3. 问题复现伪代码4. 解决方案&#xff1…

SQL:多列匹配(Multiple-column Matching)

目录 基础概念 应用场景详解 1. 多列等值匹配 2. 多列 IN 匹配(集合匹配) 3. 多列 JOIN 匹配(复合键连接) 4. 多列匹配 子查询 5. 多列匹配 EXISTS 6. 多列匹配 UNION(组合数据源) 7. 多列匹配…

基于DeepSeek的智能客服系统实践与创新

引言:AI大模型重塑客户服务新范式 近年来,AI大模型技术的突破性进展正在深刻改变传统客户服务模式。作为国内领先的AI企业,DeepSeek凭借其创新的算法架构(如MoE混合专家模型、动态学习率调度器)和极致的成本效益(仅为同类模型成本的1/20),在自然语言理解、情感分析、多…

SGLang和vllm比有什么优势?

环境: SGLang vllm 问题描述: SGLang和vllm比有什么优势? 解决方案: SGLang和vLLM都是在大语言模型(LLM)推理和部署领域的开源项目或框架,它们各自有不同的设计目标和优势。下面我综合目前…

三、Hive DDL数据库操作

在 Apache Hive 中,数据库 (Database),有时也被称为模式 (Schema),是组织和管理 表及其他对象的基本命名空间单元。熟练掌握数据库层面的数据定义语言 (DDL) 操作,是构建清晰、有序的 Hive 数据仓库的第一步。本篇笔记将详细梳理 …

Redis(2):Redis + Lua为什么可以实现原子性

Redis 作为一款高性能的键值对存储数据库,与 Lua 脚本相结合,为实现原子性操作提供了强大的解决方案,本文将深入探讨 Redis Lua 实现原子性的相关知识 原子性概念的厘清 在探讨 Redis Lua 的原子性之前,我们需要明确原子性的概念…

科普:极简的AI乱战江湖

本文无图。 大模型 ‌2022年2月,‌文生图应用的鼻祖Midjourney上线。 ‌2022年8月,‌开源版的Midjourney,也就是Stable Diffusion上线。 2022年11月30日‌,OpenAI正式发布ChatGPT-3.5。 此后,不断有【大模型】面世&…

CSS- 4.5 css + div 布局 简易网易云音乐 官网布置实例

本系列可作为前端学习系列的笔记,代码的运行环境是在HBuilder中,小编会将代码复制下来,大家复制下来就可以练习了,方便大家学习。 HTML系列文章 已经收录在前端专栏,有需要的宝宝们可以点击前端专栏查看! 点…

【滑动窗口】LeetCode 1004题解 | 最大连续1的个数 Ⅲ

最大连续1的个数 Ⅲ 一、题目链接二、题目三、题目解析四、算法原理解法一:暴力枚举 zero计数器解法二:滑动窗口 五、编写代码六、时空复杂度 一、题目链接 最大连续1的个数 Ⅲ 二、题目 三、题目解析 注意题目中说的是最多k次,在一个数组…

PyTorch音频处理技术及应用研究:从特征提取到相似度分析

文章目录 音频处理技术及应用音频处理技术音视频摘要技术音频识别及应用 梅尔频率倒谱系数音频特征尔频率倒谱系数简介及参数提取过程音频处理快速傅里叶变换(FFT)能量谱处理离散余弦转换 练习案例:音频建模加载音频数据源波形变换的类型绘制波形频谱图波形Mu-Law 编…

鸿蒙OSUniApp 实现的语音输入与语音识别功能#三方框架 #Uniapp

UniApp 实现的语音输入与语音识别功能 最近在开发跨平台应用时,客户要求添加语音输入功能以提升用户体验。经过一番调研和实践,我成功在UniApp项目中实现了语音输入与识别功能,现将过程和方法分享出来,希望对有类似需求的开发者有…

2025年卫星遥感行业最新发展趋势深度分析

一、国内发展趋势:政策引领与技术突破双轮驱动 (一)政策体系持续完善,顶层设计深化行业发展 国家级战略与标准体系构建 中国政府将卫星遥感产业纳入“十四五”规划核心战略,明确构建“通导遥”一体化空间基础设施。20…

SIP协议栈--osip源码梳理

文章目录 osiposip主体结构体code main函数 状态机转化结构体code状态转换 sip事务结构体code osip_dialog结构体code 创建并发送200 OK响应 osip_message结构体code osip_eventcode 打印接收到的SIP消息 osip OSIP(Open Source Implementation of SIP)…

Linux之Yum源与Nginx服务篇

1.Yum源知识理论总结概括 Yum源概述 Yum 源 即软件仓库的标识,里面承载着软件包集合 Yum源组成 包含模块 【OS】、【everything】、【EPOL】、【debuginfo】、【source】、【update-source】 【os】:简称operator system 它内部包含操作系统的核心组件&#x…