Example #1
0
    def __getattr__(self, attr):
        if attr in self.__dict__:
            return self.__dict__[attr]

        data = self.__dict__['_data']
        from rez.plugin_managers import plugin_manager
        if attr in plugin_manager.get_plugin_types():
            # get plugin config data, and apply overrides
            plugin_type = attr
            config_data = plugin_manager.get_plugin_config_data(plugin_type)
            d = copy.deepcopy(config_data)
            deep_update(d, data.get(plugin_type, {}))

            # validate
            schema = plugin_manager.get_plugin_config_schema(plugin_type)
            try:
                d = schema.validate(d)
            except SchemaError as e:
                raise ConfigurationError(
                    "Error in Rez configuration under plugins.%s: %s" %
                    (plugin_type, str(e)))
        elif attr in data:
            d = data[attr]
        else:
            raise AttributeError(
                "No such configuration setting: 'plugins.%s'" % attr)
        d_ = convert_dicts(d, RO_AttrDictWrapper)
        self.__dict__[attr] = d_
        return d_
Example #2
0
    def __getattr__(self, attr):
        if attr in self.__dict__:
            return self.__dict__[attr]

        data = self.__dict__['_data']
        from rez.plugin_managers import plugin_manager
        if attr in plugin_manager.get_plugin_types():
            # get plugin config data, and apply overrides
            plugin_type = attr
            config_data = plugin_manager.get_plugin_config_data(plugin_type)
            d = copy.deepcopy(config_data)
            deep_update(d, data.get(plugin_type, {}))

            # validate
            schema = plugin_manager.get_plugin_config_schema(plugin_type)
            try:
                d = schema.validate(d)
            except SchemaError as e:
                raise ConfigurationError(
                    "Error in Rez configuration under plugins.%s: %s"
                    % (plugin_type, str(e)))
        elif attr in data:
            d = data[attr]
        else:
            raise AttributeError("No such configuration setting: 'plugins.%s'"
                                 % attr)
        d_ = convert_dicts(d, RO_AttrDictWrapper)
        self.__dict__[attr] = d_
        return d_
Example #3
0
    def update_settings(self, new_settings, override=False):
        """Can be called within test methods to modify settings on a
        per-test basis (as opposed cls.settings, which modifies it for all
        tests on the class)

        Note that multiple calls will not "accumulate" updates, but will
        instead patch the class's settings with the new_settings each time.

        new_settings : dict
            the updated settings to override the config with
        override : bool
            normally, the resulting config will be the result of merging
            the base cls.settings with the new_settings - ie, like doing
            cls.settings.update(new_settings).  If this is True, however,
            then the cls.settings will be ignored entirely, and the
            new_settings will be the only configuration settings applied
        """
        # restore the "normal" config...
        from rez.utils.data_utils import deep_update

        self.teardown_config()

        # ...then copy the class settings dict to instance, so we can
        # modify...
        if override:
            self.settings = dict(new_settings)
        else:
            self.settings = dict(type(self).settings)
            deep_update(self.settings, new_settings)

        # now swap the config back in...
        self.setup_config()
Example #4
0
File: util.py Project: mottosso/rez
    def update_settings(self, new_settings, override=False):
        """Can be called within test methods to modify settings on a
        per-test basis (as opposed cls.settings, which modifies it for all
        tests on the class)

        Note that multiple calls will not "accumulate" updates, but will
        instead patch the class's settings with the new_settings each time.

        new_settings : dict
            the updated settings to override the config with
        override : bool
            normally, the resulting config will be the result of merging
            the base cls.settings with the new_settings - ie, like doing
            cls.settings.update(new_settings).  If this is True, however,
            then the cls.settings will be ignored entirely, and the
            new_settings will be the only configuration settings applied
        """
        # restore the "normal" config...
        from rez.utils.data_utils import deep_update

        self.teardown_config()

        # ...then copy the class settings dict to instance, so we can
        # modify...
        if override:
            self.settings = dict(new_settings)
        else:
            self.settings = dict(type(self).settings)
            deep_update(self.settings, new_settings)

        # now swap the config back in...
        self.setup_config()
Example #5
0
    def _data(self):
        data = copy.deepcopy(self._data_without_overrides)

        # need to do this regardless of overrides, in order to flatten
        # ModifyList instances
        deep_update(data, self.overrides)

        return data
Example #6
0
    def _data(self):
        data = copy.deepcopy(self._data_without_overrides)

        # need to do this regardless of overrides, in order to flatten
        # ModifyList instances
        deep_update(data, self.overrides)

        return data
Example #7
0
    def config_schema(self):
        """Returns the merged configuration data schema for this plugin
        type."""
        from rez.config import _plugin_config_dict
        d = _plugin_config_dict.get(self.type_name, {})

        for name, plugin_class in self.plugin_classes.items():
            if hasattr(plugin_class, "schema_dict") \
                    and plugin_class.schema_dict:
                d_ = {name: plugin_class.schema_dict}
                deep_update(d, d_)
        return dict_to_schema(d, required=True, modifier=expand_system_vars)
Example #8
0
def _load_config_from_filepaths(filepaths):
    data = {}
    sourced_filepaths = []
    loaders = ((".py", _load_config_py), ("", _load_config_yaml))

    for filepath in filepaths:
        for extension, loader in loaders:
            if extension:
                no_ext = os.path.splitext(filepath)[0]
                filepath_with_ext = no_ext + extension
            else:
                filepath_with_ext = filepath

            if not os.path.isfile(filepath_with_ext):
                continue

            data_ = loader(filepath_with_ext)
            deep_update(data, data_)
            sourced_filepaths.append(filepath_with_ext)
            break

    return data, sourced_filepaths
Example #9
0
def _load_config_from_filepaths(filepaths):
    data = {}
    sourced_filepaths = []
    loaders = ((".py", _load_config_py),
               ("", _load_config_yaml))

    for filepath in filepaths:
        for extension, loader in loaders:
            if extension:
                no_ext = os.path.splitext(filepath)[0]
                filepath_with_ext = no_ext + extension
            else:
                filepath_with_ext = filepath

            if not os.path.isfile(filepath_with_ext):
                continue

            data_ = loader(filepath_with_ext)
            deep_update(data, data_)
            sourced_filepaths.append(filepath_with_ext)
            break

    return data, sourced_filepaths
Example #10
0
    def override(self, key, value):
        def _nosuch():
            raise AttributeError("no such setting: %r" % '.'.join(key))
        if len(key) < 2:
            _nosuch()
        from rez.plugin_managers import plugin_manager
        if key[0] not in plugin_manager.get_plugin_types():
            _nosuch()

        plugin_type = key[0]
        key = key[1:]
        data = {}
        new_overrides = {plugin_type: data}
        while len(key) > 1:
            data_ = {}
            data[key[0]] = data_
            data = data_
            key = key[1:]
        data[key[0]] = value
        deep_update(self.__dict__['_data'], new_overrides)

        if plugin_type in self.__dict__:
            del self.__dict__[plugin_type]  # uncache
Example #11
0
    def override(self, key, value):
        def _nosuch():
            raise AttributeError("no such setting: %r" % '.'.join(key))
        if len(key) < 2:
            _nosuch()
        from rez.plugin_managers import plugin_manager
        if key[0] not in plugin_manager.get_plugin_types():
            _nosuch()

        plugin_type = key[0]
        key = key[1:]
        data = {}
        new_overrides = {plugin_type: data}
        while len(key) > 1:
            data_ = {}
            data[key[0]] = data_
            data = data_
            key = key[1:]
        data[key[0]] = value
        deep_update(self.__dict__['_data'], new_overrides)

        if plugin_type in self.__dict__:
            del self.__dict__[plugin_type]  # uncache
Example #12
0
    def load_plugins(self):
        import pkgutil
        from rez.backport.importlib import import_module
        type_module_name = 'rezplugins.' + self.type_name
        package = import_module(type_module_name)

        # on import, the `__path__` variable of the imported package is extended
        # to include existing directories on the plugin search path (via
        # extend_path, above). this means that `walk_packages` will walk over all
        # modules on the search path at the same level (.e.g in a
        # 'rezplugins/type_name' sub-directory).
        paths = [package.__path__] if isinstance(package.__path__, basestring) \
            else package.__path__

        # reverse plugin path order, so that custom plugins have a chance to
        # override the builtin plugins (from /rezplugins).
        paths = reversed(paths)

        for path in paths:
            for loader, modname, ispkg in pkgutil.iter_modules(
                [path], package.__name__ + '.'):

                if loader is None:
                    continue

                plugin_name = modname.split('.')[-1]
                if plugin_name.startswith('_'):
                    continue

                if config.debug("plugins"):
                    print_debug("loading %s plugin at %s: %s..." %
                                (self.type_name, path, modname))
                try:
                    # load_module will force reload the module if it's
                    # already loaded, so check for that
                    module = sys.modules.get(modname)
                    if module is None:
                        module = loader.find_module(modname).load_module(
                            modname)
                    if hasattr(module, 'register_plugin') and \
                            hasattr(module.register_plugin, '__call__'):
                        plugin_class = module.register_plugin()
                        if plugin_class != None:
                            self.register_plugin(plugin_name, plugin_class,
                                                 module)
                        else:
                            if config.debug("plugins"):
                                print_warning(
                                    "'register_plugin' function at %s: %s did not return a class."
                                    % (path, modname))
                    else:
                        if config.debug("plugins"):
                            print_warning(
                                "no 'register_plugin' function at %s: %s" %
                                (path, modname))

                        # delete from sys.modules?

                except Exception as e:
                    nameish = modname.split('.')[-1]
                    self.failed_plugins[nameish] = str(e)
                    if config.debug("plugins"):
                        import traceback
                        from StringIO import StringIO
                        out = StringIO()
                        traceback.print_exc(file=out)
                        print_debug(out.getvalue())

            # load config
            data, _ = _load_config_from_filepaths(
                [os.path.join(path, "rezconfig")])
            deep_update(self.config_data, data)
Example #13
0
    def load_plugins(self):
        import pkgutil
        from rez.backport.importlib import import_module
        type_module_name = 'rezplugins.' + self.type_name
        package = import_module(type_module_name)

        # on import, the `__path__` variable of the imported package is extended
        # to include existing directories on the plugin search path (via
        # extend_path, above). this means that `walk_packages` will walk over all
        # modules on the search path at the same level (.e.g in a
        # 'rezplugins/type_name' sub-directory).
        paths = [package.__path__] if isinstance(package.__path__, basestring) \
            else package.__path__

        # reverse plugin path order, so that custom plugins have a chance to
        # be found before the builtin plugins (from /rezplugins).
        paths = reversed(paths)

        for path in paths:
            if config.debug("plugins"):
                print_debug("searching plugin path %s...", path)

            for importer, modname, ispkg in pkgutil.iter_modules(
                [path], package.__name__ + '.'):

                if importer is None:
                    continue

                plugin_name = modname.split('.')[-1]
                if plugin_name.startswith('_') or plugin_name == 'rezconfig':
                    continue

                if plugin_name in self.plugin_modules:
                    # same named plugins will have identical module name,
                    # which will just reuse previous imported module from
                    # `sys.modules` below. skipping the rest of the process
                    # for good.
                    if config.debug("plugins"):
                        print_warning(
                            "skipped same named %s plugin at %s: %s" %
                            (self.type_name, path, modname))
                    continue

                if config.debug("plugins"):
                    print_debug("loading %s plugin at %s: %s..." %
                                (self.type_name, path, modname))
                try:
                    # nerdvegas/rez#218
                    # load_module will force reload the module if it's
                    # already loaded, so check for that
                    plugin_module = sys.modules.get(modname)
                    if plugin_module is None:
                        loader = importer.find_module(modname)
                        plugin_module = loader.load_module(modname)

                    elif os.path.dirname(plugin_module.__file__) != path:
                        if config.debug("plugins"):
                            # this should not happen but if it does, tell why.
                            print_warning(
                                "plugin module %s is not loaded from current "
                                "load path but reused from previous imported "
                                "path: %s" % (modname, plugin_module.__file__))

                    if (hasattr(plugin_module, "register_plugin")
                            and callable(plugin_module.register_plugin)):

                        plugin_class = plugin_module.register_plugin()
                        if plugin_class is not None:
                            self.register_plugin(plugin_name, plugin_class,
                                                 plugin_module)
                        else:
                            if config.debug("plugins"):
                                print_warning(
                                    "'register_plugin' function at %s: %s did "
                                    "not return a class." % (path, modname))
                    else:
                        if config.debug("plugins"):
                            print_warning(
                                "no 'register_plugin' function at %s: %s" %
                                (path, modname))

                        # delete from sys.modules?

                except Exception as e:
                    nameish = modname.split('.')[-1]
                    self.failed_plugins[nameish] = str(e)
                    if config.debug("plugins"):
                        import traceback
                        from rez.vendor.six.six import StringIO
                        out = StringIO()
                        traceback.print_exc(file=out)
                        print_debug(out.getvalue())

            # load config
            data, _ = _load_config_from_filepaths(
                [os.path.join(path, "rezconfig")])
            deep_update(self.config_data, data)