Repository: pypa/setuptools

Issue:
setuptools ignores order attribute of entrypoints inf `finalize_distribution_options` group
# Issue

I tried this entry point definition in my `setup.py`
```
# ./setup.py
[setuptools.finalize_distribution_options]
testfin = mypackage.integration:finalize
```
where finalize is a function with an `order` attribute defined, essentially like this:
```python
# ./mypackage/integration.py
def finalize(dist):
  # do something with dist
finalize.order = 99
```
**The order stays at the default of `0`.**


# Cause

The relevant code in `dist.py` says:

```python
def finalize_options(self):
    hook_key = 'setuptools.finalize_distribution_options'

    def by_order(hook):
        return getattr(hook, 'order', 0)
    eps = pkg_resources.iter_entry_points(hook_key)
    for ep in sorted(eps, key=by_order):
        ep.load()(self)
```

So, `by_order()` looks at the entry point object for the `order` attribute instead of the actual underlying object. 


# Mitigation

The following change would fix the problem, but is not elegant because `load()` would end up being called twice.

```python
def by_order(hook):
    return getattr(hook.load(), 'order', 0)
```

**I will make a PR today to try and fix that in a better way.**

--------------

Note that @jaraco [random shuffle](https://github.com/pypa/setuptools/pull/1877#issuecomment-554662936)  rational from #1877 is still valid, as they did not explicitly use the `order` attribute.
setuptools ignores order attribute of entrypoints inf `finalize_distribution_options` group
# Issue

I tried this entry point definition in my `setup.py`
```
# ./setup.py
[setuptools.finalize_distribution_options]
testfin = mypackage.integration:finalize
```
where finalize is a function with an `order` attribute defined, essentially like this:
```python
# ./mypackage/integration.py
def finalize(dist):
  # do something with dist
finalize.order = 99
```
**The order stays at the default of `0`.**


# Cause

The relevant code in `dist.py` says:

```python
def finalize_options(self):
    hook_key = 'setuptools.finalize_distribution_options'

    def by_order(hook):
        return getattr(hook, 'order', 0)
    eps = pkg_resources.iter_entry_points(hook_key)
    for ep in sorted(eps, key=by_order):
        ep.load()(self)
```

So, `by_order()` looks at the entry point object for the `order` attribute instead of the actual underlying object. 


# Mitigation

The following change would fix the problem, but is not elegant because `load()` would end up being called twice.

```python
def by_order(hook):
    return getattr(hook.load(), 'order', 0)
```

**I will make a PR today to try and fix that in a better way.**

--------------

Note that @jaraco [random shuffle](https://github.com/pypa/setuptools/pull/1877#issuecomment-554662936)  rational from #1877 is still valid, as they did not explicitly use the `order` attribute.


Discussion:

Resolving patch:
diff --git a/setuptools/dist.py b/setuptools/dist.py
--- a/setuptools/dist.py
+++ b/setuptools/dist.py
@@ -731,13 +731,13 @@ def finalize_options(self):
         to influence the order of execution. Smaller numbers
         go first and the default is 0.
         """
-        hook_key = 'setuptools.finalize_distribution_options'
+        group = 'setuptools.finalize_distribution_options'
 
         def by_order(hook):
             return getattr(hook, 'order', 0)
-        eps = pkg_resources.iter_entry_points(hook_key)
+        eps = map(lambda e: e.load(), pkg_resources.iter_entry_points(group))
         for ep in sorted(eps, key=by_order):
-            ep.load()(self)
+            ep(self)
 
     def _finalize_setup_keywords(self):
         for ep in pkg_resources.iter_entry_points('distutils.setup_keywords'):


Test patch: