Exemple #1
0
    def GET(self, id_):
        self.login_required()
        try:
            id_ = int(id_)
        except:
            return "the id is invalid!<br />"

        bk = Book.get_by_id(id_)
        if not bk:
            return "the book(%d) not exist!<br />" % id_

        bkcls = BookClass(bk.title)
        if not bkcls:
            return "the book(%d) not exist!<br />" % id_

        #如果是漫画类,则不管是否选择了“单独推送”,都自动变成“单独推送”
        if issubclass(bkcls, BaseComicBook):
            separate = 'true'
        else:
            separate = web.input().get('separate', 'true')

        if main.session.username not in bk.users:
            bk.users.append(main.session.username)
            bk.separate = bool(separate in ('true', '1'))
            bk.put()
        raise web.seeother('/my')
Exemple #2
0
    def POST(self, mgrType):
        web.header('Content-Type', 'application/json')
        user = self.getcurrentuser()
        id_ = web.input().get('id_')
        try:
            id_ = int(id_)
        except:
            return json.dumps({'status': _('The id is invalid!')})

        bk = Book.get_by_id(id_)
        if not bk:
            return json.dumps({'status': _('The book(%d) not exist!') % id_})

        if mgrType.lower() == 'unsubscribe':
            if user.name in bk.users:
                bk.users.remove(user.name)
                bk.separate = False
                bk.put()

            #为安全起见,退订后也删除网站登陆信息(如果有的话)
            subs_info = user.subscription_info(bk.title)
            if subs_info:
                subs_info.delete()

            return json.dumps({
                'status': 'ok',
                'title': bk.title,
                'desc': bk.description
            })
        elif mgrType.lower() == 'subscribe':
            separate = web.input().get('separate', '')

            respDict = {'status': 'ok'}

            bkcls = BookClass(bk.title)
            if not bkcls:
                return json.dumps({'status': 'The book(%d) not exist!' % id_})

            #如果是漫画类,则不管是否选择了“单独推送”,都自动变成“单独推送”
            if issubclass(bkcls, BaseComicBook):
                separate = 'true'

            if user.name not in bk.users:
                bk.users.append(user.name)
                bk.separate = bool(separate.lower() in ('true', '1'))
                bk.put()

            respDict['title'] = bk.title
            respDict['desc'] = bk.description
            respDict['needs_subscription'] = bk.needs_subscription
            respDict['subscription_info'] = bool(
                user.subscription_info(bk.title))
            respDict['separate'] = bk.separate
            return json.dumps(respDict)
        else:
            return json.dumps({'status': 'unknown command: %s' % mgrType})
Exemple #3
0
    def GET(self):
        username = web.input().get('u')
        id_ = web.input().get('id')  #for debug

        self.queue2push = defaultdict(list)

        books = Book.all()
        if username:  #现在投递【测试使用】,不需要判断时间和星期
            sent = []
            books2push = Book.get_by_id(
                int(id_)) if id_ and id_.isdigit() else None
            books2push = [books2push] if books2push else books
            for book in books2push:
                if not id_ and username not in book.users:
                    continue
                user = KeUser.all().filter("name = ", username).get()
                if user and user.kindle_email:
                    self.queueit(user, book.key().id(), book.separate)
                    sent.append(book.title)
            self.flushqueue()
            if len(sent):
                tips = _("Book(s) (%s) put to queue!") % u', '.join(sent)
            else:
                tips = _("No book to deliver!")
            return self.render('autoback.html', "Delivering", tips=tips)

        #定时cron调用
        sentcnt = 0
        for book in books:
            if not book.users:  #没有用户订阅此书
                continue

            bkcls = None
            if book.builtin:
                bkcls = BookClass(book.title)
                if not bkcls:
                    continue

            #确定此书是否需要下载
            for u in book.users:
                user = KeUser.all().filter("enable_send = ",
                                           True).filter("name = ", u).get()
                if not user or not user.kindle_email:
                    continue

                #先判断当天是否需要推送
                day = local_time('%A', user.timezone)
                usrdays = user.send_days
                if bkcls and bkcls.deliver_days:  #按星期推送
                    days = bkcls.deliver_days
                    if not isinstance(days, list):
                        days = [days]
                    if day not in days:
                        continue
                elif usrdays and day not in usrdays:  #为空也表示每日推送
                    continue

                #时间判断
                h = int(local_time("%H", user.timezone)) + 1
                if h >= 24:
                    h -= 24
                if bkcls and bkcls.deliver_times:
                    times = bkcls.deliver_times
                    if not isinstance(times, list):
                        times = [times]
                    if h not in times:
                        continue
                elif user.send_time != h:
                    continue

                #到了这里才是需要推送的
                self.queueit(user, book.key().id(), book.separate)
                sentcnt += 1
        self.flushqueue()
        return "Put <strong>%d</strong> books to queue!" % sentcnt
Exemple #4
0
 def GET(self):
     bookid = web.input().get("id")
     emails = web.input().get("emails")
     booktype = web.input().get("type", "mobi")
     if not bookid or not emails:
         return "No book to send!<br />"
     try:
         bookid = int(bookid)
     except:
         return "id of book is invalid!<br />"
         
     bk = Book.get_by_id(bookid)
     if not bk:
         return "Title of feeds not exist!<br />"
     
     if bk.builtin:
         book = BookClass(bk.title)
         if not book:
             return "the builtin book not exist!<br />"
         book = book()
     else: # 自定义RSS
         if bk.feedscount == 0:
             return "the book has no feed!<br />"
         book = BaseFeedBook()
         book.title = bk.title
         book.description = bk.description
         book.language = bk.language
         book.keep_image = bk.keep_image
         book.fulltext_by_readability = True
         feeds = bk.feeds
         book.feeds = [(feed.title, feed.url, feed.isfulltext) for feed in feeds]
         book.url_filters = [flt.url for flt in UrlFilter.all()]
     
     emails = emails.split(',')
     
     opts = oeb = None
     
     # 创建 OEB
     global log
     opts = getOpts()
     oeb = CreateOeb(log, None, opts)
     setMetaData(oeb, book.title, book.language, local_time(), SrcEmail)
     oeb.container = ServerContainer(log)
     
     #guide
     mhfile = book.mastheadfile
     if mhfile:
         id, href = oeb.manifest.generate('masthead', mhfile) # size:600*60
         oeb.manifest.add(id, href, MimeFromFilename(mhfile))
         oeb.guide.add('masthead', 'Masthead Image', href)
     
     coverfile = book.coverfile
     if coverfile:
         id, href = oeb.manifest.generate('cover', coverfile)
         item = oeb.manifest.add(id, href, MimeFromFilename(coverfile))
         oeb.guide.add('cover', 'Cover', href)
         oeb.metadata.add('cover', id)
     
     itemcnt = 0
     sections = OrderedDict()
     # 对于html文件,变量名字自文档
     # 对于图片文件,section为图片mime,url为原始链接,title为文件名,content为二进制内容
     for sec_or_media, url, title, content, brief in book.Items():
         if not sec_or_media or not title or not content:
             continue
         
         if sec_or_media.startswith(r'image/'):
             id, href = oeb.manifest.generate(id='img', href=title)
             item = oeb.manifest.add(id, href, sec_or_media, data=content)
         else:
             id, href = oeb.manifest.generate(id='feed', href='feed%d.htm'%itemcnt)
             item = oeb.manifest.add(id, href, 'text/html', data=content)
             oeb.spine.add(item, True)
             sections.setdefault(sec_or_media, [])
             sections[sec_or_media].append((title, item, brief))
             itemcnt += 1
             
     if itemcnt > 0: # 建立TOC,杂志模式需要为两层目录结构
         for sec in sections.keys():
             sectoc = oeb.toc.add(sec, sections[sec][0][1].href)
             for title, a, brief in sections[sec]:
                 sectoc.add(title, a.href, description=brief if brief else None)
         
         #TODO
         oeb.toc.rationalize_play_orders()
         
         oIO = byteStringIO()
         o = EPUBOutput() if booktype == "epub" else MOBIOutput()
         o.convert(oeb, oIO, opts, log)
         self.SendToKindle(emails, book.title, booktype, str(oIO.getvalue()))
         rs = "%s(%s).%s Sent!"%(book.title,local_time(),booktype)
         log.info(rs)
         return rs
     else:
         self.deliverlog(emails, book.title, 0, status='nonews')
         rs = "No new feeds."
         log.info(rs)
         return rs
Exemple #5
0
    def GET(self):
        username = web.input().get("u")
        bookid = web.input().get("id")
        to = web.input().get("to")
        booktype = web.input().get("type", "mobi")
        titlefmt = web.input().get("titlefmt")
        tz = int(web.input().get("tz", TIMEZONE))
        if not bookid or not to:
            return "No book to send!<br />"
        try:
            bookid = int(bookid)
        except:
            return "id of book is invalid!<br />"

        bk = Book.get_by_id(bookid)
        if not bk:
            return "Title of feeds not exist!<br />"

        if bk.builtin:
            book = BookClass(bk.title)
            if not book:
                return "the builtin book not exist!<br />"
            book = book()
            book.url_filters = [flt.url for flt in UrlFilter.all()]
        else:  # 自定义RSS
            if bk.feedscount == 0:
                return "the book has no feed!<br />"
            book = BaseFeedBook()
            book.title = bk.title
            book.description = bk.description
            book.language = bk.language
            book.keep_image = bk.keep_image
            book.oldest_article = bk.oldest_article
            book.fulltext_by_readability = True
            feeds = bk.feeds
            book.feeds = [(feed.title, feed.url, feed.isfulltext) for feed in feeds]
            book.url_filters = [flt.url for flt in UrlFilter.all()]

        opts = oeb = None

        # 创建 OEB
        global log
        opts = getOpts()
        oeb = CreateOeb(log, None, opts)
        title = "%s %s" % (book.title, local_time(titlefmt, tz)) if titlefmt else book.title

        setMetaData(oeb, title, book.language, local_time(tz=tz), SrcEmail)
        oeb.container = ServerContainer(log)

        # guide
        mhfile = book.mastheadfile
        if mhfile:
            id, href = oeb.manifest.generate("masthead", mhfile)  # size:600*60
            oeb.manifest.add(id, href, MimeFromFilename(mhfile))
            oeb.guide.add("masthead", "Masthead Image", href)

        coverfile = book.coverfile
        if coverfile:
            id, href = oeb.manifest.generate("cover", coverfile)
            item = oeb.manifest.add(id, href, MimeFromFilename(coverfile))
            oeb.guide.add("cover", "Cover", href)
            oeb.metadata.add("cover", id)

        itemcnt = 0
        sections = OrderedDict()
        # 对于html文件,变量名字自文档
        # 对于图片文件,section为图片mime,url为原始链接,title为文件名,content为二进制内容
        for sec_or_media, url, title, content, brief in book.Items(opts):
            if not sec_or_media or not title or not content:
                continue

            if sec_or_media.startswith(r"image/"):
                id, href = oeb.manifest.generate(id="img", href=title)
                item = oeb.manifest.add(id, href, sec_or_media, data=content)
            else:
                id, href = oeb.manifest.generate(id="feed", href="feed%d.html" % itemcnt)
                item = oeb.manifest.add(id, href, "application/xhtml+xml", data=content)
                oeb.spine.add(item, True)
                sections.setdefault(sec_or_media, [])
                sections[sec_or_media].append((title, item, brief))
                itemcnt += 1

        if itemcnt > 0:  # 建立TOC,杂志模式需要为两层目录结构
            stoc = ["<html><head><title>Table Of Contents</title></head><body>"]
            for sec in sections.keys():
                stoc.append('<h3><a href="%s">%s</a></h3>' % (sections[sec][0][1].href, sec))
                sectoc = oeb.toc.add(sec, sections[sec][0][1].href)
                for title, a, brief in sections[sec]:
                    stoc.append('&nbsp;&nbsp;&nbsp;&nbsp;<a href="%s">%s</a><br />' % (a.href, title))
                    sectoc.add(title, a.href, description=brief if brief else None)
            stoc.append("</body></html>")
            id, href = oeb.manifest.generate(id="toc", href="toc.html")
            item = oeb.manifest.add(id, href, "application/xhtml+xml", data="".join(stoc))
            oeb.guide.add("toc", "Table of Contents", href)
            oeb.spine.add(item, True)

            oIO = byteStringIO()
            o = EPUBOutput() if booktype == "epub" else MOBIOutput()
            o.convert(oeb, oIO, opts, log)
            self.SendToKindle(username, to, book.title, booktype, str(oIO.getvalue()), tz)
            rs = "%s(%s).%s Sent!" % (book.title, local_time(tz=tz), booktype)
            log.info(rs)
            return rs
        else:
            self.deliverlog(username, to, book.title, 0, status="nonews", tz=tz)
            rs = "No new feeds."
            log.info(rs)
            return rs
Exemple #6
0
 def GET(self):
     username = web.input().get("u")
     bookid = web.input().get("id")
     #to = web.input().get("to")
     #booktype = web.input().get("type", "mobi")
     #titlefmt = web.input().get("titlefmt")
     #tz = int(web.input().get("tz", TIMEZONE))
     #if not bookid:
     #    return "No book to send!<br />"
     
     user = KeUser.all().filter("name = ", username).get()
     if not user:
         return "User not exist!<br />"
     
     to = user.kindle_email
     booktype = user.book_type
     titlefmt = user.titlefmt
     tz = user.timezone
     
     bookid = bookid.split(',') if ',' in bookid else [bookid]
     bks = []
     for id in bookid:
         try:
             bks.append(Book.get_by_id(int(id)))
         except:
             continue
             #return "id of book is invalid or book not exist!<br />"
     
     if len(bks) == 0:
         return "No have book to push!"
     elif len(bks) == 1:
         book4meta = BookClass(bks[0].title) if bks[0].builtin else bks[0]
     else: #多本书合并推送时使用“自定义RSS”的元属性
         book4meta = user.ownfeeds
     
     if not book4meta:
         return "No have book to push.<br />"
         
     opts = oeb = None
     
     # 创建 OEB
     global log
     opts = getOpts()
     oeb = CreateOeb(log, None, opts)
     title = "%s %s" % (book4meta.title, local_time(titlefmt, tz)) if titlefmt else book4meta.title
     
     setMetaData(oeb, title, book4meta.language, local_time(tz=tz), 'KindleEar')
     oeb.container = ServerContainer(log)
     
     #guide
     if len(bks)==1 and bks[0].builtin:
         mhfile = book4meta.mastheadfile
         coverfile = book4meta.coverfile
     else:
         mhfile = DEFAULT_MASTHEAD
         coverfile = DEFAULT_COVER
     
     if mhfile:
         id, href = oeb.manifest.generate('masthead', mhfile) # size:600*60
         oeb.manifest.add(id, href, MimeFromFilename(mhfile))
         oeb.guide.add('masthead', 'Masthead Image', href)
     
     if coverfile:
         id, href = oeb.manifest.generate('cover', coverfile)
         item = oeb.manifest.add(id, href, MimeFromFilename(coverfile))
         oeb.guide.add('cover', 'Cover', href)
         oeb.metadata.add('cover', id)
     
     itemcnt,imgindex = 0,0
     sections = OrderedDict()
     for bk in bks:
         if bk.builtin:
             book = BookClass(bk.title)
             if not book:
                 log.warn('not exist book <%s>' % bk.title)
                 continue
             book = book(imgindex=imgindex)
             book.url_filters = [flt.url for flt in user.urlfilter]
         else: # 自定义RSS
             if bk.feedscount == 0:
                 continue  #return "the book has no feed!<br />"
             book = BaseFeedBook(imgindex=imgindex)
             book.title = bk.title
             book.description = bk.description
             book.language = bk.language
             book.keep_image = bk.keep_image
             book.oldest_article = bk.oldest_article
             book.fulltext_by_readability = True
             feeds = bk.feeds
             book.feeds = [(feed.title, feed.url, feed.isfulltext) for feed in feeds]
             book.url_filters = [flt.url for flt in user.urlfilter]            
         
         # 对于html文件,变量名字自文档
         # 对于图片文件,section为图片mime,url为原始链接,title为文件名,content为二进制内容
         for sec_or_media, url, title, content, brief in book.Items(opts,user):
             if not sec_or_media or not title or not content:
                 continue
             
             if sec_or_media.startswith(r'image/'):
                 id, href = oeb.manifest.generate(id='img', href=title)
                 item = oeb.manifest.add(id, href, sec_or_media, data=content)
                 imgindex += 1
             else:
                 id, href = oeb.manifest.generate(id='feed', href='feed%d.html'%itemcnt)
                 item = oeb.manifest.add(id, href, 'application/xhtml+xml', data=content)
                 oeb.spine.add(item, True)
                 sections.setdefault(sec_or_media, [])
                 sections[sec_or_media].append((title, item, brief))
                 itemcnt += 1
                 
     if itemcnt > 0: # 建立TOC,杂志模式需要为两层目录结构
         stoc = ['<html><head><title>Table Of Contents</title></head><body><h2>Table Of Contents</h2>']
         for sec in sections.keys():
             stoc.append('<h3><a href="%s">%s</a></h3>'%(sections[sec][0][1].href,sec))
             sectoc = oeb.toc.add(sec, sections[sec][0][1].href)
             for title, a, brief in sections[sec]:
                 stoc.append('&nbsp;&nbsp;&nbsp;&nbsp;<a href="%s">%s</a><br />'%(a.href,title))
                 sectoc.add(title, a.href, description=brief if brief else None)
         stoc.append('</body></html>')
         id, href = oeb.manifest.generate(id='toc', href='toc.html')
         item = oeb.manifest.add(id, href, 'application/xhtml+xml', data=''.join(stoc))
         oeb.guide.add('toc', 'Table of Contents', href)
         oeb.spine.add(item, True)
         
         oIO = byteStringIO()
         o = EPUBOutput() if booktype == "epub" else MOBIOutput()
         o.convert(oeb, oIO, opts, log)
         self.SendToKindle(username, to, book4meta.title, booktype, str(oIO.getvalue()), tz)
         rs = "%s(%s).%s Sent!"%(book4meta.title, local_time(tz=tz), booktype)
         log.info(rs)
         return rs
     else:
         self.deliverlog(username, to, book4meta.title, 0, status='nonews',tz=tz)
         rs = "No new feeds."
         log.info(rs)
         return rs
Exemple #7
0
    def GET(self):
        username = web.input().get("u")
        bookid = web.input().get("id")

        user = KeUser.all().filter("name = ", username).get()
        if not user:
            return "User not exist!<br />"

        to = user.kindle_email
        if (';' in to) or (',' in to):
            to = to.replace(',', ';').replace(' ', '').split(';')

        booktype = user.book_type  #mobi,epub
        bookmode = user.book_mode or 'periodical'  #periodical,comic
        titlefmt = user.titlefmt
        tz = user.timezone

        bookid = bookid.split(',') if ',' in bookid else [bookid]
        bks = []
        for id_ in bookid:
            try:
                bks.append(Book.get_by_id(int(id_)))
            except:
                continue
                #return "id of book is invalid or book not exist!<br />"

        book4meta = None
        if len(bks) == 0:
            return "No have book to push!"
        elif len(bks) == 1:
            if bks[0].builtin:
                book4meta = BookClass(bks[0].title)
                mhfile = book4meta.mastheadfile
                coverfile = book4meta.coverfile
                if issubclass(book4meta, BaseComicBook
                              ):  #如果单独推送一个继承自BaseComicBook的书籍,则自动设置为漫画模式
                    bookmode = 'comic'
            else:  #单独的推送自定义RSS
                book4meta = bks[0]
                mhfile = DEFAULT_MASTHEAD
                coverfile = DEFAULT_COVER
        else:  #多本书合并推送时使用“自定义RSS”的元属性
            book4meta = user.ownfeeds
            mhfile = DEFAULT_MASTHEAD
            coverfile = DEFAULT_COVER_BV if user.merge_books else DEFAULT_COVER

        if not book4meta:
            return "No have book to push.<br />"

        opts = None
        oeb = None

        # 创建 OEB
        #global log
        opts = getOpts(user.device, bookmode)
        oeb = CreateOeb(main.log, None, opts)
        bookTitle = "%s %s" % (book4meta.title, local_time(
            titlefmt, tz)) if titlefmt else book4meta.title

        if bookmode == 'comic':
            pubtype = 'book:book:KindleEar'
        else:
            pubtype = 'periodical:magazine:KindleEar'

        setMetaData(oeb,
                    bookTitle,
                    book4meta.language,
                    local_time("%Y-%m-%d", tz),
                    pubtype=pubtype)
        oeb.container = ServerContainer(main.log)

        #guide
        if mhfile:
            id_, href = oeb.manifest.generate('masthead',
                                              mhfile)  # size:600*60
            oeb.manifest.add(id_, href, MimeFromFilename(mhfile))
            oeb.guide.add('masthead', 'Masthead Image', href)

        if coverfile:
            imgData = None
            imgMime = ''
            #使用保存在数据库的用户上传的封面
            if coverfile == DEFAULT_COVER and user.cover:
                imgData = user.cover
                imgMime = 'image/jpeg'  #保存在数据库中的只可能是jpeg格式
            elif callable(coverfile):  #如果封面需要回调的话
                try:
                    imgData = book4meta().coverfile()
                    if imgData:
                        imgType = imghdr.what(None, imgData)
                        if imgType:  #如果是合法图片
                            imgMime = r"image/" + imgType
                        else:
                            main.log.warn(
                                'content of cover is invalid : [%s].' %
                                bookTitle)
                            imgData = None
                except Exception as e:
                    main.log.warn(
                        'Failed to fetch cover for book [%s]. [Error: %s]' %
                        (bookTitle, str(e)))
                    coverfile = DEFAULT_COVER
                    imgData = None
                    imgMime = ''

            if imgData and imgMime:
                id_, href = oeb.manifest.generate('cover', 'cover.jpg')
                item = oeb.manifest.add(id_, href, imgMime, data=imgData)
            else:
                id_, href = oeb.manifest.generate('cover', coverfile)
                item = oeb.manifest.add(id_, href, MimeFromFilename(coverfile))
            oeb.guide.add('cover', 'Cover', href)
            oeb.metadata.add('cover', id_)
        elif len(bks) > 1 and DEFAULT_COVER:
            #将所有书籍的封面拼贴成一个
            #如果DEFAULT_COVER=None说明用户不需要封面
            id_, href = oeb.manifest.generate('cover', 'cover.jpg')
            item = oeb.manifest.add(id_,
                                    href,
                                    'image/jpeg',
                                    data=self.MergeCovers(bks, opts, user))
            oeb.guide.add('cover', 'Cover', href)
            oeb.metadata.add('cover', id_)

        itemcnt, imgindex = 0, 0
        sections = OrderedDict()
        toc_thumbnails = {}  #map img-url -> manifest-href
        for bk in bks:
            if bk.builtin:
                cbook = BookClass(bk.title)
                if not cbook:
                    main.log.warn('not exist book <%s>' % bk.title)
                    continue
                book = cbook(imgindex=imgindex, opts=opts, user=user)
                book.url_filters = [flt.url for flt in user.urlfilter]
                if bk.needs_subscription:  #需要登录
                    subs_info = user.subscription_info(bk.title)
                    if subs_info:
                        book.account = subs_info.account
                        book.password = subs_info.password
            else:  # 自定义RSS
                if bk.feedscount == 0:
                    continue  #return "the book has no feed!<br />"

                book = BaseFeedBook(imgindex=imgindex, opts=opts, user=user)
                book.title = bk.title
                book.description = bk.description
                book.language = bk.language
                book.keep_image = bk.keep_image
                book.oldest_article = bk.oldest_article
                book.fulltext_by_readability = True
                feeds = bk.feeds
                book.feeds = []
                for feed in feeds:
                    if feed.url.startswith(
                        ("http://www.cartoonmad.com", "http://ac.qq.com",
                         "http://m.ac.qq.com")):
                        self.ProcessComicRSS(username, user, feed)
                    else:
                        book.feeds.append(
                            (feed.title, feed.url, feed.isfulltext))
                book.url_filters = [flt.url for flt in user.urlfilter]

            # 对于html文件,变量名字自文档,thumbnail为文章第一个img的url
            # 对于图片文件,section为图片mime,url为原始链接,title为文件名,content为二进制内容,
            #    img的thumbail仅当其为article的第一个img为True
            try:  #书的质量可能不一,一本书的异常不能影响其他书籍的推送
                for sec_or_media, url, title, content, brief, thumbnail in book.Items(
                ):
                    if not sec_or_media or not title or not content:
                        continue

                    if sec_or_media.startswith(r'image/'):
                        id_, href = oeb.manifest.generate(id='img', href=title)
                        item = oeb.manifest.add(id_,
                                                href,
                                                sec_or_media,
                                                data=content)
                        if thumbnail:
                            toc_thumbnails[url] = href
                        imgindex += 1
                    else:
                        #id, href = oeb.manifest.generate(id='feed', href='feed%d.html'%itemcnt)
                        #item = oeb.manifest.add(id, href, 'application/xhtml+xml', data=content)
                        #oeb.spine.add(item, True)
                        sections.setdefault(sec_or_media, [])
                        sections[sec_or_media].append(
                            (title, brief, thumbnail, content))
                        itemcnt += 1
            except Exception as e:
                excFileName, excFuncName, excLineNo = get_exc_location()
                main.log.warn(
                    "Failed to push <%s> : %s, in file '%s', %s (line %d)" %
                    (book.title, str(e), excFileName, excFuncName, excLineNo))
                continue

        volumeTitle = ''
        if itemcnt > 0:
            #漫画模式不需要TOC和缩略图
            if bookmode == 'comic':
                insertHtmlToc = False
                insertThumbnail = False
                if len(bks) == 1 and book:  #因为漫画模式没有目录,所以在标题中添加卷号
                    volumeTitle = book.LastDeliveredVolume()
                    oeb.metadata.clear('title')
                    oeb.metadata.add('title', bookTitle + volumeTitle)
            else:
                insertHtmlToc = GENERATE_HTML_TOC
                insertThumbnail = GENERATE_TOC_THUMBNAIL

            InsertToc(oeb, sections, toc_thumbnails, insertHtmlToc,
                      insertThumbnail)
            oIO = byteStringIO()
            o = EPUBOutput() if booktype == "epub" else MOBIOutput()
            o.convert(oeb, oIO, opts, main.log)
            try:
                ultima_log = DeliverLog.all().order('-time').get()
            except:
                ultima_log = sorted(DeliverLog.all(),
                                    key=attrgetter('time'),
                                    reverse=True)
                ultima_log = ultima_log[0] if ultima_log else None
            if ultima_log:
                diff = datetime.datetime.utcnow() - ultima_log.datetime
                if diff.days * 86400 + diff.seconds < 10:
                    time.sleep(8)
            self.SendToKindle(username, to, book4meta.title + volumeTitle,
                              booktype, str(oIO.getvalue()), tz)
            rs = "%s(%s).%s Sent!" % (book4meta.title, local_time(tz=tz),
                                      booktype)
            main.log.info(rs)
            return rs
        else:
            self.deliverlog(username,
                            str(to),
                            book4meta.title + volumeTitle,
                            0,
                            status='nonews',
                            tz=tz)
            rs = "No new feeds."
            main.log.info(rs)
            return rs
Exemple #8
0
    def MergeCovers(self, bks, opts, user):
        coverfiles = []
        callableInstances = []
        for bk in bks:
            if bk.builtin:
                book = BookClass(bk.title)
                if book and book.coverfile:
                    if callable(book.coverfile):
                        instan = book()
                        callableInstances.append(instan)
                        coverfiles.append(instan.coverfile)
                    else:
                        coverfiles.append(book.coverfile)
            elif DEFAULT_COVER:
                coverfiles.append(DEFAULT_COVER)

        num_imgs = len(coverfiles)
        if num_imgs > 9:  #大于9个则随机选择9个
            coverfiles = random.sample(coverfiles, 9)
            num_imgs = 9

        imgs_orig = []
        srvcontainer = ServerContainer()
        for cv in coverfiles:
            img = None
            #使用用户上传的保存在数据库的封面
            if cv == DEFAULT_COVER and user.cover:
                try:
                    img = Image.open(StringIO.StringIO(user.cover))
                except:
                    img = None
            elif callable(cv):  #如果封面需要回调的话
                try:
                    data = cv()
                    if data:
                        img = Image.open(StringIO.StringIO(data))
                    else:
                        cv = DEFAULT_COVER
                        img = None
                except Exception as e:
                    main.log.warn(
                        '[MergeCovers] Content of cover is invalid : [%s].' %
                        str(e))
                    cv = DEFAULT_COVER
                    img = None
            try:
                if not img:
                    img = Image.open(StringIO.StringIO(srvcontainer.read(cv)))
            except Exception as e:
                main.log.warn('[MergeCovers] Cover file invalid [%s], %s' %
                              (str(cv), str(e)))
            else:
                imgs_orig.append(img)
        num_imgs = len(imgs_orig)
        if num_imgs == 0:
            return srvcontainer.read(DEFAULT_COVER)

        #所有图像的宽高最大值,保证粘贴过程不丢失任何像素
        w = max([im.size[0] for im in imgs_orig])
        h = max([im.size[1] for im in imgs_orig])

        if num_imgs == 1:
            pos_info = [(0, 0)]
            new_size = (w, h)
        elif num_imgs <= 4:  #4等分
            pos_info = [(0, 0), (w, 0), (0, h), (w, h)]
            new_size = (w * 2, h * 2)
            if num_imgs < 4:  #填满4格
                imgs_orig += random.sample(imgs_orig, 4 - num_imgs)
        elif num_imgs in (5, 6):  #1个大的,5个小的
            pos_info = [[(0, 0, w * 2, h * 2), (w * 2, 0), (w * 2, h),
                         (0, h * 2), (w, h * 2), (w * 2, h * 2)],
                        [(w, 0, w * 2, h * 2), (0, 0), (0, h), (0, h * 2),
                         (w, h * 2), (w * 2, h * 2)],
                        [(0, h, w * 2, h * 2), (0, 0), (w, 0), (w * 2, 0),
                         (w * 2, h), (w * 2, h * 2)],
                        [(0, 0), (w, 0), (w * 2, 0), (0, h),
                         (w, h, w * 2, h * 2), (0, h * 2)]]
            pos_info = random.choice(pos_info)
            if num_imgs == 5:  #填满6格
                #pos_info = [pos_info[0]] + random.sample(pos_info[1:], 4)
                imgs_orig.append(random.choice(imgs_orig))
            new_size = (w * 3, h * 3)
        else:  #九宫格
            pos_info = [(0, 0), (w, 0), (w * 2, 0), (0, h), (w, h), (w * 2, h),
                        (0, h * 2), (w, h * 2), (w * 2, h * 2)]
            new_size = (w * 3, h * 3)
            if num_imgs < 9:
                imgs_orig += random.sample(imgs_orig, 9 - num_imgs)

        #随机安排每个图片的位置
        random.shuffle(pos_info)

        #拼接图片
        imgnew = Image.new('L' if opts.graying_image else 'RGB', new_size,
                           'white')
        for idx, img in enumerate(imgs_orig):
            pos = pos_info[idx]
            if len(pos) > 2:  #如果元素为4个,则前两个是在大图中的位置,后两个是缩小后的图片尺寸
                img = img.resize(pos[2:])
                pos = pos[:2]
            imgnew.paste(img, pos)

        #新生成的图片再整体缩小到设定大小
        rw, rh = opts.reduce_image_to
        ratio = min(
            float(rw) / float(new_size[0]),
            float(rh) / float(new_size[1]))
        imgnew = imgnew.resize(
            (int(new_size[0] * ratio), int(new_size[1] * ratio)))
        data = StringIO.StringIO()
        imgnew.save(data, 'JPEG')
        return data.getvalue()
Exemple #9
0
 def GET(self):
     username = web.input().get("u")
     bookid = web.input().get("id")
     
     user = KeUser.all().filter("name = ", username).get()
     if not user:
         return "User not exist!<br />"
     
     to = user.kindle_email
     booktype = user.book_type
     titlefmt = user.titlefmt
     tz = user.timezone
     
     bookid = bookid.split(',') if ',' in bookid else [bookid]
     bks = []
     for id_ in bookid:
         try:
             bks.append(Book.get_by_id(int(id_)))
         except:
             continue
             #return "id of book is invalid or book not exist!<br />"
     
     if len(bks) == 0:
         return "No have book to push!"
     elif len(bks) == 1:
         book4meta = BookClass(bks[0].title) if bks[0].builtin else bks[0]
     else: #多本书合并推送时使用“自定义RSS”的元属性
         book4meta = user.ownfeeds
     
     if not book4meta:
         return "No have book to push.<br />"
         
     opts = oeb = None
     
     # 创建 OEB
     #global log
     opts = getOpts(user.device)
     oeb = CreateOeb(main.log, None, opts)
     title = "%s %s" % (book4meta.title, local_time(titlefmt, tz)) if titlefmt else book4meta.title
     
     setMetaData(oeb, title, book4meta.language, local_time("%Y-%m-%d",tz), 'KindleEar')
     oeb.container = ServerContainer(main.log)
     
     #guide
     if len(bks) == 1:
         if bks[0].builtin:
             mhfile = book4meta.mastheadfile
             coverfile = book4meta.coverfile
         else: #单独的推送自定义RSS
             mhfile = DEFAULT_MASTHEAD
             coverfile = DEFAULT_COVER
     else:
         mhfile = DEFAULT_MASTHEAD
         coverfile = DEFAULT_COVER_BV if user.merge_books else DEFAULT_COVER
     
     if mhfile:
         id_, href = oeb.manifest.generate('masthead', mhfile) # size:600*60
         oeb.manifest.add(id_, href, MimeFromFilename(mhfile))
         oeb.guide.add('masthead', 'Masthead Image', href)
     
     if coverfile:
         id_, href = oeb.manifest.generate('cover', coverfile)
         item = oeb.manifest.add(id_, href, MimeFromFilename(coverfile))
         oeb.guide.add('cover', 'Cover', href)
         oeb.metadata.add('cover', id_)
     elif len(bks) > 1 and DEFAULT_COVER:
         #将所有书籍的封面拼贴成一个
         #如果DEFAULT_COVER=None说明用户不需要封面
         id_, href = oeb.manifest.generate('cover', 'cover.jpg')
         item = oeb.manifest.add(id_, href, 'image/jpeg', data=self.MergeCovers(bks, opts))
         oeb.guide.add('cover', 'Cover', href)
         oeb.metadata.add('cover', id_)
         
     itemcnt,imgindex = 0,0
     sections = OrderedDict()
     toc_thumbnails = {} #map img-url -> manifest-href
     for bk in bks:
         if bk.builtin:
             book = BookClass(bk.title)
             if not book:
                 main.log.warn('not exist book <%s>' % bk.title)
                 continue
             book = book(imgindex=imgindex)
             book.url_filters = [flt.url for flt in user.urlfilter]
             if bk.needs_subscription: #需要登录
                 subs_info = user.subscription_info(bk.title)
                 if subs_info:
                     book.account = subs_info.account
                     book.password = subs_info.password
         else: # 自定义RSS
             if bk.feedscount == 0:
                 continue  #return "the book has no feed!<br />"
             book = BaseFeedBook(imgindex=imgindex)
             book.title = bk.title
             book.description = bk.description
             book.language = bk.language
             book.keep_image = bk.keep_image
             book.oldest_article = bk.oldest_article
             book.fulltext_by_readability = True
             feeds = bk.feeds
             book.feeds = [(feed.title, feed.url, feed.isfulltext) for feed in feeds]
             book.url_filters = [flt.url for flt in user.urlfilter]
             
         # 对于html文件,变量名字自文档,thumbnail为文章第一个img的url
         # 对于图片文件,section为图片mime,url为原始链接,title为文件名,content为二进制内容,
         #    img的thumbail仅当其为article的第一个img为True
         try: #书的质量可能不一,一本书的异常不能影响推送
             for sec_or_media, url, title, content, brief, thumbnail in book.Items(opts,user):
                 if not sec_or_media or not title or not content:
                     continue
                 
                 if sec_or_media.startswith(r'image/'):
                     id_, href = oeb.manifest.generate(id='img', href=title)
                     item = oeb.manifest.add(id_, href, sec_or_media, data=content)
                     if thumbnail:
                         toc_thumbnails[url] = href
                     imgindex += 1
                 else:
                     #id, href = oeb.manifest.generate(id='feed', href='feed%d.html'%itemcnt)
                     #item = oeb.manifest.add(id, href, 'application/xhtml+xml', data=content)
                     #oeb.spine.add(item, True)
                     sections.setdefault(sec_or_media, [])
                     sections[sec_or_media].append((title, brief, thumbnail, content))
                     itemcnt += 1
         except Exception as e:
             main.log.warn("Failure in pushing book '%s' : %s" % (book.title, str(e)))
             continue
             
     if itemcnt > 0:
         InsertToc(oeb, sections, toc_thumbnails)
         oIO = byteStringIO()
         o = EPUBOutput() if booktype == "epub" else MOBIOutput()
         o.convert(oeb, oIO, opts, main.log)
         ultima_log = DeliverLog.all().order('-time').get()
         if ultima_log:
             diff = datetime.datetime.utcnow() - ultima_log.datetime
             if diff.days * 86400 + diff.seconds < 5:
                 time.sleep(8)
         self.SendToKindle(username, to, book4meta.title, booktype, str(oIO.getvalue()), tz)
         rs = "%s(%s).%s Sent!"%(book4meta.title, local_time(tz=tz), booktype)
         main.log.info(rs)
         return rs
     else:
         self.deliverlog(username, to, book4meta.title, 0, status='nonews',tz=tz)
         rs = "No new feeds."
         main.log.info(rs)
         return rs
Exemple #10
0
 def GET(self):
     username = web.input().get("u")
     bookid = web.input().get("id")
     
     user = KeUser.all().filter("name = ", username).get()
     if not user:
         return "User not exist!<br />"
     
     to = user.kindle_email
     booktype = user.book_type
     titlefmt = user.titlefmt
     tz = user.timezone
     
     bookid = bookid.split(',') if ',' in bookid else [bookid]
     bks = []
     for id in bookid:
         try:
             bks.append(Book.get_by_id(int(id)))
         except:
             continue
             #return "id of book is invalid or book not exist!<br />"
     
     if len(bks) == 0:
         return "No have book to push!"
     elif len(bks) == 1:
         book4meta = BookClass(bks[0].title) if bks[0].builtin else bks[0]
     else: #多本书合并推送时使用“自定义RSS”的元属性
         book4meta = user.ownfeeds
     
     if not book4meta:
         return "No have book to push.<br />"
         
     opts = oeb = None
     
     # 创建 OEB
     #global log
     opts = getOpts(user.device)
     oeb = CreateOeb(main.log, None, opts)
     title = "%s %s" % (book4meta.title, local_time(titlefmt, tz)) if titlefmt else book4meta.title
     
     setMetaData(oeb, title, book4meta.language, local_time("%Y-%m-%d",tz), 'KindleEar')
     oeb.container = ServerContainer(main.log)
     
     #guide
     if len(bks)==1 and bks[0].builtin:
         mhfile = book4meta.mastheadfile
         coverfile = book4meta.coverfile
     else:
         mhfile = DEFAULT_MASTHEAD
         coverfile = DEFAULT_COVER_BV if user.merge_books else DEFAULT_COVER
     
     if mhfile:
         id_, href = oeb.manifest.generate('masthead', mhfile) # size:600*60
         oeb.manifest.add(id_, href, MimeFromFilename(mhfile))
         oeb.guide.add('masthead', 'Masthead Image', href)
     
     if coverfile:
         id_, href = oeb.manifest.generate('cover', coverfile)
         item = oeb.manifest.add(id_, href, MimeFromFilename(coverfile))
         oeb.guide.add('cover', 'Cover', href)
         oeb.metadata.add('cover', id_)
     elif len(bks)>1 and DEFAULT_COVER:
         #将所有书籍的封面拼贴成一个
         #如果DEFAULT_COVER=None说明用户不需要封面
         id_, href = oeb.manifest.generate('cover', 'cover.jpg')
         item = oeb.manifest.add(id_, href, 'image/jpeg', data=self.MergeCovers(bks,opts))
         oeb.guide.add('cover', 'Cover', href)
         oeb.metadata.add('cover', id_)
         
     itemcnt,imgindex = 0,0
     sections = OrderedDict()
     toc_thumbnails = {} #map img-url -> manifest-href
     for bk in bks:
         if bk.builtin:
             book = BookClass(bk.title)
             if not book:
                 main.log.warn('not exist book <%s>' % bk.title)
                 continue
             book = book(imgindex=imgindex)
             book.url_filters = [flt.url for flt in user.urlfilter]
             if bk.needs_subscription: #需要登录
                 subs_info = user.subscription_info(bk.title)
                 if subs_info:
                     book.account = subs_info.account
                     book.password = subs_info.password
         else: # 自定义RSS
             if bk.feedscount == 0:
                 continue  #return "the book has no feed!<br />"
             book = BaseFeedBook(imgindex=imgindex)
             book.title = bk.title
             book.description = bk.description
             book.language = bk.language
             book.keep_image = bk.keep_image
             book.oldest_article = bk.oldest_article
             book.fulltext_by_readability = True
             feeds = bk.feeds
             book.feeds = [(feed.title, feed.url, feed.isfulltext) for feed in feeds]
             book.url_filters = [flt.url for flt in user.urlfilter]
             
         # 对于html文件,变量名字自文档,thumbnail为文章第一个img的url
         # 对于图片文件,section为图片mime,url为原始链接,title为文件名,content为二进制内容,
         #    img的thumbail仅当其为article的第一个img为True
         for sec_or_media, url, title, content, brief, thumbnail in book.Items(opts,user):
             if not sec_or_media or not title or not content:
                 continue
             
             if sec_or_media.startswith(r'image/'):
                 id_, href = oeb.manifest.generate(id='img', href=title)
                 item = oeb.manifest.add(id_, href, sec_or_media, data=content)
                 if thumbnail:
                     toc_thumbnails[url] = href
                 imgindex += 1
             else:
                 #id, href = oeb.manifest.generate(id='feed', href='feed%d.html'%itemcnt)
                 #item = oeb.manifest.add(id, href, 'application/xhtml+xml', data=content)
                 #oeb.spine.add(item, True)
                 sections.setdefault(sec_or_media, [])
                 sections[sec_or_media].append((title, brief, thumbnail, content))
                 itemcnt += 1
                 
     if itemcnt > 0:
         InsertToc(oeb, sections, toc_thumbnails)
         oIO = byteStringIO()
         o = EPUBOutput() if booktype == "epub" else MOBIOutput()
         o.convert(oeb, oIO, opts, main.log)
         ultima_log = DeliverLog.all().order('-time').get()
         if ultima_log:
             diff = datetime.datetime.utcnow() - ultima_log.datetime
             if diff.days * 86400 + diff.seconds < 5:
                 time.sleep(8)
         self.SendToKindle(username, to, book4meta.title, booktype, str(oIO.getvalue()), tz)
         rs = "%s(%s).%s Sent!"%(book4meta.title, local_time(tz=tz), booktype)
         main.log.info(rs)
         return rs
     else:
         self.deliverlog(username, to, book4meta.title, 0, status='nonews',tz=tz)
         rs = "No new feeds."
         main.log.info(rs)
         return rs
Exemple #11
0
 def MergeCovers(self, bks, opts):
     "将所有书籍的封面拼起来,为了更好的效果,请保证图片的大小统一。"
     from StringIO import StringIO
     from PIL import Image
     import random
     
     coverfiles = []
     for bk in bks:
         if bk.builtin:
             book = BookClass(bk.title)
             if book and book.coverfile:
                 coverfiles.append(book.coverfile)
                 
     num_imgs = len(coverfiles)
     if num_imgs > 9:#大于9个则随机选择9个
         coverfiles = random.sample(coverfiles, 9)
         num_imgs = 9
     
     imgs_orig = []
     srvcontainer = ServerContainer()
     for cv in coverfiles:
         try:
             img = Image.open(StringIO(srvcontainer.read(cv)))
         except Exception as e:
             continue
         else:
             imgs_orig.append(img)
     num_imgs = len(imgs_orig)
     if num_imgs == 0:
         return srvcontainer.read(DEFAULT_COVER)
     
     #所有图像的宽高最大值,保证粘贴过程不丢失任何像素
     w = max([im.size[0] for im in imgs_orig])
     h = max([im.size[1] for im in imgs_orig])
     
     if num_imgs == 1:
         pos_info = [(0,0)]
         new_size = (w,h)
     elif num_imgs <=4:
         pos_info = [(0,0),(w,0),(0,h),(w,h)]
         new_size = (w*2,h*2)
     elif num_imgs in (5,6): #1个大的,4个或5个小的
         pos_info = [[(0,0,w*2,h*2),(w*2,0),(w*2,h),(0,h*2),(w,h*2),(w*2,h*2)],
         [(w,0,w*2,h*2),(0,0),(0,h),(0,h*2),(w,h*2),(w*2,h*2)],
         [(0,h,w*2,h*2),(0,0),(w,0),(w*2,0),(w*2,h),(w*2,h*2)],
         [(0,0),(w,0),(w*2,0),(0,h),(w,h,w*2,h*2),(0,h*2)]]
         pos_info = random.choice(pos_info)
         if num_imgs == 5:
             pos_info = [pos_info[0]] + random.sample(pos_info[1:],4)
         new_size = (w*3,h*3)
     else:
         pos_info = [(0,0),(w,0),(w*2,0),(0,h),(w,h),(w*2,h),(0,h*2),(w,h*2),(w*2,h*2)]
         new_size = (w*3,h*3)
         
     #随机安排每个图片的位置
     random.shuffle(pos_info)
     
     imgnew = Image.new('L' if opts.graying_image else 'RGB', new_size, 'white')
     for idx,img in enumerate(imgs_orig):
         pos = pos_info[idx]
         if len(pos) > 2:
             img = img.resize(pos[2:])
             pos = pos[:2]
         imgnew.paste(img, pos)
     
     rw,rh = opts.reduce_image_to
     ratio = min(float(rw)/float(new_size[0]), float(rh)/float(new_size[0]))
     imgnew = imgnew.resize((int(new_size[0]*ratio), int(new_size[1]*ratio)))
     data = StringIO()
     imgnew.save(data, 'JPEG')
     return data.getvalue()
     
Exemple #12
0
 def GET(self):
     username = web.input().get("u")
     bookid = web.input().get("id")
     to = web.input().get("to")
     booktype = web.input().get("type", "mobi")
     titlefmt = web.input().get("titlefmt")
     tz = int(web.input().get("tz", TIMEZONE))
     if not bookid or not to:
         return "No book to send!<br />"
     try:
         bookid = int(bookid)
     except:
         return "id of book is invalid!<br />"
         
     bk = Book.get_by_id(bookid)
     if not bk:
         return "Title of feeds not exist!<br />"
     
     if bk.builtin:
         book = BookClass(bk.title)
         if not book:
             return "the builtin book not exist!<br />"
         book = book()
     else: # 自定义RSS
         if bk.feedscount == 0:
             return "the book has no feed!<br />"
         book = BaseFeedBook()
         book.title = bk.title
         book.description = bk.description
         book.language = bk.language
         book.keep_image = bk.keep_image
         book.oldest_article = bk.oldest_article
         book.fulltext_by_readability = True
         feeds = bk.feeds
         book.feeds = [(feed.title, feed.url, feed.isfulltext) for feed in feeds]
         book.url_filters = [flt.url for flt in UrlFilter.all()]
     
     opts = oeb = None
     
     # 创建 OEB
     global log
     opts = getOpts()
     oeb = CreateOeb(log, None, opts)
     if titlefmt:
         title = "%s %s" % (book.title, local_time(titlefmt, tz))
     else:
         title = book.title
     setMetaData(oeb, title, book.language, local_time(tz=tz), SrcEmail)
     oeb.container = ServerContainer(log)
     
     #guide
     mhfile = book.mastheadfile
     if mhfile:
         id, href = oeb.manifest.generate('masthead', mhfile) # size:600*60
         oeb.manifest.add(id, href, MimeFromFilename(mhfile))
         oeb.guide.add('masthead', 'Masthead Image', href)
     
     coverfile = book.coverfile
     if coverfile:
         id, href = oeb.manifest.generate('cover', coverfile)
         item = oeb.manifest.add(id, href, MimeFromFilename(coverfile))
         oeb.guide.add('cover', 'Cover', href)
         oeb.metadata.add('cover', id)
     
     itemcnt = 0
     sections = OrderedDict()
     # 对于html文件,变量名字自文档
     # 对于图片文件,section为图片mime,url为原始链接,title为文件名,content为二进制内容
     for sec_or_media, url, title, content, brief in book.Items():
         if not sec_or_media or not title or not content:
             continue
         
         if sec_or_media.startswith(r'image/'):
             id, href = oeb.manifest.generate(id='img', href=title)
             item = oeb.manifest.add(id, href, sec_or_media, data=content)
         else:
             id, href = oeb.manifest.generate(id='feed', href='feed%d.htm'%itemcnt)
             item = oeb.manifest.add(id, href, 'text/html', data=content)
             oeb.spine.add(item, True)
             sections.setdefault(sec_or_media, [])
             sections[sec_or_media].append((title, item, brief))
             itemcnt += 1
             
     if itemcnt > 0: # 建立TOC,杂志模式需要为两层目录结构
         for sec in sections.keys():
             sectoc = oeb.toc.add(sec, sections[sec][0][1].href)
             for title, a, brief in sections[sec]:
                 sectoc.add(title, a.href, description=brief if brief else None)
         
         oIO = byteStringIO()
         o = EPUBOutput() if booktype == "epub" else MOBIOutput()
         o.convert(oeb, oIO, opts, log)
         self.SendToKindle(username, to, book.title, booktype, str(oIO.getvalue()), tz)
         rs = "%s(%s).%s Sent!"%(book.title, local_time(tz=tz), booktype)
         log.info(rs)
         return rs
     else:
         self.deliverlog(username, to, book.title, 0, status='nonews',tz=tz)
         rs = "No new feeds."
         log.info(rs)
         return rs
Exemple #13
0
 def GET(self):
     username = web.input().get('u')
     books = Book.all()
     if username: # 现在投递,不判断时间和星期
         sent = []
         for book in books:
             if username not in book.users:
                 continue
             user = KeUser.all().filter("name = ", username).get()
             if user and user.kindle_email:
                 self.queueit(user, book.key().id())
                 sent.append(book.title)
         if len(sent):
             tips = _("Book(s) (%s) put to queue!") % u', '.join(sent)
         else:
             tips = _("No book(s) to deliver!")
         return jjenv.get_template("autoback.html").render(nickname=session.username,
             title='Delivering',tips=tips)
     
     #定时cron调用
     sentcnt = 0
     for book in books:
         if not book.users: # 没有用户订阅此书
             continue
         
         #确定此书是否需要下载
         for u in book.users:
             user = KeUser.all().filter("enable_send = ",True).filter("name = ", u).get()
             if not user or not user.kindle_email:
                 continue
             
             #先判断当天是否需要推送
             day = local_time('%A', user.timezone)
             usrdays = user.send_days
             if usrdays and day not in usrdays: #为空也表示每日推送
                 continue
             
             #时间判断
             h = int(local_time("%H", user.timezone)) + 1
             h = h - 24 if h > 24 else h    
             if user.send_time != h:
                 continue
             
             #到了这里才算需要推送
             if book.builtin:
                 bkcls = BookClass(book.title)
                 if not bkcls:
                     continue
                 if bkcls.deliver_days: #按星期推送                            
                     days = bkcls.deliver_days
                     if not isinstance(days, list):
                         days = [days]
                     if day in days:
                         self.queueit(user, book.key().id())
                         sentcnt += 1
                 else: #每天推送
                     self.queueit(user, book.key().id())
                     sentcnt += 1
             else:
                 self.queueit(user, book.key().id())
                 sentcnt += 1
     return "Put <strong>%d</strong> books to queue!" % sentcnt
Exemple #14
0
    def GET(self):
        username = web.input().get('u')
        id_ = web.input().get('id')
        feedsId = web.input().get('feedsId')
        if id_:
            id_ = [int(item) for item in id_.split('|') if item.isdigit()]
        
        self.queue2push = defaultdict(list)
        
        books = Book.all()
        if username: #现在投递【测试使用】,不需要判断时间和星期
            user = KeUser.all().filter("name = ", username).get()
            if not user or not user.kindle_email:
                return self.render('autoback.html', "Delivering", tips=_('The username not exist or the email of kindle is empty.'))

            sent = []
            if id_: #推送特定账号指定的书籍,这里不判断特定账号是否已经订阅了指定的书籍,只要提供就推送
                books2push = [Book.get_by_id(item) for item in id_ if Book.get_by_id(item)]
            else: #推送特定账号所有的书籍
                books2push = [item for item in books if username in item.users]
            
            for book in books2push:
                self.queueit(user, book.key().id(), book.separate, feedsId)
                sent.append(book.title)
            self.flushqueue()

            if len(sent):
                tips = _("Book(s) (%s) put to queue!") % u', '.join(sent)
            else:
                tips = _("No book to deliver!")

            return self.render('autoback.html', "Delivering", tips=tips)
        
        #定时cron调用
        sentcnt = 0
        for book in books:
            if not book.users: #没有用户订阅此书
                continue
            
            bkcls = None
            if book.builtin:
                bkcls = BookClass(book.title)
                if not bkcls:
                    continue
            
            #确定此书是否需要下载
            for u in book.users:
                user = KeUser.all().filter("enable_send = ",True).filter("name = ", u).get()
                if not user or not user.kindle_email:
                    continue
                    
                #先判断当天是否需要推送
                day = local_time('%A', user.timezone)
                usrdays = user.send_days
                if bkcls and bkcls.deliver_days: #按星期推送
                    days = bkcls.deliver_days
                    if not isinstance(days, list):
                        days = [days]
                    if day not in days:
                        continue
                elif usrdays and day not in usrdays: #为空也表示每日推送
                    continue
                    
                #时间判断
                h = int(local_time("%H", user.timezone)) + 1
                if h >= 24:
                    h -= 24
                if bkcls and bkcls.deliver_times:
                    times = bkcls.deliver_times
                    if not isinstance(times, list):
                        times = [times]
                    if h not in times:
                        continue
                elif user.send_time != h:
                    continue
                
                #到了这里才是需要推送的
                self.queueit(user, book.key().id(), book.separate)
                sentcnt += 1
        self.flushqueue()
        return "Put <strong>%d</strong> books to queue!" % sentcnt
        
Exemple #15
0
 def GET(self):
     id = web.input().get("id")
     emails = web.input().get("emails")
     booktype = web.input().get("type", "mobi")
     if not id or not emails:
         return "No book to send!<br />"
     try:
         id = int(id)
     except:
         return "id of book is invalid!<br />"
         
     bk = Book.all().ancestor(db.Key.from_path("Book", id)).get()
     if not bk:
         return "Title of feeds not exist!<br />"
     
     if bk.builtin:
         book = BookClass(bk.title)
         if not book:
             return "the builtin book not exist!<br />"
         book = book()
     else: # 自定义RSS
         feeds = bk.feeds()
         if feeds.count() == 0:
             return "the book has no feed!<br />"
         book = BaseFeedBook()
         book.title = bk.title
         book.description = bk.description
         book.language = bk.language
         book.feed_encoding = bk.feed_encoding
         book.page_encoding = bk.page_encoding
         book.mastheadfile = bk.mastheadfile
         book.coverfile = bk.coverfile
         book.keep_image = bk.keep_image
         book.fulltext_by_readability = True
         for feed in feeds:
             book.feeds.append((feed.title, feed.url))
     
     emails = emails.split(',')
     
     opts = oeb = None
     
     # 创建 OEB
     global log
     opts = getOpts()
     oeb = CreateOeb(log, None, opts)
     setMetaData(oeb, book.title, book.language, local_time(), SrcEmail)
     oeb.container = ServerContainer(log)
     
     #guide
     mhfile = book.mastheadfile if book.mastheadfile else 'mh_default.gif'    
     id, href = oeb.manifest.generate('masthead', mhfile) # size:600*60
     oeb.manifest.add(id, href, 'image/gif')
     oeb.guide.add('masthead', 'Masthead Image', href)
     
     coverfile = book.coverfile if book.coverfile else DEFAULT_COVER
     if coverfile:
         id, href = oeb.manifest.generate('cover', coverfile)
         item = oeb.manifest.add(id, href, MimeFromFilename(coverfile))
         oeb.guide.add('cover', 'Cover', href)
         oeb.metadata.add('cover', id)
         
     pages, idx = [], 0
     sections = OrderedDict()
     # 对于html文件,变量名字自文档
     # 对于图片文件,catalog为图片mime,url为原始链接,title为文件名,content为二进制内容
     for section, url, title, content in book.Items():
         if section.startswith(r'image/'):
             id, href = oeb.manifest.generate(id='img', href=title)
             item = oeb.manifest.add(id, href, section, data=content)
         else:
             id, href = oeb.manifest.generate(id='feed', href='feed%d.htm'%idx)
             item = oeb.manifest.add(id, href, 'text/html', data=content)
             oeb.spine.add(item, True)
             sections.setdefault(section, []).append((title, item))
         idx += 1
         
     if idx > 0: # 建立TOC,杂志模式需要为两层目录结构
         for sec in sections.keys():
             sectoc = oeb.toc.add(sec, sections[sec][0][1].href)
             for title, a in sections[sec]:
                 sectoc.add(title, a.href)
         
         oIO = byteStringIO()
         o = EPUBOutput() if booktype == "epub" else MOBIOutput()
         o.convert(oeb, oIO, opts, log)
         self.SendToKindle(emails, book.title, booktype, str(oIO.getvalue()))
         return "%s(%s).%s Sent!<br />"%(book.title,local_time(),booktype)
     else:
         return "No new feeds.<br />"