When we must use multimethods, this could be abstracted out like this (did not test that):
```python
def version_dependent(default_function):
    mm = MultiMethod(default_function.__name__, version.product_version_dispatch)
    mm.method(Default)(default_function)
    return mm


@version_dependent
def get_message_level(el):
    """default"""
    return sel.get_attribute(el, "class") or "error"


@get_message_level.method(upstream)
def get_message_level_up(el):
    """blablabla"""
```

Or even more (again untested) - more readable version:
```python
def version_dependent(default_function):
    mm = MultiMethod(default_function.__name__, version.product_version_dispatch)
    mm.method(Default)(default_function)
    mm.version = lambda self, ver: self.method(LooseVersion(ver))
    return mm


@version_dependent
def get_message_level(el):
    """default"""
    return sel.get_attribute(el, "class") or "error"


@get_message_level.version("9.9.9.9")
def get_message_level_up(el):
    """blablabla"""
```