[PATCH 01 of 11] configitems: allow for the registration of "generic" config item
Boris Feld
boris.feld at octobus.net
Fri Oct 13 17:55:07 UTC 2017
# HG changeset patch
# User Boris Feld <boris.feld at octobus.net>
# Date 1507625355 -7200
# Tue Oct 10 10:49:15 2017 +0200
# Node ID 429c6e9c7c3a4f601db17c6553a8fcdad35708a8
# Parent 37b4375b1221e3bda055f0cbecf06b3c9510fd2c
# EXP-Topic config.register.ready
# Available At https://bitbucket.org/octobus/mercurial-devel/
# hg pull https://bitbucket.org/octobus/mercurial-devel/ -r 429c6e9c7c3a
configitems: allow for the registration of "generic" config item
Some section can contains arbitrary keys (eg: color, alias, extensions). We
add a way to register some generic config items for them. This is necessary to
get all the config registered. We use a regular expression because some sub-
attributes (eg: hooks.xxx.priority) can define default value on their own.
diff --git a/mercurial/configitems.py b/mercurial/configitems.py
--- a/mercurial/configitems.py
+++ b/mercurial/configitems.py
@@ -8,6 +8,7 @@
from __future__ import absolute_import
import functools
+import re
from . import (
encoding,
@@ -33,20 +34,56 @@
:section: the official config section where to find this item,
:name: the official name within the section,
:default: default value for this item,
- :alias: optional list of tuples as alternatives.
+ :alias: optional list of tuples as alternatives,
+ :generic: this is a generic definition, match name using regular expression.
"""
- def __init__(self, section, name, default=None, alias=()):
+ def __init__(self, section, name, default=None, alias=(),
+ generic=False, priority=0):
self.section = section
self.name = name
self.default = default
self.alias = list(alias)
+ self.generic = generic
+ self.priority = priority
+ self._re = None
+ if generic:
+ self._re = re.compile(self.name)
+
+class itemregister(dict):
+ """A specialized dictionary that can handle wild-card selection"""
+
+ def __init__(self):
+ super(itemregister, self).__init__()
+ self._generics = set()
+
+ def update(self, other):
+ super(itemregister, self).update(other)
+ self._generics.update(other._generics)
+
+ def __setitem__(self, key, item):
+ super(itemregister, self).__setitem__(key, item)
+ if item.generic:
+ self._generics.add(item)
+
+ def get(self, key):
+ if key in self:
+ return self[key]
+
+ # search for a matching generic item
+ generics = sorted(self._generics, key=(lambda x: (x.priority, x.name)))
+ for item in generics:
+ if item._re.match(key):
+ return item
+
+ # fallback to dict get
+ return super(itemregister, self).get(key)
coreitems = {}
def _register(configtable, *args, **kwargs):
item = configitem(*args, **kwargs)
- section = configtable.setdefault(item.section, {})
+ section = configtable.setdefault(item.section, itemregister())
if item.name in section:
msg = "duplicated config item registration for '%s.%s'"
raise error.ProgrammingError(msg % (item.section, item.name))
More information about the Mercurial-devel
mailing list