Esempio n. 1
0
def qute_help(win_id, request):
    """Handler for qute:help. Return HTML content as bytes."""
    try:
        utils.read_file('html/doc/index.html')
    except FileNotFoundError:
        html = jinja.env.get_template('error.html').render(
            title="Error while loading documentation",
            url=request.url().toDisplayString(),
            error="This most likely means the documentation was not generated "
                  "properly. If you are running qutebrowser from the git "
                  "repository, please run scripts/asciidoc2html.py."
                  "If you're running a released version this is a bug, please "
                  "use :report to report it.",
            icon='')
        return html.encode('UTF-8', errors='xmlcharrefreplace')
    urlpath = request.url().path()
    if not urlpath or urlpath == '/':
        urlpath = 'index.html'
    else:
        urlpath = urlpath.lstrip('/')
    if not docutils.docs_up_to_date(urlpath):
        message.error(win_id, "Your documentation is outdated! Please re-run "
                      "scripts/asciidoc2html.py.")
    path = 'html/doc/{}'.format(urlpath)
    return utils.read_file(path).encode('UTF-8', errors='xmlcharrefreplace')
Esempio n. 2
0
def qute_help(url):
    """Handler for qute:help."""
    try:
        utils.read_file('html/doc/index.html')
    except OSError:
        html = jinja.render(
            'error.html',
            title="Error while loading documentation",
            url=url.toDisplayString(),
            error="This most likely means the documentation was not generated "
            "properly. If you are running qutebrowser from the git "
            "repository, please run scripts/asciidoc2html.py. "
            "If you're running a released version this is a bug, please "
            "use :report to report it.",
            icon='',
            qutescheme=True)
        return 'text/html', html
    urlpath = url.path()
    if not urlpath or urlpath == '/':
        urlpath = 'index.html'
    else:
        urlpath = urlpath.lstrip('/')
    if not docutils.docs_up_to_date(urlpath):
        message.error("Your documentation is outdated! Please re-run "
                      "scripts/asciidoc2html.py.")
    path = 'html/doc/{}'.format(urlpath)
    if urlpath.endswith('.png'):
        return 'image/png', utils.read_file(path, binary=True)
    else:
        data = utils.read_file(path)
        return 'text/html', data
Esempio n. 3
0
def qute_help(win_id, request):
    """Handler for qute:help. Return HTML content as bytes."""
    try:
        utils.read_file('html/doc/index.html')
    except FileNotFoundError:
        html = jinja.env.get_template('error.html').render(
            title="Error while loading documentation",
            url=request.url().toDisplayString(),
            error="This most likely means the documentation was not generated "
            "properly. If you are running qutebrowser from the git "
            "repository, please run scripts/asciidoc2html.py."
            "If you're running a released version this is a bug, please "
            "use :report to report it.",
            icon='')
        return html.encode('UTF-8', errors='xmlcharrefreplace')
    urlpath = request.url().path()
    if not urlpath or urlpath == '/':
        urlpath = 'index.html'
    else:
        urlpath = urlpath.lstrip('/')
    if not docutils.docs_up_to_date(urlpath):
        message.error(
            win_id, "Your documentation is outdated! Please re-run "
            "scripts/asciidoc2html.py.")
    path = 'html/doc/{}'.format(urlpath)
    return utils.read_file(path).encode('UTF-8', errors='xmlcharrefreplace')
Esempio n. 4
0
def qute_help(url):
    """Handler for qute:help."""
    try:
        utils.read_file('html/doc/index.html')
    except OSError:
        html = jinja.render(
            'error.html',
            title="Error while loading documentation",
            url=url.toDisplayString(),
            error="This most likely means the documentation was not generated "
                  "properly. If you are running qutebrowser from the git "
                  "repository, please run scripts/asciidoc2html.py. "
                  "If you're running a released version this is a bug, please "
                  "use :report to report it.",
            icon='',
            qutescheme=True)
        return 'text/html', html
    urlpath = url.path()
    if not urlpath or urlpath == '/':
        urlpath = 'index.html'
    else:
        urlpath = urlpath.lstrip('/')
    if not docutils.docs_up_to_date(urlpath):
        message.error("Your documentation is outdated! Please re-run "
                      "scripts/asciidoc2html.py.")
    path = 'html/doc/{}'.format(urlpath)
    if urlpath.endswith('.png'):
        return 'image/png', utils.read_file(path, binary=True)
    else:
        data = utils.read_file(path)
        return 'text/html', data
Esempio n. 5
0
def qute_help(url):
    """Handler for qute://help."""
    urlpath = url.path()
    if not urlpath or urlpath == '/':
        urlpath = 'index.html'
    else:
        urlpath = urlpath.lstrip('/')
    if not docutils.docs_up_to_date(urlpath):
        message.error("Your documentation is outdated! Please re-run "
                      "scripts/asciidoc2html.py.")

    path = 'html/doc/{}'.format(urlpath)
    if not urlpath.endswith('.html'):
        try:
            bdata = utils.read_file(path, binary=True)
        except OSError as e:
            raise QuteSchemeOSError(e)
        mimetype, _encoding = mimetypes.guess_type(urlpath)
        assert mimetype is not None, url
        return mimetype, bdata

    try:
        data = utils.read_file(path)
    except OSError:
        # No .html around, let's see if we find the asciidoc
        asciidoc_path = path.replace('.html', '.asciidoc')
        if asciidoc_path.startswith('html/doc/'):
            asciidoc_path = asciidoc_path.replace('html/doc/', '../doc/help/')

        try:
            asciidoc = utils.read_file(asciidoc_path)
        except OSError:
            asciidoc = None

        if asciidoc is None:
            raise

        preamble = textwrap.dedent("""
            There was an error loading the documentation!

            This most likely means the documentation was not generated
            properly. If you are running qutebrowser from the git repository,
            please (re)run scripts/asciidoc2html.py and reload this page.

            If you're running a released version this is a bug, please use
            :report to report it.

            Falling back to the plaintext version.

            ---------------------------------------------------------------


        """)
        return 'text/plain', (preamble + asciidoc).encode('utf-8')
    else:
        return 'text/html', data
Esempio n. 6
0
def qute_help(url):
    """Handler for qute://help."""
    urlpath = url.path()
    if not urlpath or urlpath == '/':
        urlpath = 'index.html'
    else:
        urlpath = urlpath.lstrip('/')
    if not docutils.docs_up_to_date(urlpath):
        message.error("Your documentation is outdated! Please re-run "
                      "scripts/asciidoc2html.py.")

    path = 'html/doc/{}'.format(urlpath)
    if not urlpath.endswith('.html'):
        try:
            bdata = utils.read_file(path, binary=True)
        except OSError as e:
            raise QuteSchemeOSError(e)
        mimetype, _encoding = mimetypes.guess_type(urlpath)
        assert mimetype is not None, url
        return mimetype, bdata

    try:
        data = utils.read_file(path)
    except OSError:
        # No .html around, let's see if we find the asciidoc
        asciidoc_path = path.replace('.html', '.asciidoc')
        if asciidoc_path.startswith('html/doc/'):
            asciidoc_path = asciidoc_path.replace('html/doc/', '../doc/help/')

        try:
            asciidoc = utils.read_file(asciidoc_path)
        except OSError:
            asciidoc = None

        if asciidoc is None:
            raise

        preamble = textwrap.dedent("""
            There was an error loading the documentation!

            This most likely means the documentation was not generated
            properly. If you are running qutebrowser from the git repository,
            please (re)run scripts/asciidoc2html.py and reload this page.

            If you're running a released version this is a bug, please use
            :report to report it.

            Falling back to the plaintext version.

            ---------------------------------------------------------------


        """)
        return 'text/plain', (preamble + asciidoc).encode('utf-8')
    else:
        return 'text/html', data
Esempio n. 7
0
    def _init_js(self):
        """Initialize global qutebrowser JavaScript."""
        js_code = javascript.wrap_global(
            'scripts',
            utils.read_file('javascript/scroll.js'),
            utils.read_file('javascript/webelem.js'),
            utils.read_file('javascript/caret.js'),
        )
        # FIXME:qtwebengine what about subframes=True?
        self._inject_early_js('js', js_code, subframes=True)
        self._init_stylesheet()

        greasemonkey = objreg.get('greasemonkey')
        greasemonkey.scripts_reloaded.connect(self._inject_userscripts)
        self._inject_userscripts()
Esempio n. 8
0
    def _init_js(self):
        js_code = '\n'.join([
            '"use strict";',
            'window._qutebrowser = {};',
            utils.read_file('javascript/scroll.js'),
            utils.read_file('javascript/webelem.js'),
        ])
        script = QWebEngineScript()
        script.setInjectionPoint(QWebEngineScript.DocumentCreation)
        script.setSourceCode(js_code)

        page = self._widget.page()
        script.setWorldId(QWebEngineScript.ApplicationWorld)

        # FIXME:qtwebengine  what about runsOnSubFrames?
        page.scripts().insert(script)
Esempio n. 9
0
    def on_mode_entered(self, mode):
        """Ignore attempts to focus the widget if in any status-input mode."""
        if mode in (usertypes.KeyMode.command, usertypes.KeyMode.prompt,
                    usertypes.KeyMode.yesno):
            log.webview.debug("Ignoring focus because mode {} was "
                              "entered.".format(mode))
            self.setFocusPolicy(Qt.NoFocus)
        elif mode == usertypes.KeyMode.caret:
            settings = self.settings()
            settings.setAttribute(QWebSettings.CaretBrowsingEnabled, True)
            self.selection_enabled = bool(self.page().selectedText())

            if self.isVisible():
                # Sometimes the caret isn't immediately visible, but unfocusing
                # and refocusing it fixes that.
                self.clearFocus()
                self.setFocus(Qt.OtherFocusReason)

                # Move the caret to the first element in the viewport if there
                # isn't any text which is already selected.
                #
                # Note: We can't use hasSelection() here, as that's always
                # true in caret mode.
                if not self.page().selectedText():
                    self.page().currentFrame().evaluateJavaScript(
                        utils.read_file('javascript/position_caret.js'))
Esempio n. 10
0
def _init_stylesheet(profile):
    """Initialize custom stylesheets.

    Partially inspired by QupZilla:
    https://github.com/QupZilla/qupzilla/blob/v2.0/src/lib/app/mainapplication.cpp#L1063-L1101
    """
    old_script = profile.scripts().findScript('_qute_stylesheet')
    if not old_script.isNull():
        profile.scripts().remove(old_script)

    css = shared.get_user_stylesheet()
    source = '\n'.join([
        '"use strict";',
        'window._qutebrowser = window._qutebrowser || {};',
        utils.read_file('javascript/stylesheet.js'),
        javascript.assemble('stylesheet', 'set_css', css),
    ])

    script = QWebEngineScript()
    script.setName('_qute_stylesheet')
    script.setInjectionPoint(QWebEngineScript.DocumentCreation)
    script.setWorldId(QWebEngineScript.ApplicationWorld)
    script.setRunsOnSubFrames(True)
    script.setSourceCode(source)
    profile.scripts().insert(script)
Esempio n. 11
0
def get_pdfjs_res_and_path(path):
    """Get a pdf.js resource in binary format.

    Returns a (content, path) tuple, where content is the file content and path
    is the path where the file was found. If path is None, the bundled version
    was used.

    Args:
        path: The path inside the pdfjs directory.
    """
    path = path.lstrip('/')
    content = None
    file_path = None

    # First try a system wide installation
    # System installations might strip off the 'build/' or 'web/' prefixes.
    # qute expects them, so we need to adjust for it.
    names_to_try = [path, _remove_prefix(path)]
    for system_path in SYSTEM_PDFJS_PATHS:
        content, file_path = _read_from_system(system_path, names_to_try)
        if content is not None:
            break

    # Fallback to bundled pdf.js
    if content is None:
        res_path = '3rdparty/pdfjs/{}'.format(path)
        try:
            content = utils.read_file(res_path, binary=True)
        except FileNotFoundError:
            raise PDFJSNotFound(path) from None

    return content, file_path
Esempio n. 12
0
    def __init__(self, pac_str):
        """Create a PAC resolver.

        Args:
            pac_str: JavaScript code containing PAC resolver.
        """
        self._engine = QJSEngine()

        self._engine.installExtensions(QJSEngine.ConsoleExtension)

        self._ctx = _PACContext(self._engine)
        self._engine.globalObject().setProperty(
            "PAC", self._engine.newQObject(self._ctx))
        self._evaluate(_PACContext.JS_DEFINITIONS, "pac_js_definitions")
        self._evaluate(utils.read_file("javascript/pac_utils.js"), "pac_utils")
        proxy_config = self._engine.newObject()
        proxy_config.setProperty("bindings", self._engine.newObject())
        self._engine.globalObject().setProperty("ProxyConfig", proxy_config)

        self._evaluate(pac_str, "pac")
        global_js_object = self._engine.globalObject()
        self._resolver = global_js_object.property("FindProxyForURL")
        if not self._resolver.isCallable():
            err = "Cannot resolve FindProxyForURL function, got '{}' instead"
            raise EvalProxyError(err.format(self._resolver.toString()))
Esempio n. 13
0
    def __init__(self, pac_str):
        """Create a PAC resolver.

        Args:
            pac_str: JavaScript code containing PAC resolver.
        """
        self._engine = QJSEngine()

        self._engine.installExtensions(QJSEngine.ConsoleExtension)

        self._ctx = _PACContext(self._engine)
        self._engine.globalObject().setProperty(
            "PAC", self._engine.newQObject(self._ctx))
        self._evaluate(_PACContext.JS_DEFINITIONS, "pac_js_definitions")
        self._evaluate(utils.read_file("javascript/pac_utils.js"), "pac_utils")
        proxy_config = self._engine.newObject()
        proxy_config.setProperty("bindings", self._engine.newObject())
        self._engine.globalObject().setProperty("ProxyConfig", proxy_config)

        self._evaluate(pac_str, "pac")
        global_js_object = self._engine.globalObject()
        self._resolver = global_js_object.property("FindProxyForURL")
        if not self._resolver.isCallable():
            err = "Cannot resolve FindProxyForURL function, got '{}' instead"
            raise EvalProxyError(err.format(self._resolver.toString()))
Esempio n. 14
0
    def _on_mode_entered(self, mode):
        if mode != usertypes.KeyMode.caret:
            return

        if self._widget.hasSelection():
            self._selection_state = browsertab.SelectionState.normal
        else:
            self._selection_state = browsertab.SelectionState.none
        self.selection_toggled.emit(self._selection_state)
        settings = self._widget.settings()
        settings.setAttribute(QWebSettings.CaretBrowsingEnabled, True)

        if self._widget.isVisible():
            # Sometimes the caret isn't immediately visible, but unfocusing
            # and refocusing it fixes that.
            self._widget.clearFocus()
            self._widget.setFocus(Qt.OtherFocusReason)

            # Move the caret to the first element in the viewport if there
            # isn't any text which is already selected.
            #
            # Note: We can't use hasSelection() here, as that's always
            # true in caret mode.
            if self._selection_state is browsertab.SelectionState.none:
                self._widget.page().currentFrame().evaluateJavaScript(
                    utils.read_file('javascript/position_caret.js'))
Esempio n. 15
0
def _init_stylesheet(profile):
    """Initialize custom stylesheets.

    Partially inspired by QupZilla:
    https://github.com/QupZilla/qupzilla/blob/v2.0/src/lib/app/mainapplication.cpp#L1063-L1101
    """
    old_script = profile.scripts().findScript('_qute_stylesheet')
    if not old_script.isNull():
        profile.scripts().remove(old_script)

    css = shared.get_user_stylesheet()
    source = '\n'.join([
        '"use strict";',
        'window._qutebrowser = window._qutebrowser || {};',
        utils.read_file('javascript/stylesheet.js'),
        javascript.assemble('stylesheet', 'set_css', css),
    ])

    script = QWebEngineScript()
    script.setName('_qute_stylesheet')
    script.setInjectionPoint(QWebEngineScript.DocumentCreation)
    script.setWorldId(QWebEngineScript.ApplicationWorld)
    script.setRunsOnSubFrames(True)
    script.setSourceCode(source)
    profile.scripts().insert(script)
Esempio n. 16
0
def get_pdfjs_res(path):
    """Get a pdf.js resource in binary format.

    Args:
        path: The path inside the pdfjs directory.
    """
    path = path.lstrip('/')
    content = None

    # First try a system wide installation
    # System installations might strip off the 'build/' or 'web/' prefixes.
    # qute expects them, so we need to adjust for it.
    names_to_try = [path, _remove_prefix(path)]
    for system_path in SYSTEM_PDFJS_PATHS:
        content = _read_from_system(system_path, names_to_try)
        if content is not None:
            break

    # Fallback to bundled pdf.js
    if content is None:
        res_path = '3rdparty/pdfjs/{}'.format(path)
        try:
            content = utils.read_file(res_path, binary=True)
        except FileNotFoundError:
            raise PDFJSNotFound

    try:
        # Might be script/html or might be binary
        text_content = content.decode('utf-8')
    except UnicodeDecodeError:
        return content
    text_content = fix_urls(text_content)
    return text_content.encode('utf-8')
Esempio n. 17
0
    def _init_js(self):
        js_code = '\n'.join([
            '"use strict";',
            'window._qutebrowser = {};',
            utils.read_file('javascript/scroll.js'),
            utils.read_file('javascript/webelem.js'),
        ])
        script = QWebEngineScript()
        script.setInjectionPoint(QWebEngineScript.DocumentCreation)
        script.setSourceCode(js_code)

        page = self._widget.page()
        script.setWorldId(QWebEngineScript.ApplicationWorld)

        # FIXME:qtwebengine  what about runsOnSubFrames?
        page.scripts().insert(script)
Esempio n. 18
0
 def _data_url(self, path):
     """Get a data: url for the broken qutebrowser logo."""
     data = utils.read_file(path, binary=True)
     filename = utils.resource_filename(path)
     mimetype = mimetypes.guess_type(filename)
     assert mimetype is not None, path
     return urlutils.data_url(mimetype[0], data).toString()
Esempio n. 19
0
def _asciidoc_fallback_path(html_path: str) -> Optional[str]:
    """Fall back to plaintext asciidoc if the HTML is unavailable."""
    path = html_path.replace('.html', '.asciidoc')
    try:
        return utils.read_file(path)
    except OSError:
        return None
Esempio n. 20
0
def _asciidoc_fallback_path(html_path):
    """Fall back to plaintext asciidoc if the HTML is unavailable."""
    path = html_path.replace('.html', '.asciidoc')
    try:
        return utils.read_file(path)
    except OSError:
        return None
Esempio n. 21
0
def get_pdfjs_res(path):
    """Get a pdf.js resource in binary format.

    Args:
        path: The path inside the pdfjs directory.
    """
    path = path.lstrip('/')
    content = None

    # First try a system wide installation
    # System installations might strip off the 'build/' or 'web/' prefixes.
    # qute expects them, so we need to adjust for it.
    names_to_try = [path, _remove_prefix(path)]
    for system_path in SYSTEM_PDFJS_PATHS:
        content = _read_from_system(system_path, names_to_try)
        if content is not None:
            break

    # Fallback to bundled pdf.js
    if content is None:
        res_path = '3rdparty/pdfjs/{}'.format(path)
        try:
            content = utils.read_file(res_path, binary=True)
        except FileNotFoundError:
            raise PDFJSNotFound

    try:
        # Might be script/html or might be binary
        text_content = content.decode('utf-8')
    except UnicodeDecodeError:
        return content
    text_content = fix_urls(text_content)
    return text_content.encode('utf-8')
Esempio n. 22
0
 def to_perc(self, x=None, y=None):
     js_code = """
         {scroll_js}
         scroll_to_perc({x}, {y});
     """.format(scroll_js=utils.read_file('javascript/scroll.js'),
                x='undefined' if x is None else x,
                y='undefined' if y is None else y)
     self._tab.run_js_async(js_code)
Esempio n. 23
0
def data_url(path):
    """Get a data: url for the broken qutebrowser logo."""
    data = utils.read_file(path, binary=True)
    filename = utils.resource_filename(path)
    mimetype = mimetypes.guess_type(filename)
    assert mimetype is not None, path
    b64 = base64.b64encode(data).decode('ascii')
    return 'data:{};charset=utf-8;base64,{}'.format(mimetype[0], b64)
Esempio n. 24
0
def assemble(name, function, *args):
    """Assemble a javascript file and a function call."""
    code = "{code}\n_qutebrowser_{function}({args});".format(
        code=utils.read_file('javascript/{}.js'.format(name)),
        function=function,
        args=', '.join(_convert_js_arg(arg) for arg in args),
    )
    return code
Esempio n. 25
0
 def get_source(self, _env, template):
     path = os.path.join(self._subdir, template)
     try:
         source = utils.read_file(path)
     except OSError:
         raise jinja2.TemplateNotFound(template)
     # Currently we don't implement auto-reloading, so we always return True
     # for up-to-date.
     return source, path, lambda: True
Esempio n. 26
0
def render(template, **kwargs):
    """Render the given template and pass the given arguments to it."""
    try:
        return _env.get_template(template).render(**kwargs)
    except jinja2.exceptions.UndefinedError:
        log.misc.exception("UndefinedError while rendering " + template)
        err_path = os.path.join('html', 'undef_error.html')
        err_template = utils.read_file(err_path)
        tb = traceback.format_exc()
        return err_template.format(pagename=template, traceback=tb)
Esempio n. 27
0
    def _init_js(self):
        js_code = '\n'.join([
            '"use strict";',
            'window._qutebrowser = window._qutebrowser || {};',
            utils.read_file('javascript/scroll.js'),
            utils.read_file('javascript/webelem.js'),
            utils.read_file('javascript/caret.js'),
        ])
        script = QWebEngineScript()
        # We can't use DocumentCreation here as WORKAROUND for
        # https://bugreports.qt.io/browse/QTBUG-66011
        script.setInjectionPoint(QWebEngineScript.DocumentReady)
        script.setSourceCode(js_code)

        page = self._widget.page()
        script.setWorldId(QWebEngineScript.ApplicationWorld)

        # FIXME:qtwebengine  what about runsOnSubFrames?
        page.scripts().insert(script)
Esempio n. 28
0
    def run_file(self, filename: str, expected=None) -> None:
        """Run a javascript file.

        Args:
            filename: The javascript filename, relative to
                      qutebrowser/javascript.
            expected: The value expected return from the javascript execution
        """
        source = utils.read_file(os.path.join('javascript', filename))
        self.run(source, expected)
Esempio n. 29
0
    def _init_js(self):
        js_code = '\n'.join([
            '"use strict";',
            'window._qutebrowser = window._qutebrowser || {};',
            utils.read_file('javascript/scroll.js'),
            utils.read_file('javascript/webelem.js'),
            utils.read_file('javascript/caret.js'),
        ])
        script = QWebEngineScript()
        # We can't use DocumentCreation here as WORKAROUND for
        # https://bugreports.qt.io/browse/QTBUG-66011
        script.setInjectionPoint(QWebEngineScript.DocumentReady)
        script.setSourceCode(js_code)

        page = self._widget.page()
        script.setWorldId(QWebEngineScript.ApplicationWorld)

        # FIXME:qtwebengine  what about runsOnSubFrames?
        page.scripts().insert(script)
Esempio n. 30
0
    def run_file(self, filename: str, expected=None) -> None:
        """Run a javascript file.

        Args:
            filename: The javascript filename, relative to
                      qutebrowser/javascript.
            expected: The value expected return from the javascript execution
        """
        source = utils.read_file(os.path.join('javascript', filename))
        self.run(source, expected)
Esempio n. 31
0
def qute_javascript(url):
    """Handler for qute://javascript.

    Return content of file given as query parameter.
    """
    path = url.path()
    if path:
        path = "javascript" + os.sep.join(path.split('/'))
        return 'text/html', utils.read_file(path, binary=False)
    else:
        raise UrlInvalidError("No file specified")
Esempio n. 32
0
def qute_javascript(url):
    """Handler for qute://javascript.

    Return content of file given as query parameter.
    """
    path = url.path()
    if path:
        path = "javascript" + os.sep.join(path.split('/'))
        return 'text/html', utils.read_file(path, binary=False)
    else:
        raise UrlInvalidError("No file specified")
Esempio n. 33
0
 def get_source(self, _env, template):
     path = os.path.join(self._subdir, template)
     try:
         source = utils.read_file(path)
     except OSError as e:
         source = html_fallback.replace("%ERROR%", html.escape(str(e)))
         source = source.replace("%FILE%", html.escape(template))
         log.misc.exception("The {} template could not be loaded from {}"
                            .format(template, path))
     # Currently we don't implement auto-reloading, so we always return True
     # for up-to-date.
     return source, path, lambda: True
Esempio n. 34
0
    def run_file(self, filename):
        """Run a javascript file.

        Args:
            filename: The javascript filename, relative to
                      qutebrowser/javascript.

        Return:
            The javascript return value.
        """
        source = utils.read_file(os.path.join('javascript', filename))
        return self.run(source)
Esempio n. 35
0
    def run_file(self, filename):
        """Run a javascript file.

        Args:
            filename: The javascript filename, relative to
                      qutebrowser/javascript.

        Return:
            The javascript return value.
        """
        source = utils.read_file(os.path.join('javascript', filename))
        return self.run(source)
Esempio n. 36
0
def get_pdfjs_res_and_path(path):
    """Get a pdf.js resource in binary format.

    Returns a (content, path) tuple, where content is the file content and path
    is the path where the file was found. If path is None, the bundled version
    was used.

    Args:
        path: The path inside the pdfjs directory.
    """
    path = path.lstrip('/')
    content = None
    file_path = None

    system_paths = [
        # Debian pdf.js-common
        # Arch Linux pdfjs (AUR)
        '/usr/share/pdf.js/',
        # Flatpak (Flathub)
        '/app/share/pdf.js/',
        # Arch Linux pdf.js (AUR)
        '/usr/share/javascript/pdf.js/',
        # Debian libjs-pdf
        '/usr/share/javascript/pdf/',
        # fallback to bundled pdf.js on windows
        ##        os.path.join(os.getcwd(), '3rdparty', 'pdfjs'),
        # fallback
        os.path.join(standarddir.data(), 'pdfjs'),
        # hardcoded fallback for --temp-basedir
        os.path.expanduser('~/.local/share/qutebrowser/pdfjs/'),
    ]

    # First try a system wide installation
    # System installations might strip off the 'build/' or 'web/' prefixes.
    # qute expects them, so we need to adjust for it.
    names_to_try = [path, _remove_prefix(path)]
    for system_path in system_paths:
        content, file_path = _read_from_system(system_path, names_to_try)
        if content is not None:
            break

    # Fallback to bundled pdf.js
    if content is None:
        res_path = '3rdparty/pdfjs/{}'.format(path)
        try:
            content = utils.read_file(file_path, binary=True)
        except FileNotFoundError:
            raise PDFJSNotFound(path) from None
        except OSError as e:
            log.misc.warning("OSError while reading PDF.js file: {}".format(e))
            raise PDFJSNotFound(path) from None

    return content, file_path
Esempio n. 37
0
    def _init_js(self):
        js_code = '\n'.join([
            '"use strict";',
            'window._qutebrowser = {};',
            utils.read_file('javascript/scroll.js'),
            utils.read_file('javascript/webelem.js'),
        ])
        script = QWebEngineScript()
        script.setInjectionPoint(QWebEngineScript.DocumentCreation)
        page = self._widget.page()
        script.setSourceCode(js_code)

        try:
            page.runJavaScript("", QWebEngineScript.ApplicationWorld)
        except TypeError:
            # We're unable to pass a world to runJavaScript
            script.setWorldId(QWebEngineScript.MainWorld)
        else:
            script.setWorldId(QWebEngineScript.ApplicationWorld)

        # FIXME:qtwebengine  what about runsOnSubFrames?
        page.scripts().insert(script)
Esempio n. 38
0
    def _init_js(self):
        js_code = '\n'.join([
            '"use strict";',
            'window._qutebrowser = {};',
            utils.read_file('javascript/scroll.js'),
            utils.read_file('javascript/webelem.js'),
        ])
        script = QWebEngineScript()
        script.setInjectionPoint(QWebEngineScript.DocumentCreation)
        page = self._widget.page()
        script.setSourceCode(js_code)

        try:
            page.runJavaScript("", QWebEngineScript.ApplicationWorld)
        except TypeError:
            # We're unable to pass a world to runJavaScript
            script.setWorldId(QWebEngineScript.MainWorld)
        else:
            script.setWorldId(QWebEngineScript.ApplicationWorld)

        # FIXME:qtwebengine  what about runsOnSubFrames?
        page.scripts().insert(script)
Esempio n. 39
0
    def _on_scroll_pos_changed(self):
        """Update the scroll position attributes when it changed."""
        def update_scroll_pos(jsret):
            """Callback after getting scroll position via JS."""
            assert isinstance(jsret, dict)
            self._pos_perc = (jsret['perc']['x'], jsret['perc']['y'])
            self._pos_px = QPoint(jsret['px']['x'], jsret['px']['y'])
            self.perc_changed.emit(*self._pos_perc)

        js_code = """
            {scroll_js}
            scroll_pos();
        """.format(scroll_js=utils.read_file('javascript/scroll.js'))
        self._tab.run_js_async(js_code, update_scroll_pos)
Esempio n. 40
0
    def _init_stylesheet(self):
        """Initialize custom stylesheets.

        Partially inspired by QupZilla:
        https://github.com/QupZilla/qupzilla/blob/v2.0/src/lib/app/mainapplication.cpp#L1063-L1101
        """
        self._remove_early_js('stylesheet')
        css = shared.get_user_stylesheet()
        js_code = javascript.wrap_global(
            'stylesheet',
            utils.read_file('javascript/stylesheet.js'),
            javascript.assemble('stylesheet', 'set_css', css),
        )
        self._inject_early_js('stylesheet', js_code, subframes=True)
Esempio n. 41
0
def get_pdfjs_res_and_path(path):
    """Get a pdf.js resource in binary format.

    Returns a (content, path) tuple, where content is the file content and path
    is the path where the file was found. If path is None, the bundled version
    was used.

    Args:
        path: The path inside the pdfjs directory.
    """
    path = path.lstrip('/')
    content = None
    file_path = None

    system_paths = [
        # Debian pdf.js-common
        # Arch Linux pdfjs (AUR)
        '/usr/share/pdf.js/',
        # Arch Linux pdf.js (AUR)
        '/usr/share/javascript/pdf.js/',
        # Debian libjs-pdf
        '/usr/share/javascript/pdf/',
        # fallback
        os.path.join(standarddir.data(), 'pdfjs'),
        # hardcoded fallback for --temp-basedir
        os.path.expanduser('~/.local/share/qutebrowser/pdfjs/'),
    ]

    # First try a system wide installation
    # System installations might strip off the 'build/' or 'web/' prefixes.
    # qute expects them, so we need to adjust for it.
    names_to_try = [path, _remove_prefix(path)]
    for system_path in system_paths:
        content, file_path = _read_from_system(system_path, names_to_try)
        if content is not None:
            break

    # Fallback to bundled pdf.js
    if content is None:
        res_path = '3rdparty/pdfjs/{}'.format(path)
        try:
            content = utils.read_file(res_path, binary=True)
        except FileNotFoundError:
            raise PDFJSNotFound(path) from None
        except OSError as e:
            log.misc.warning("OSError while reading PDF.js file: {}".format(e))
            raise PDFJSNotFound(path) from None

    return content, file_path
Esempio n. 42
0
def _asciidoc_fallback_path(html_path):
    """Fall back to plaintext asciidoc if the HTML is unavailable."""
    asciidoc_path = html_path.replace('.html', '.asciidoc')
    asciidoc_paths = [asciidoc_path]
    if asciidoc_path.startswith('html/doc/'):
        asciidoc_paths += [asciidoc_path.replace('html/doc/', '../doc/help/'),
                           asciidoc_path.replace('html/doc/', '../doc/')]

    for path in asciidoc_paths:
        try:
            return utils.read_file(path)
        except OSError:
            pass

    return None
Esempio n. 43
0
def qute_help(url: QUrl) -> _HandlerRet:
    """Handler for qute://help."""
    urlpath = url.path()
    if not urlpath or urlpath == '/':
        urlpath = 'index.html'
    else:
        urlpath = urlpath.lstrip('/')
    if not docutils.docs_up_to_date(urlpath):
        message.error("Your documentation is outdated! Please re-run "
                      "scripts/asciidoc2html.py.")

    path = 'html/doc/{}'.format(urlpath)
    if not urlpath.endswith('.html'):
        try:
            bdata = utils.read_file_binary(path)
        except OSError as e:
            raise SchemeOSError(e)
        mimetype = utils.guess_mimetype(urlpath)
        return mimetype, bdata

    try:
        data = utils.read_file(path)
    except OSError:
        asciidoc = _asciidoc_fallback_path(path)

        if asciidoc is None:
            raise

        preamble = textwrap.dedent("""
            There was an error loading the documentation!

            This most likely means the documentation was not generated
            properly. If you are running qutebrowser from the git repository,
            please (re)run scripts/asciidoc2html.py and reload this page.

            If you're running a released version this is a bug, please use
            :report to report it.

            Falling back to the plaintext version.

            ---------------------------------------------------------------


        """)
        return 'text/plain', (preamble + asciidoc).encode('utf-8')
    else:
        return 'text/html', data
Esempio n. 44
0
def _asciidoc_fallback_path(html_path):
    """Fall back to plaintext asciidoc if the HTML is unavailable."""
    asciidoc_path = html_path.replace('.html', '.asciidoc')
    asciidoc_paths = [asciidoc_path]
    if asciidoc_path.startswith('html/doc/'):
        asciidoc_paths += [
            asciidoc_path.replace('html/doc/', '../doc/help/'),
            asciidoc_path.replace('html/doc/', '../doc/')
        ]

    for path in asciidoc_paths:
        try:
            return utils.read_file(path)
        except OSError:
            pass

    return None
Esempio n. 45
0
    def on_mode_entered(self, mode):
        """Ignore attempts to focus the widget if in any status-input mode."""
        if mode in (usertypes.KeyMode.command, usertypes.KeyMode.prompt,
                    usertypes.KeyMode.yesno):
            log.webview.debug("Ignoring focus because mode {} was "
                              "entered.".format(mode))
            self.setFocusPolicy(Qt.NoFocus)
        elif mode == usertypes.KeyMode.caret:
            settings = self.settings()
            settings.setAttribute(QWebSettings.CaretBrowsingEnabled, True)
            self.selection_enabled = False

            if self.isVisible():
                # Sometimes the caret isn't immediately visible, but unfocusing
                # and refocusing it fixes that.
                self.clearFocus()
                self.setFocus(Qt.OtherFocusReason)
                self.page().currentFrame().evaluateJavaScript(
                    utils.read_file('javascript/position_caret.js'))
Esempio n. 46
0
    def _on_mode_entered(self, mode):
        if mode != usertypes.KeyMode.caret:
            return

        settings = self._widget.settings()
        settings.setAttribute(QWebSettings.CaretBrowsingEnabled, True)
        self.selection_enabled = bool(self.selection())

        if self._widget.isVisible():
            # Sometimes the caret isn't immediately visible, but unfocusing
            # and refocusing it fixes that.
            self._widget.clearFocus()
            self._widget.setFocus(Qt.OtherFocusReason)

            # Move the caret to the first element in the viewport if there
            # isn't any text which is already selected.
            #
            # Note: We can't use hasSelection() here, as that's always
            # true in caret mode.
            if not self.selection():
                self._widget.page().currentFrame().evaluateJavaScript(utils.read_file("javascript/position_caret.js"))
Esempio n. 47
0
def get_pdfjs_res_and_path(path):
    """Get a pdf.js resource in binary format.

    Returns a (content, path) tuple, where content is the file content and path
    is the path where the file was found. If path is None, the bundled version
    was used.

    Args:
        path: The path inside the pdfjs directory.
    """
    path = path.lstrip("/")
    content = None
    file_path = None

    # First try a system wide installation
    # System installations might strip off the 'build/' or 'web/' prefixes.
    # qute expects them, so we need to adjust for it.
    names_to_try = [path, _remove_prefix(path)]
    for system_path in SYSTEM_PDFJS_PATHS:
        content, file_path = _read_from_system(system_path, names_to_try)
        if content is not None:
            break

    # Fallback to bundled pdf.js
    if content is None:
        res_path = "3rdparty/pdfjs/{}".format(path)
        try:
            content = utils.read_file(res_path, binary=True)
        except FileNotFoundError:
            raise PDFJSNotFound(path) from None

    try:
        # Might be script/html or might be binary
        text_content = content.decode("utf-8")
    except UnicodeDecodeError:
        return (content, file_path)
    text_content = fix_urls(text_content)
    return (text_content.encode("utf-8"), file_path)
Esempio n. 48
0
def _git_str():
    """Try to find out git version.

    Return:
        string containing the git commit ID.
        None if there was an error or we're not in a git repo.
    """
    # First try via subprocess if possible
    commit = None
    if not hasattr(sys, "frozen"):
        try:
            gitpath = os.path.join(os.path.dirname(os.path.realpath(__file__)), os.path.pardir, os.path.pardir)
        except (NameError, OSError):
            log.misc.exception("Error while getting git path")
        else:
            commit = _git_str_subprocess(gitpath)
    if commit is not None:
        return commit
    # If that fails, check the git-commit-id file.
    try:
        return utils.read_file("git-commit-id")
    except (OSError, ImportError):
        return None
Esempio n. 49
0
def _git_str():
    """Try to find out git version.

    Return:
        string containing the git commit ID.
        None if there was an error or we're not in a git repo.
    """
    # First try via subprocess if possible
    commit = None
    if not hasattr(sys, "frozen"):
        try:
            gitpath = os.path.join(os.path.dirname(os.path.realpath(__file__)),
                                   os.path.pardir, os.path.pardir)
        except (NameError, OSError):
            log.misc.exception("Error while getting git path")
        else:
            commit = _git_str_subprocess(gitpath)
    if commit is not None:
        return commit
    # If that fails, check the git-commit-id file.
    try:
        return utils.read_file('git-commit-id')
    except (OSError, ImportError):
        return None
Esempio n. 50
0
def qute_gpl(_win_id, _request):
    """Handler for qute:gpl. Return HTML content as bytes."""
    return utils.read_file('html/COPYING.html').encode('ASCII')
Esempio n. 51
0
def qute_resource(url):
    """Serve resources via a qute://resource/... URL."""
    data = utils.read_file(url.path(), binary=True)
    mimetype, _encoding = mimetypes.guess_type(url.fileName())
    assert mimetype is not None, url
    return mimetype, data
Esempio n. 52
0
def init() -> None:
    """Initialize configdata from the YAML file."""
    global DATA, MIGRATIONS
    DATA, MIGRATIONS = _read_yaml(utils.read_file('config/configdata.yml'))
Esempio n. 53
0
def qute_gpl(_url):
    """Handler for qute://gpl. Return HTML content as string."""
    return 'text/html', utils.read_file('html/license.html')
Esempio n. 54
0
def init():
    """Initialize configdata from the YAML file."""
    global DATA
    DATA = _read_yaml(utils.read_file('config/configdata.yml'))
Esempio n. 55
0
def qute_gpl(_url):
    """Handler for qute:gpl. Return HTML content as string."""
    return 'text/html', utils.read_file('html/COPYING.html')