最近看到tutorials.jenkov.com/java-nio 的java-nio教程比较优质。在网站上找了下居然没有pdf下载的连接。该网站又在外网,需要挂代理才能访问,因此产生了自己抓取资源制作电子书想法。
主要思路
查看了下网页结构主要是获取左侧教程目录每一个文章的链接,抓取其中的网页内容转成pdf即可。这种事当然不能通过手工来做,技术上的思路:
主要是通过Python的Requests库抓取网页文本信息,利用BeautifulSoup提取所需的部分最后利用PDFKit由html生成pdf电子书即可。
最后生成的效果是一个带有书签的pdf电子书:
全部代码与遇到的坑
- 其中第一需要对抓取的资源部分不需要的部分将其中的css改成display:none
- pdfkit依赖wkhtmltopdf,需要本机安装wkhtmlpdf软件(如果你是ubuntu跟我一样apt install wkhtmlpdf即可)
- 需要对生成电子书的书签、水印样式有需求,通过给pdfkit设置相关参数即可。可以参考wkhtmltopdf.org/usage/wkhtm…
- 解决html转pdf文章文字、表格断页问题。采用网上的page-break-before等样式未完美解决。
- 此代码主要针对的是tutorials.jenkov.com/java-nio/ ,聪明的你如果有python基础相信很快能举一反三抓取互联网其他资源生成电子书。
import requests
import pdfkit
from bs4 import BeautifulSoup
options = {
'page-size': 'Letter',
'margin-top': '5mm',
'margin-bottom': '20mm',
'encoding': "UTF-8",
'no-outline': None,
'outline-depth': 10,
'header-right': "本资源由www.codehome.vip从互联网采集而来",
'header-font-size':8,
'outline-depth':5,
'outline':''
}
def dealHtml(url):
print(url)
r = requests.get(url)
html = r.text
html = html.replace("</head>", '''</head><style> * {
page-break-inside: avoid!important;
page-break-after: avoid!important;
page-break-before: avoid!important;
}
html, body ,pre,table, img, blockquote{
overflow-x: hidden;
page-break-inside: avoid!important;
page-break-after: avoid!important;
page-break-before: avoid!important;
}
</style>''')
html = html.replace("#bottomNavBar2Parent{", "#bottomNavBar2Parent{display:none;")
html=html.replace("#lastUpdate{","#lastUpdate{display:none;")
html = html.replace("#bottomSocial{", "#bottomSocial{display:none;")
html = html.replace('img src="/images/', 'img src="http://tutorials.jenkov.com/images/')
html=html.replace('class="codeBox"','class="codeBox" style="overflow:hidden; display: inline-block;page-break-inside: avoid!important;page-break-after: avoid!important;page-break-before: avoid!important;" ')
html=html.replace('.topBar, .footer {','.topBar, .footer {display:none;')
return html
website = "http://tutorials.jenkov.com"
r = requests.get("http://tutorials.jenkov.com/java-nio/index.html")
soup = BeautifulSoup(r.content, "lxml")
hreflist = []
hrefs = soup.select("#trailToc > ol > li > a")
allbook=""
for href in hrefs:
newHref = website + href['href']
hreflist.append(newHref)
allbook=allbook+dealHtml(newHref)
try:
pdfkit.from_string(allbook,"java-nio.pdf", options=options)
except:
pass
如果你想获得此电子书,微信关注公众号:程序员众推 后台发送nioo即可。