コード例 #1
0
ファイル: SearchPage.py プロジェクト: gutenbergtools/autocat3
    def setup(self, os, sql):
        os.f_format_subtitle = os.format_subtitle
        os.f_format_url = BaseSearcher.SearchUrlFormatter('author')
        os.f_format_thumb_url = os.format_none
        os.sort_orders = ('downloads', 'quantity', 'alpha', 'release_date')
        os.icon = 'author'
        os.class_ += 'navlink'
        os.title = _('All Authors')

        sql.query = """
                    SELECT
                       authors.author as title,
                       coalesce (authors.born_floor || '', '') || '-' ||
                          coalesce (authors.died_floor || '', '') as subtitle,
                       authors.pk as pk,
                       max (books.release_date) as release_date,
                       sum (books.downloads) as downloads,
                       count (books.pk) as quantity"""

        sql.from_ = ('authors', 'mn_books_authors as mn', 'books')
        sql.groupby += ('authors.author', 'subtitle', 'authors.pk')
        sql.where.append('authors.pk = mn.fk_authors')
        sql.where.append('books.pk = mn.fk_books')

        if len(os.query):
            sql.fulltext('authors.tsvec', os.query)
            os.title = _("Authors: {author}").format(author=os.query)
        else:
            sql.where.append(
                "authors.author not in ('Various', 'Anonymous', 'Unknown')")
コード例 #2
0
ファイル: SearchPage.py プロジェクト: gutenbergtools/autocat3
    def setup(self, os, sql):
        os.f_format_url = BaseSearcher.SearchUrlFormatter('bookshelf')
        os.f_format_thumb_url = os.format_none
        os.sort_orders = ('downloads', 'quantity', 'alpha', 'release_date',
                          'authors')
        os.icon = 'bookshelf'
        os.class_ += 'navlink'
        os.title = _('All Bookshelves')

        sql.query = """
                    SELECT
                       bookshelves.bookshelf as title,
                       bookshelves.pk as pk,
                       max (books.release_date) as release_date,
                       sum (books.downloads) as downloads,
                       count (books.pk) as quantity"""

        sql.from_ = ('bookshelves', 'mn_books_bookshelves as mn', 'books')
        sql.groupby += ('bookshelves.bookshelf', 'bookshelves.pk')
        sql.where.append('bookshelves.pk = mn.fk_bookshelves')
        sql.where.append('books.pk = mn.fk_books')

        if len(os.query):
            sql.fulltext('bookshelves.tsvec', os.query)
            os.title = _("Bookshelves: {bookshelf}").format(bookshelf=os.query)
コード例 #3
0
    def dummy_text_holder ():
        """Never gets called.

        Only holds some gettext messages to translate.  Keep this in
        sync with GutenbergDatabaseDublinCore.

        """
        _('Copyrighted. Read the copyright notice inside this book for details.')
        _('Public domain in the USA.')
コード例 #4
0
ファイル: StartPage.py プロジェクト: gutenbergtools/autocat3
    def index(self, **dummy_kwargs):
        """ Output the start page. """

        os = BaseSearcher.OpenSearch()

        os.log_request('start')

        os.search_terms = ''
        os.title = {
            'opds': _('Project Gutenberg'),
            'stanza': _('Project Gutenberg')
        }.get(os.format, _('Search Project Gutenberg'))

        cat = BaseSearcher.Cat()
        cat.header = _(
            'Welcome to Project Gutenberg. Use the search box to find your book or pick a link.'
        )
        cat.title = _('Popular')
        cat.subtitle = _('Our most popular books.')
        cat.url = os.url('search', sort_order='downloads')
        cat.class_ += 'navlink'
        cat.icon = 'popular'
        cat.order = 2
        os.entries.append(cat)

        cat = BaseSearcher.Cat()
        cat.title = _('Latest')
        cat.subtitle = _('Our latest releases.')
        cat.url = os.url('search', sort_order='release_date')
        cat.class_ += 'navlink'
        cat.icon = 'date'
        cat.order = 3
        os.entries.append(cat)

        cat = BaseSearcher.Cat()
        cat.title = _('Random')
        cat.subtitle = _('Random books.')
        cat.url = os.url('search', sort_order='random')
        cat.class_ += 'navlink'
        cat.icon = 'random'
        cat.order = 4
        os.entries.append(cat)

        os.total_results = 0
        os.template = 'results'
        os.page = 'start'

        os.url_share = os.url('/', host=os.file_host)
        os.twit = os.tagline

        os.finalize()

        return self.format(os)
コード例 #5
0
ファイル: SearchPage.py プロジェクト: PYTHON01100100/autocat3
    def setup (self, os, sql):
        os.sort_orders = ('downloads', 'release_date', 'title', 'random')
        os.icon = 'book'
        os.class_ += 'booklink'
        os.f_format_icon = os.format_icon_titles

        if os.sort_order == 'random':
            sql.where.append ("pk in (select pk from books order by random() limit 20)")
        if len (os.query):
            sql.fulltext ('books.tsvec', os.query)
            os.title = _("Books: {title}").format (title = os.query)
        else:
            os.title = _('All Books')
コード例 #6
0
ファイル: SearchPage.py プロジェクト: gutenbergtools/autocat3
    def setup(self, os, sql):
        os.sort_orders = ('downloads', )
        os.icon = 'book'
        os.class_ += 'booklink'
        os.f_format_icon = os.format_icon_titles
        os.title = _('Readers also downloaded')

        sql.query = """
                    SELECT
                       books.pk,
                       books.title,
                       books.filing,
                       books.author,
                       books.release_date,
                       books.fk_categories,
                       books.fk_langs,
                       books.coverpages,
                       d.dl as downloads
                    FROM
                      v_appserver_books_4 as books
                        JOIN (
                          SELECT
                            s1.fk_books as pk, count (s1.id) as dl
                          FROM
                            scores.also_downloads as s1,
                            scores.also_downloads as s2
                          WHERE s2.fk_books = %(fk_books)s
                            AND s1.fk_books != %(fk_books)s
                            AND s1.id = s2.id
                          GROUP BY s1.fk_books) as d
                        ON d.pk = books.pk"""
        sql.from_ = ()
        sql.params['fk_books'] = os.id
コード例 #7
0
ファイル: SearchPage.py プロジェクト: PYTHON01100100/autocat3
    def fixup (self, os):

        if (os.start_index == 1 and len (os.entries) > 0):

            # browse-by-author page for maintainers
            if 'is-catalog-maintainer' in cherrypy.request.cookie:
                cat = BaseSearcher.Cat ()
                cat.type = mt.html
                cat.rel = 'related'
                cat.title = _('Browse by Author')
                cat.url = "/browse/authors/%s#a%d" % (os.author[:1].lower (), os.id)
                cat.class_ += 'navlink grayed'
                cat.icon = 'internal'
                cat.order = 9
                os.entries.insert (0, cat)

            # wikipedia links etc.
            rows = BaseSearcher.SQLSearcher.execute (
                """SELECT url, description AS title FROM author_urls
                   WHERE fk_authors = %(fk_authors)s""",
                { 'fk_authors': os.id } )
            for row in rows:
                cat = BaseSearcher.Cat ()
                cat.type = mt.html
                cat.rel = 'related'
                cat.title = _('See also: {title}').format (title = row.title)
                cat.url = row.url
                cat.class_ += 'navlink grayed'
                cat.icon = 'external'
                cat.order = 8
                os.entries.insert (0, cat)

            # author aliases
            if os.format  == 'html':
                rows = BaseSearcher.SQLSearcher.execute (
                    """SELECT alias AS title FROM aliases
                       WHERE fk_authors = %(fk_authors)s AND alias_heading = 1""",
                    { 'fk_authors': os.id }
                    )

                for row in rows:
                    cat = BaseSearcher.Cat ()
                    cat.title = _('Alias {alias}').format (alias = row.title)
                    cat.class_ += 'grayed'
                    cat.icon = 'alias'
                    cat.order = 7
                    os.entries.insert (0, cat)
コード例 #8
0
    def index (self, **kwargs):
        """ Output the page. """

        #
        # OAuth 2.0 flow see:
        # http://tools.ietf.org/html/rfc6749
        #

        session = self.get_or_create_session ()
        if 'id' in kwargs:
            session.ebook = EbookMetaData (kwargs)
        if session.ebook is None:
            raise cherrypy.HTTPError (400, "No ebook selected. Are your cookies enabled?")

        name = self.name

        if 'not_approved' in kwargs or 'error' in kwargs:
            self._dialog (
                _('Sorry. The file could not be sent to {name}.').format (name = name),
                _('Error'))
            self.redirect_done (session)

        try:
            session.oauth_dance (kwargs)
            log ("Sending file %s to %s" % (
                session.ebook.get_source_url (), name))

            with closing (self.request_ebook (session)) as r:
                r.raise_for_status ()
                self.upload_file (session, r)

            log ("File %s sent to %s" % (
                session.ebook.get_source_url (), name))
            self._dialog (
                _('The file has been sent to {name}.').format (name = name),
                _('Sent to {name}').format (name = name))
            self.redirect_done (session)

        except (OAuth2Error, ) as what:
            session.unauthorized (what)
            self.unauthorized ('OAuthError: ' + str (what.urlencoded))

        except (RequestException, IOError, ValueError) as what:
            session.unauthorized (what)
            self.unauthorized ('RequestError: ' + str (what))
            raise cherrypy.HTTPError (500, str (what))
コード例 #9
0
    def no_records_found(os):
        """ Message. """

        cat = BaseSearcher.Cat()
        cat.rel = '__notfound__'
        cat.title = _('No records found.')
        cat.url = os.url('start')
        cat.class_ += 'navlink grayed'
        cat.icon = 'bibrec'
        cat.order = 11
        return cat
コード例 #10
0
    def sort_by_downloads(os):
        """ Append the sort by downloads link. """

        cat = BaseSearcher.Cat()
        cat.rel = 'popular'
        cat.title = _('Sort by Popularity')
        cat.url = os.url_carry(sort_order='downloads')
        cat.class_ += 'navlink grayed'
        cat.icon = 'popular'
        cat.order = 4.0
        os.entries.insert(0, cat)
コード例 #11
0
    def sort_by_quantity(os):
        """ Append the sort by quantity link. """

        cat = BaseSearcher.Cat()
        cat.rel = 'numerous'
        cat.title = _('Sort by Quantity')
        cat.url = os.url_carry(sort_order='quantity')
        cat.class_ += 'navlink grayed'
        cat.icon = 'quantity'
        cat.order = 4.3
        os.entries.insert(0, cat)
コード例 #12
0
    def sort_by_release_date(os):
        """ Append the sort by release date link. """

        cat = BaseSearcher.Cat()
        cat.rel = 'new'
        cat.title = _('Sort by Release Date')
        cat.url = os.url_carry(sort_order='release_date')
        cat.class_ += 'navlink grayed'
        cat.icon = 'date'
        cat.order = 4.4
        os.entries.insert(0, cat)
コード例 #13
0
    def sort_by_author(os):
        """ Append the sort alphabetically by author link. """

        cat = BaseSearcher.Cat()
        cat.rel = 'alphabethical'
        cat.title = _('Sort Alphabetically by Author')
        cat.url = os.url_carry(sort_order='author')
        cat.class_ += 'navlink grayed'
        cat.icon = 'alpha'
        cat.order = 4.2
        os.entries.insert(0, cat)
コード例 #14
0
    def did_you_mean(os, corr, corrected_query):
        """ Message. """

        cat = BaseSearcher.Cat()
        cat.rel = '__didyoumean__'
        cat.title = _('Did you mean: {correction}').format(correction=corr)
        cat.url = os.url('search', query=corrected_query)
        cat.class_ += 'navlink'
        cat.icon = 'suggestion'
        cat.order = 12
        return cat
コード例 #15
0
    def status_line(os):
        """ Placeholder for status line. """

        cat = BaseSearcher.Cat()
        cat.rel = '__statusline__'
        cat.class_ += 'grayed'
        cat.icon = 'bibrec'
        cat.order = 10
        cat.header = os.title
        cat.title = _(u"Displaying results {from_}–{to}").format(
            from_=os.start_index, to=os.end_index)
        return cat
コード例 #16
0
    def translate (self):
        """ Translate DublinCore struct. """

        if self.translated:
            # already translated
            return

        self.hr_release_date = babel.dates.format_date (
            self.release_date, locale = str (cherrypy.response.i18n.locale))

        if cherrypy.response.i18n.locale.language == 'en':
            # no translation required
            return

        self.rights = _(self.rights)
        for author in self.authors:
            author.role = _(author.role)
        for marc in self.marcs:
            marc.caption = _(marc.caption)
        for dcmitype in self.dcmitypes:
            dcmitype.description = _(dcmitype.description)
        for lang in self.languages:
            if lang.id in cherrypy.response.i18n.locale.languages:
                lang.language = cherrypy.response.i18n.locale.languages[lang.id].capitalize ()
        for file_ in self.files:
            file_.hr_filetype = _(file_.hr_filetype)
        for file_ in self.generated_files:
            file_.hr_filetype = _(file_.hr_filetype)

        self.translated = True
コード例 #17
0
ファイル: SearchPage.py プロジェクト: gutenbergtools/autocat3
    def setup(self, os, sql):
        os.sort_orders = ('downloads', 'title', 'author', 'release_date')
        os.title_icon = 'bookshelf'
        os.icon = 'book'
        os.class_ += 'booklink'
        os.f_format_icon = os.format_icon_titles
        os.bookshelf = BaseSearcher.sql_get(
            "select bookshelf from bookshelves where pk = %(pk)s", pk=os.id)
        os.title = _('Books in {bookshelf}').format(bookshelf=os.bookshelf)

        sql.from_.append('mn_books_bookshelves as mn')
        sql.where.append('books.pk = mn.fk_books')
        sql.where.append("mn.fk_bookshelves = %(fk_bookshelves)s")
        sql.params['fk_bookshelves'] = os.id
コード例 #18
0
ファイル: SearchPage.py プロジェクト: gutenbergtools/autocat3
    def setup(self, os, sql):
        os.sort_orders = ('downloads', 'title', 'release_date')
        os.title_icon = 'subject'
        os.icon = 'book'
        os.class_ += 'booklink'
        os.f_format_icon = os.format_icon_titles
        os.subject = BaseSearcher.sql_get(
            "select subject from subjects where pk = %(pk)s", pk=os.id)
        os.title = _('Books about {subject}').format(subject=os.subject)

        sql.from_.append('mn_books_subjects as mn')
        sql.where.append('books.pk = mn.fk_books')
        sql.where.append("mn.fk_subjects = %(fk_subjects)s")
        sql.params['fk_subjects'] = os.id
コード例 #19
0
ファイル: SearchPage.py プロジェクト: gutenbergtools/autocat3
    def setup(self, os, sql):
        os.sort_orders = ('downloads', 'title', 'release_date')
        os.title_icon = 'author'
        os.icon = 'book'
        os.class_ += 'booklink'
        os.f_format_icon = os.format_icon_titles
        os.author = BaseSearcher.sql_get(
            "select author from authors where pk = %(pk)s", pk=os.id)
        os.title = _('Books by {author}').format(author=os.author)

        sql.from_.append('mn_books_authors as mn')
        sql.where.append('books.pk = mn.fk_books')
        sql.where.append("mn.fk_authors = %(fk_authors)s")
        sql.params['fk_authors'] = os.id
コード例 #20
0
ファイル: SearchPage.py プロジェクト: gutenbergtools/autocat3
    def fixup(self, os):
        """ strip marc subfields, add social media hints and facet links """

        for e in os.entries:
            if '$' in e.title:
                e.title = DublinCore.strip_marc_subfields(e.title)

        if (os.sort_order == 'release_date' and os.total_results > 0
                and os.start_index == 1):
            cat = BaseSearcher.Cat()
            cat.title = _('Follow new books on Twitter')
            cat.subtitle = _("Follow our new books on Twitter.")
            cat.url = 'https://twitter.com/gutenberg_new'
            cat.class_ += 'navlink grayed'
            cat.icon = 'twitter'
            cat.order = 5
            os.entries.insert(0, cat)

            cat = BaseSearcher.Cat()
            cat.title = _('Follow new books on Facebook')
            cat.subtitle = _(
                "Follow the link and like the page to have us post new books to your wall."
            )
            cat.url = 'https://www.facebook.com/gutenberg.new'
            cat.class_ += 'navlink grayed'
            cat.icon = 'facebook'
            cat.order = 5
            os.entries.insert(0, cat)

        if (len(os.query) and os.start_index == 1):
            sql2 = BaseSearcher.SQLStatement()
            sql2.query = "select count (*) from bookshelves"
            sql2.fulltext('bookshelves.tsvec', os.query)
            rows = BaseSearcher.SQLSearcher.execute(*sql2.build())
            if rows[0][0] > 0:
                cat = BaseSearcher.Cat()
                cat.rel = 'related'
                cat.title = _('Bookshelves')
                cat.subtitle = __('One bookshelf matches your query.',
                                  '{count} bookshelves match your search.',
                                  rows[0][0]).format(count=rows[0][0])
                cat.url = os.url('bookshelf_search', query=os.query)
                cat.class_ += 'navlink grayed'
                cat.icon = 'bookshelf'
                cat.order = 3
                os.entries.insert(0, cat)

            sql2 = BaseSearcher.SQLStatement()
            sql2.query = "select count (*) from subjects"
            sql2.fulltext('subjects.tsvec', os.query)
            rows = BaseSearcher.SQLSearcher.execute(*sql2.build())
            if rows[0][0] > 0:
                cat = BaseSearcher.Cat()
                cat.rel = 'related'
                cat.title = _('Subjects')
                cat.subtitle = __(
                    'One subject heading matches your search.',
                    '{count} subject headings match your search.',
                    rows[0][0]).format(count=rows[0][0])
                cat.url = os.url('subject_search', query=os.query)
                cat.class_ += 'navlink grayed'
                cat.icon = 'subject'
                cat.order = 3
                os.entries.insert(0, cat)

            sql2 = BaseSearcher.SQLStatement()
            sql2.query = "select count (*) from authors"
            sql2.fulltext('authors.tsvec', os.query)
            rows = BaseSearcher.SQLSearcher.execute(*sql2.build())
            if rows[0][0] > 0:
                cat = BaseSearcher.Cat()
                cat.rel = 'related'
                cat.title = _('Authors')
                cat.subtitle = __('One author name matches your search.',
                                  '{count} author names match your search.',
                                  rows[0][0]).format(count=rows[0][0])
                cat.url = os.url('author_search', query=os.query)
                cat.class_ += 'navlink grayed'
                cat.icon = 'author'
                cat.order = 3
                os.entries.insert(0, cat)
コード例 #21
0
    def __init__(self):
        self.format = None
        self.page = None
        self.template = None
        self.query = None
        self.id = None
        self.sort_order = None
        self.search_terms = None
        self.start_index = 1
        self.items_per_page = 1
        self.total_results = -1
        self.page_mode = 'screen'
        self.user_dialog = ('', '')
        self.opensearch_support = 0  # 0 = none, 1 = full, 2 = fake(Stanza, Aldiko, ...)
        self.books_in_archive = babel.numbers.format_number(
            books_in_archive, locale=str(cherrypy.response.i18n.locale))
        self.breadcrumbs = [
            (_('Project Gutenberg'), _('Go to the Main page.'), '/'),
            (__('1 free ebook', '{count} free ebooks',
                books_in_archive).format(count=self.books_in_archive),
             _('Start a new search.'), '/ebooks/'),
        ]

        # default output formatting functions
        self.f_format_title = self.format_title
        self.f_format_subtitle = self.format_author
        self.f_format_extra = self.format_none  # depends on sort order, set in fix_sortorder ()
        self.f_format_url = self.format_bibrec_url
        self.f_format_thumb_url = self.format_thumb_url
        self.f_format_icon = self.format_icon  # icon class

        self.user_agent = cherrypy.request.headers.get('User-Agent', '')

        cherrypy.request.os = self
        s = cherrypy.session
        k = cherrypy.request.params

        host = cherrypy.request.headers.get('X-Forwarded-Host',
                                            cherrypy.config['host'])
        self.host = host.split(',')[-1].strip()  # keep only the last hub
        # turns out X-Forwarded-Protocol (X-Forwarded-Proto is the defacto standaard)
        # is not a thing and has to be set in HAProxy
        self.protocol = cherrypy.request.headers.get('X-Forwarded-Protocol',
                                                     'https')

        # sanity check
        if self.host not in (cherrypy.config['all_hosts']):
            self.host = cherrypy.config['host']
        if self.protocol not in VALID_PROTOCOLS:
            self.protocol = 'https'

        self.urlgen = routes.URLGenerator(cherrypy.routes_mapper,
                                          {'HTTP_HOST': self.host})

        self.set_format(k.get('format'))

        # query: this param is set when an actual query is requested

        self.query = ''
        if 'query' in k:
            self.query = SQLStatement.preprocess_query(k['query'])

        # search_terms: this is used to carry the last query
        # to display in the search input box

        self.search_terms = self.query or s.get('search_terms', '')

        self.sort_order = k.get('sort_order') or s.get(
            'sort_order') or USER_SORT_ORDERS[0]
        if self.sort_order not in USER_SORT_ORDERS:
            raise cherrypy.HTTPError(400, 'Bad Request. Unknown sort order.')
        s['sort_order'] = self.sort_order

        try:
            self.id = int(k.get('id') or '0')
            self.start_index = int(k.get('start_index') or '1')
            self.items_per_page = min(100,
                                      int(k.get('items_per_page') or '25'))
        except ValueError as what:
            raise cherrypy.HTTPError(400, 'Bad Request. ' + str(what))

        self.file_host = cherrypy.config['file_host']
        self.now = datetime.datetime.utcnow().replace(
            microsecond=0).isoformat() + 'Z'
        self.do_animations = 'Kindle/' not in self.user_agent  # no animations on e-ink
        self.ip = cherrypy.request.remote.ip
        self.type_opds = 'application/atom+xml;profile=opds-catalog'

        self.base_url = None
        self.canonical_url = None
        self.entries = []

        # NOTE: For page titles etc.
        self.pg = self.title = _('Project Gutenberg')
        # NOTE: The tagline at the top of every page.
        self.tagline = _(
            'Project Gutenberg offers {count} free ebooks to download.'
        ).format(count=self.books_in_archive)
        # NOTE: The site's description in the html meta tags.
        self.description = _(
            'Project Gutenberg offers {count} free ebooks for '
            'Kindle, iPad, Nook, Android, and iPhone.').format(
                count=self.books_in_archive)
        # NOTE: The placeholder inside an empty search box.
        self.placeholder = _('Search Project Gutenberg.')

        # these need to be here because they have to be localized
        # NOTE: Msg to user indicating the order of the search results.
        self.sorted_msgs = {
            'downloads': _("sorted by popularity"),
            'release_date': _("sorted by release date"),
            'quantity': _("sorted by quantity of books"),
            'title': _("sorted alphabetically"),
            'alpha': _("sorted alphabetically by title"),
            'author': _("sorted alphabetically by author"),
            'nentry': _("sorted by relevance"),
            'random': _("in random order"),
        }

        self.snippet_image_url = self.url('/pics/logo-144x144.png',
                                          host=self.file_host)
        self.og_type = 'website'
        self.class_ = ClassAttr()
        self.title_icon = None
        self.icon = None
        self.sort_orders = []
        self.alternate_sort_orders = []

        lang = self.lang = s.get('_lang_', 'en_US')
        if len(lang) == 2:
            lang = self.lang_to_default_locale.get(lang, 'en_US')
        lang2 = self.lang[:2]

        self.paypal_lang = lang if lang in PAYPAL_LANGS else 'en_US'
        self.flattr_lang = lang if lang in FLATTR_LANGS else 'en_US'

        lang = lang.replace('_', '-')

        self.google_lang = lang if lang in GOOGLE_LANGS else (
            lang2 if lang2 in GOOGLE_LANGS else 'en-US')
        lang = lang.lower()
        self.twitter_lang = lang if lang in TWITTER_LANGS else (
            lang2 if lang2 in TWITTER_LANGS else 'en')

        self.viewport = "width=device-width"  # , initial-scale=1.0"
        self.touch_icon = '/gutenberg/apple-icon.png'
        self.touch_icon_precomposed = None  # not yet used

        if 'user_dialog' in s:
            self.user_dialog = s['user_dialog']
            del s['user_dialog']

        msg = k.get('msg')
        if msg is not None:
            if msg == 'welcome_stranger':
                self.user_dialog = (_(
                    "Welcome to Project Gutenberg. "
                    "You'll find here {count} ebooks completely free of charge."
                ).format(count=self.books_in_archive), _('Welcome'))