[cig-commits] r6675 - cs/pythia/trunk/pyre/applications

leif at geodynamics.org leif at geodynamics.org
Tue Apr 24 15:27:10 PDT 2007


Author: leif
Date: 2007-04-24 15:27:09 -0700 (Tue, 24 Apr 2007)
New Revision: 6675

Added:
   cs/pythia/trunk/pyre/applications/Preprocessor.py
Modified:
   cs/pythia/trunk/pyre/applications/Shell.py
Log:
Added a macro capability:

    [myapp.macros]
    foo = 42

    [myapp]
    answer = ${foo}

Macros obey the same rules as properties: e.g., you can provide
default macros under ~/.pyre, and override them in a local .cfg file
or on the command line.

Environment variables are also provided:

    [myapp]
    input-file = ${HOME}/stuff/input.txt

Currently, unrecognized macros are left untouched (they do not expand
to the empty string).

Macro references can be dotted:

    [myapp.macros.abc]
    foo = 42

    [myapp]
    answer = ${abc.foo}

The macro system is completely informal.  Macro names are not declared
anywhere in the code.  The macro hierarchy does not necessarily have
any correspondence to the component hierarchy.


Added: cs/pythia/trunk/pyre/applications/Preprocessor.py
===================================================================
--- cs/pythia/trunk/pyre/applications/Preprocessor.py	2007-04-24 22:18:14 UTC (rev 6674)
+++ cs/pythia/trunk/pyre/applications/Preprocessor.py	2007-04-24 22:27:09 UTC (rev 6675)
@@ -0,0 +1,76 @@
+#!/usr/bin/env python
+#
+# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+#
+#                      California Institute of Technology
+#                        (C) 2007  All Rights Reserved
+#
+# {LicenseText}
+#
+# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+#
+
+
+from pyre.components import Component
+from pyre.util import expandMacros
+from pyre.inventory.odb.Registry import Registry
+import os
+
+
+class Preprocessor(Component):
+
+
+    def updateConfiguration(self, registry):
+        self.macros.update(registry)
+        return []
+
+
+    def expandMacros(self, registry):
+        macros = self._prepareMacros()
+        self._expandMacros(macros, registry)
+        return
+
+
+    def _prepareMacros(self):
+        
+        class RecursionProtector(object):
+            def __init__(self, macros):
+                self.macros = macros
+                self.recur = {}
+            def __getitem__(self, key):
+                if self.recur.has_key(key):
+                    return ""
+                self.recur[key] = True
+                value = expandMacros(self.macros[key], self)
+                del self.recur[key]
+                return value
+
+        macros = {}
+        
+        # add environment variables
+        macros.update(os.environ)
+        
+        # flatten my macro registry
+        for path, value, locator in self.macros.allProperties():
+            key = '.'.join(path[1:])
+            macros[key] = value
+
+        return RecursionProtector(macros)
+
+
+    def _expandMacros(self, macros, registry):
+        for name, descriptor in registry.properties.items():
+            newValue = expandMacros(descriptor.value, macros)
+            descriptor.value = newValue
+        for node in registry.facilities.values():
+            self._expandMacros(macros, node)
+        return
+
+
+    def __init__(self, name):
+        Component.__init__(self, "macros", name)
+        self.macros = Registry(self.name)
+        return
+
+
+# end of file

Modified: cs/pythia/trunk/pyre/applications/Shell.py
===================================================================
--- cs/pythia/trunk/pyre/applications/Shell.py	2007-04-24 22:18:14 UTC (rev 6674)
+++ cs/pythia/trunk/pyre/applications/Shell.py	2007-04-24 22:27:09 UTC (rev 6675)
@@ -35,7 +35,10 @@
     journal = journal.facility()
     journal.meta['tip'] = 'the logging facility'
 
+    from Preprocessor import Preprocessor
+    pp = pyre.inventory.facility("macros", factory=Preprocessor, args=["macros"])
 
+
     def __init__(self, app):
         Configurable.__init__(self, app.name)
 
@@ -104,9 +107,16 @@
 
         # start fresh
         context = app.newConfigContext()
+
+        # ~~ configure the application ~~~
         
-        # configure the application
+        # update user options from the command line
         app.updateConfiguration(app.registry)
+        
+        # expand macros
+        self.pp.expandMacros(app.inventory._priv_registry)
+
+        # transfer user input to the app's inventory
         app.applyConfiguration(context)
 
         # the main application behavior



More information about the cig-commits mailing list