#!/usr/bin/env python # -*- coding: utf-8 -*- __license__ = 'GPL v3' __copyright__ = 'Chris Moore 2025' __version__ = '1.0' import os from calibre import walk from calibre.ptempfile import PersistentTemporaryFile from calibre.utils.zipfile import ZipFile from calibre.web.feeds.news import BasicNewsRecipe class lwn_epub(BasicNewsRecipe): __author__ = 'Chris Moore' title = 'lwn' language = 'en' publisher = 'lwn.net' publication_type = 'magazine' description = 'The weekly subscriber-only edition from Linux Weekly News' needs_subscription = True conversion_options = { 'publisher': publisher, 'language': language, 'comments': description, 'no_default_epub_cover': True, 'preserve_cover_aspect_ratio': True } def build_index(self): browser = self.get_browser() browser.open('https://lwn.net/current') # find the link epublink = browser.find_link(text='Download EPUB') # download ebook self.report_progress(0, _('Downloading ePUB')) response = browser.follow_link(epublink) book_file = PersistentTemporaryFile(suffix='.epub') book_file.write(response.read()) book_file.close() # convert self.report_progress(0.2, _('Converting to OEB')) oeb = self.output_dir + '/INPUT/' if not os.path.exists(oeb): os.makedirs(oeb) with ZipFile(book_file.name) as f: f.extractall(path=oeb) for f in walk(oeb): if f.endswith('.opf'): return f def get_browser(self): br = BasicNewsRecipe.get_browser(self) if self.username is not None and self.password is not None: br.open('https://lwn.net/login') br.select_form(name='loginform') br['uname'] = self.username br['pword'] = self.password br.submit() return br