Пример #1
0
    def load_plugins(self, path: str) -> bool:
        """Attempt to load plugins from the path specified.

        :param path: full path to a directory where to look for plugins
        :return: success
        """
        success = False
        user_input_requester = self.get_option("user-input-requester")
        for loader, name, ispkg in pkgutil.iter_modules([path]):
            # set the full plugin module name
            module_name = f"streamlink.plugins.{name}"
            try:
                mod = load_module(module_name, path)
            except ImportError:
                log.exception(f"Failed to load plugin {name} from {path}\n")
                continue

            if not hasattr(mod, "__plugin__") or not issubclass(
                    mod.__plugin__, Plugin):
                continue
            success = True
            plugin = mod.__plugin__
            plugin.bind(self, name, user_input_requester)
            if plugin.module in self.plugins:
                log.debug(
                    f"Plugin {plugin.module} is being overridden by {mod.__file__}"
                )
            self.plugins[plugin.module] = plugin

        return success
Пример #2
0
    def __new__(mcs, name, bases, dict):
        plugin_path = os.path.dirname(streamlink.plugins.__file__)
        plugins = []
        for loader, pname, ispkg in pkgutil.iter_modules([plugin_path]):
            module = load_module(pname, plugin_path)
            if hasattr(module, "__plugin__"):
                plugins.append((pname))

        session = Streamlink()

        def gentest(pname):
            def load_plugin_test(self):
                # Reset file variable to ensure it is still open when doing
                # load_plugin else python might open the plugin source .py
                # using ascii encoding instead of utf-8.
                # See also open() call here: imp._HackedGetData.get_data
                file, pathname, desc = imp.find_module(pname, [plugin_path])
                session.load_plugin(pname, file, pathname, desc)
                # validate that can_handle_url does not fail
                session.plugins[pname].can_handle_url("http://test.com")

            return load_plugin_test

        for pname in plugins:
            dict['test_{0}_load'.format(pname)] = gentest(pname)

        return type.__new__(mcs, name, bases, dict)
Пример #3
0
    def __new__(mcs, name, bases, dict):
        plugin_path = os.path.dirname(streamlink.plugins.__file__)
        plugins = []
        for loader, pname, ispkg in pkgutil.iter_modules([plugin_path]):
            module = load_module(f"streamlink.plugins.{pname}", plugin_path)
            if hasattr(module, "__plugin__"):
                plugins.append((loader, pname))

        def gentest(loader, pname):
            def load_plugin_test(self):
                plugin = loader.find_module(pname).load_module(pname)
                assert hasattr(plugin, "__plugin__"), "It exports __plugin__"
                assert issubclass(
                    plugin.__plugin__,
                    Plugin), "__plugin__ is an instance of the Plugin class"

                assert callable(plugin.__plugin__._get_streams
                                ), "The plugin implements _get_streams"
                assert callable(plugin.__plugin__.can_handle_url
                                ), "The plugin implements can_handle_url"
                sig = inspect.signature(plugin.__plugin__.can_handle_url)
                assert str(
                    sig) == "(url)", "can_handle_url only accepts the url arg"

            return load_plugin_test

        for loader, pname in plugins:
            dict[f"test_{pname}_load"] = gentest(loader, pname)

        return type.__new__(mcs, name, bases, dict)
Пример #4
0
    def __new__(mcs, name, bases, dict):
        plugin_path = os.path.dirname(streamlink.plugins.__file__)
        plugins = []
        for loader, pname, ispkg in pkgutil.iter_modules([plugin_path]):
            module = load_module(pname, plugin_path)
            if hasattr(module, "__plugin__"):
                plugins.append((pname))

        session = Streamlink()

        def gentest(pname):
            def load_plugin_test(self):
                # Reset file variable to ensure it is still open when doing
                # load_plugin else python might open the plugin source .py
                # using ascii encoding instead of utf-8.
                # See also open() call here: imp._HackedGetData.get_data
                file, pathname, desc = imp.find_module(pname, [plugin_path])
                session.load_plugin(pname, file, pathname, desc)
                # validate that can_handle_url does not fail
                session.plugins[pname].can_handle_url("http://test.com")

            return load_plugin_test

        for pname in plugins:
            dict['test_{0}_load'.format(pname)] = gentest(pname)

        return type.__new__(mcs, name, bases, dict)
Пример #5
0
    def __new__(mcs, name, bases, dict):
        plugin_path = os.path.dirname(streamlink.plugins.__file__)
        plugins = []
        for loader, pname, ispkg in pkgutil.iter_modules([plugin_path]):
            module = load_module(pname, plugin_path)
            if hasattr(module, "__plugin__"):
                plugins.append((loader, pname))

        def gentest(loader, pname):
            def load_plugin_test(self):
                plugin = loader.find_module(pname).load_module(pname)
                assert hasattr(plugin, "__plugin__"), "It exports __plugin__"
                assert issubclass(
                    plugin.__plugin__,
                    Plugin), "__plugin__ is an instance of the Plugin class"

                classname = plugin.__plugin__.__name__
                assert classname == classname[0].upper() + classname[
                    1:], "__plugin__ class name starts with uppercase letter"
                assert "_" not in classname, "__plugin__ class name does not contain underscores"

                assert callable(plugin.__plugin__._get_streams
                                ), "The plugin implements _get_streams"
                assert callable(plugin.__plugin__.can_handle_url
                                ), "The plugin implements can_handle_url"
                if hasattr(inspect, 'signature'):
                    sig = inspect.signature(plugin.__plugin__.can_handle_url)
                else:
                    argspec = inspect.getargspec(
                        plugin.__plugin__.can_handle_url)
                    # Generate the argument list that is separated by colons.
                    args = argspec.args[:]
                    if argspec.defaults:
                        offset = len(args) - len(argspec.defaults)
                        for i, default in enumerate(argspec.defaults):
                            args[i + offset] = '{}={!r}'.format(
                                args[i + offset], argspec.defaults[i])
                    if argspec.varargs:
                        args.append('*' + argspec.varargs)
                    if argspec.keywords:
                        args.append('**' + argspec.keywords)
                    sig = '(' + ', '.join(args[1:]) + ')'

                assert str(
                    sig) == "(url)", "can_handle_url only accepts the url arg"

            return load_plugin_test

        for loader, pname in plugins:
            dict["test_{0}_load".format(pname)] = gentest(loader, pname)

        return type.__new__(mcs, name, bases, dict)
Пример #6
0
    def __new__(mcs, name, bases, dict):
        plugin_path = os.path.dirname(streamlink.plugins.__file__)
        plugins = []
        for loader, pname, ispkg in pkgutil.iter_modules([plugin_path]):
            module = load_module(f"streamlink.plugins.{pname}", plugin_path)
            if hasattr(module, "__plugin__"):
                plugins.append((loader, pname))

        def gentest(loader, pname):
            def load_plugin_test(self):
                plugin = loader.find_module(pname).load_module(pname)
                assert hasattr(plugin, "__plugin__"), "It exports __plugin__"

                pluginclass = plugin.__plugin__
                assert issubclass(
                    plugin.__plugin__,
                    Plugin), "__plugin__ is an instance of the Plugin class"

                classname = pluginclass.__name__
                assert classname == classname[0].upper() + classname[
                    1:], "__plugin__ class name starts with uppercase letter"
                assert "_" not in classname, "__plugin__ class name does not contain underscores"

                assert isinstance(pluginclass.matchers, list) and len(
                    pluginclass.matchers) > 0, "Has at least one matcher"
                assert all(
                    isinstance(matcher, Matcher) for matcher in
                    pluginclass.matchers), "Only has valid matchers"

                assert not hasattr(
                    pluginclass, "can_handle_url"
                ), "Does not implement deprecated can_handle_url(url)"
                assert not hasattr(
                    pluginclass,
                    "priority"), "Does not implement deprecated priority(url)"
                assert callable(
                    pluginclass._get_streams), "Implements _get_streams()"

            return load_plugin_test

        for loader, pname in plugins:
            dict[f"test_{pname}_load"] = gentest(loader, pname)

        return type.__new__(mcs, name, bases, dict)
Пример #7
0
def load_support_plugin(name):
    """Loads a plugin from the same directory as the calling plugin.

    The path used is extracted from the last call in module scope,
    therefore this must be called only from module level in the
    originating plugin or the correct plugin path will not be found.

    """

    # Get the path of the caller module
    stack = list(filter(lambda f: f[3] == "<module>", inspect.stack()))
    prev_frame = stack[0]
    path = os.path.dirname(prev_frame[1])

    # Major hack. If we are frozen by bbfreeze the stack trace will
    # contain relative paths. We therefore use the __file__ variable
    # in this module to correct it.
    if not os.path.isabs(path):
        prefix = os.path.normpath(__file__ + "../../../../../")
        path = os.path.join(prefix, path)

    return load_module(name, path)
Пример #8
0
 def test_load_module(self):
     self.assertEqual(
         sys.modules[__name__].__test_marker__,
         load_module(__name__.split(".")[-1],
                     os.path.dirname(__file__)).__test_marker__)
Пример #9
0
 def test_load_module(self):
     self.assertEqual(
         sys.modules[__name__].__test_marker__,
         load_module(__name__.split(".")[-1], os.path.dirname(__file__)).__test_marker__
     )