Repository: easybuilders/easybuild-easyblocks

Issue:
numexpr can't be installed as an extension
The reason is two-fold:

As an extension this is not executed:

https://github.com/easybuilders/easybuild-easyblocks/blob/develop/easybuild/easyblocks/n/numexpr.py#L59

And therefore the variable is not defined, it is built without VML, and it would fail on the sanity check.

With that fixed, there is another more convoluted issue. The sanity check executed follows this order:

1. Sanity check in `numexpr.py`
2. Sanity check in `pythonpackage`
3. Sanity check in `extensioneasyblock`
4. Sanity check in `easyblock`
5. Sanity check in `extensioneasyblock` again
6. And finally sanity check in `easyblock` again, where it fails

5 and 6 happens due to this condition:

https://github.com/easybuilders/easybuild-framework/blob/develop/easybuild/framework/extensioneasyblock.py#L154

Without the `custom_commands` it works just fine. But that should be ok.

The log does not help much, but shows that there is a weird issue (sanity checked passed, and then failed):

```
== 2020-03-26 20:57:10,714 run.py:200 DEBUG run_cmd: running cmd python -c 'import numexpr; assert(numexpr.use_vml)' (in /gpfs/software/juwels/stages/Devel-2019a/software/Jupyter/2019a-gcccoremkl-8.3.0-2019.3.199-devel2-Python-3.6.8)
== 2020-03-26 20:57:10,715 run.py:219 INFO running cmd: python -c 'import numexpr; assert(numexpr.use_vml)'
== 2020-03-26 20:57:11,196 run.py:536 DEBUG cmd "python -c 'import numexpr; assert(numexpr.use_vml)'" exited with exit code 0 and output:

== 2020-03-26 20:57:11,196 run.py:570 DEBUG Using default regular expression: (?<![(,-]|\w)(?:error|segmentation fault|failed)(?![(,-]|\.?\w)
== 2020-03-26 20:57:11,197 easyblock.py:2574 INFO sanity check command python -c 'import numexpr; assert(numexpr.use_vml)' ran successfully! (output: )
== 2020-03-26 20:57:11,198 easyblock.py:2595 DEBUG Skipping RPATH sanity check
== 2020-03-26 20:57:11,198 easyblock.py:2601 DEBUG Sanity check passed!
== 2020-03-26 20:57:11,198 extensioneasyblock.py:160 INFO Sanity check for numexpr successful!
== 2020-03-26 20:57:11,199 easyblock.py:2473 WARNING failing sanity check for 'numexpr' extension: (see log for details)
== 2020-03-26 20:57:11,199 easyblock.py:2479 WARNING extensions sanity check failed for 1 extensions:
```

The funny bit. If I wrap this condition https://github.com/easybuilders/easybuild-framework/blob/develop/easybuild/framework/easyblock.py#L2622 like this:

```
         print("before extension easyblock failed message: "+str(self.sanity_check_fail_msgs))
         # also run sanity check for extensions (unless we are an extension ourselves)
         if not extension:
             self._sanity_check_step_extensions()
         print("after extension easyblock failed message: "+str(self.sanity_check_fail_msgs))
```

I get this output:

```
before extension easyblock failed message: []
after extension easyblock failed message: []
after extension easyblock failed message: ['extensions sanity check failed for 1 extensions: numexpr', "failing sanity check for 'numexpr' extension: (see log for details)"]
```

Note the 2 "after" with a single "before". It is late and I am tired and hungry, but that looks pretty weird to me and I am starting to believe in leprechauns


Discussion:

Resolving patch:
diff --git a/easybuild/easyblocks/n/numexpr.py b/easybuild/easyblocks/n/numexpr.py
--- a/easybuild/easyblocks/n/numexpr.py
+++ b/easybuild/easyblocks/n/numexpr.py
@@ -52,16 +52,12 @@ def __init__(self, *args, **kwargs):
 
         self.imkl_root = None
 
-    def prepare_step(self, *args, **kwargs):
-        """Prepare environment for building and installing numexpr."""
-        super(EB_numexpr, self).prepare_step(*args, **kwargs)
-
-        self.imkl_root = get_software_root('imkl')
-
     def configure_step(self):
         """Custom configuration procedure for numexpr."""
         super(EB_numexpr, self).configure_step()
 
+        self.imkl_root = get_software_root('imkl')
+
         # if Intel MKL is available, set up site.cfg such that the right VML library is used;
         # this makes a *big* difference in terms of performance;
         # see also https://github.com/pydata/numexpr/blob/master/site.cfg.example
@@ -103,4 +99,4 @@ def sanity_check_step(self):
         if self.imkl_root:
             custom_commands.append("python -c 'import numexpr; assert(numexpr.use_vml)'")
 
-        super(EB_numexpr, self).sanity_check_step(custom_commands=custom_commands)
+        return super(EB_numexpr, self).sanity_check_step(custom_commands=custom_commands)


Test patch: