-
Notifications
You must be signed in to change notification settings - Fork 31
Description
Description
Currently, users who need custom drivers must either subclass a built-in driver and manage their own constructor function, or dynamically mutate driver.rules after instantiation. There is no way to register a custom driver so that it works seamlessly with Platform enum lookup, get_hconfig(), and other constructor functions.
Additionally, users cannot override built-in drivers — if the Cisco IOS driver does not match their environment, they must bypass the standard API entirely.
Proposed Change
1. Expose HConfigDriverBase and HConfigDriverRules as public API
Ensure these are exported from hier_config (or hier_config.platforms) so users can subclass HConfigDriverBase without reaching into internal modules:
from hier_config import HConfigDriverBase, HConfigDriverRules2. Add a driver registration function that extends Platform
from hier_config import register_driver, Platform, HConfigDriverBase, HConfigDriverRules
class MyNOSDriver(HConfigDriverBase):
@staticmethod
def _instantiate_rules() -> HConfigDriverRules:
return HConfigDriverRules(...)
register_driver("MY_NOS", MyNOSDriver)
# Platform enum is now extended with the new value
config = get_hconfig(Platform.MY_NOS, config_text)register_driver() adds a new member to the Platform enum and maps it to the given driver class. All constructors (get_hconfig(), get_hconfig_fast_load(), etc.) use the registered driver automatically.
3. Override built-in drivers
Passing an existing Platform value overrides the built-in driver:
register_driver("CISCO_IOS", MyCustomIOSDriver)
# Now uses MyCustomIOSDriver instead of the built-in
config = get_hconfig(Platform.CISCO_IOS, config_text)4. Optional: unregister_driver() and get_registered_drivers()
unregister_driver(Platform.MY_NOS) # removes custom platform
get_registered_drivers() # returns dict of all registered driversImplementation Notes
The current driver lookup lives in constructors.py:get_hconfig_driver() with a hardcoded dict mapping Platform -> driver class. This would become a module-level registry dict that register_driver() writes to and get_hconfig_driver() reads from. Built-in drivers are registered at import time as defaults.
Extending a Python Enum at runtime requires care. Options include:
- Use
enum.extend_enum(aenum library) or a custom metaclass - Rebuild
Platformwith the new member viaPlatform = Enum("Platform", {**existing, name: auto()}) - Use a registry that accepts both
Platformmembers and registered string keys, withPlatformextended via__getattr__on the module
Benefits
- Users can bring their own drivers without forking the library
- Built-in drivers can be overridden for environments with non-standard behavior
- Custom platforms are first-class
Platformenum members — no separate enum needed - Eliminates the need for the custom
get_custom_hconfig_driver()pattern documented indocs/drivers.md
Breaking Change
Yes — Platform enum becomes dynamically extensible. The get_hconfig_driver() internal lookup changes. Users who imported the hardcoded platform-to-driver mapping would need to update.