Skip to content

Commit

Permalink
Adding support for reading & writing <Property> elements.
Browse files Browse the repository at this point in the history
Throws error is model with Property is simulated.
See #16
  • Loading branch information
pgleeson committed Nov 19, 2015
1 parent ccf5824 commit fc4e504
Show file tree
Hide file tree
Showing 6 changed files with 101 additions and 2 deletions.
2 changes: 1 addition & 1 deletion lems/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,4 +8,4 @@

logger = logging.getLogger('LEMS')

__version__ = '0.4.4'
__version__ = '0.4.5'
55 changes: 55 additions & 0 deletions lems/model/component.py
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,41 @@ def toxml(self):
"""

return '<Fixed parameter="{0}"'.format(self.name) + ' value="{0}"'.format(self.fixed_value)+'/>'



class Property(LEMSBase):
"""
Store the specification of a property.
"""

def __init__(self, name, dimension = None, description = ''):
"""
Constructor.
"""

self.name = name
""" Name of the property.
@type: str """

self.dimension = dimension
""" Physical dimensions of the property.
@type: str """

self.description = description
""" Description of the property.
@type: str """


def toxml(self):
"""
Exports this object into a LEMS XML object
"""

return '<Property name="{0}"'.format(self.name) +\
(' dimension="{0}"'.format(self.dimension) if self.dimension else 'none') +\
'/>'


class IndexParameter(LEMSBase):
"""
Expand Down Expand Up @@ -615,6 +650,10 @@ def __init__(self):
""" Map of parameters in this component type.
@type: Map(str -> lems.model.component.Parameter) """

self.properties = Map()
""" Map of properties in this component type.
@type: Map(str -> lems.model.component.Property) """

self.derived_parameters = Map()
""" Map of derived_parameters in this component type.
@type: Map(str -> lems.model.component.Parameter) """
Expand Down Expand Up @@ -697,6 +736,17 @@ def add_parameter(self, parameter):

self.parameters[parameter.name] = parameter


def add_property(self, property):
"""
Adds a property to this component type.
@param property: Property to be added.
@type property: lems.model.component.Property
"""

self.properties[property.name] = property

def add_derived_parameter(self, derived_parameter):
"""
Adds a derived_parameter to this component type.
Expand Down Expand Up @@ -853,6 +903,8 @@ def add(self, child):

if isinstance(child, Parameter):
self.add_parameter(child)
elif isinstance(child, Property):
self.add_property(child)
elif isinstance(child, DerivedParameter):
self.add_derived_parameter(child)
elif isinstance(child, IndexParameter):
Expand Down Expand Up @@ -926,6 +978,9 @@ def toxml(self):

chxmlstr = ''

for property in self.properties:
chxmlstr += property.toxml()

for parameter in self.parameters:
chxmlstr += parameter.toxml()

Expand Down
7 changes: 7 additions & 0 deletions lems/model/model.py
Original file line number Diff line number Diff line change
Expand Up @@ -346,6 +346,8 @@ def merge_component_types(self, ct, base_ct):
else:
ct.parameters[parameter.name] = base_ct.parameters[parameter.name]

merge_maps(ct.properties, base_ct.properties)

merge_maps(ct.derived_parameters, base_ct.derived_parameters)
merge_maps(ct.index_parameters, base_ct.index_parameters)
merge_maps(ct.constants, base_ct.constants)
Expand Down Expand Up @@ -415,6 +417,11 @@ def fatten_component(self, c):
raise ModelError("Parameter '{0}' not initialized for component '{1}'",
parameter.name, c.id)

### Resolve properties
for property in ct.properties:
property2 = property.copy()
fc.add(property2)

### Resolve derived_parameters
for derived_parameter in ct.derived_parameters:
derived_parameter2 = derived_parameter.copy()
Expand Down
33 changes: 33 additions & 0 deletions lems/parser/LEMS.py
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,7 @@ def init_parser(self):
'componentreference',
'exposure', 'eventport',
'fixed', 'link', 'parameter',
'property',
'indexparameter',
'path', 'requirement',
'componentrequirement',
Expand Down Expand Up @@ -187,6 +188,7 @@ def init_parser(self):
self.tag_parse_table['onevent'] = self.parse_on_event
self.tag_parse_table['onstart'] = self.parse_on_start
self.tag_parse_table['parameter'] = self.parse_parameter
self.tag_parse_table['property'] = self.parse_property
self.tag_parse_table['path'] = self.parse_path
self.tag_parse_table['record'] = self.parse_record
self.tag_parse_table['regime'] = self.parse_regime
Expand Down Expand Up @@ -1181,6 +1183,37 @@ def parse_parameter(self, node):
parameter = Parameter(name, dimension)

self.current_component_type.add_parameter(parameter)

def parse_property(self, node):
"""
Parses <Property>
@param node: Node containing the <Property> element
@type node: xml.etree.Element
@raise ParseError: Raised when the property does not have a name.
@raise ParseError: Raised when the property does not have a
dimension.
"""

if self.current_component_type == None:
self.raise_error('Property can only be defined in ' +
'a component type')

try:
name = node.lattrib['name']
except:
self.raise_error('<Property> must specify a name')

try:
dimension = node.lattrib['dimension']
except:
self.raise_error("Property '{0}' has no dimension",
name)

property = Property(name, dimension)

self.current_component_type.add_property(property)


def parse_index_parameter(self, node):
Expand Down
4 changes: 4 additions & 0 deletions lems/sim/build.py
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,10 @@ def build_runnable(self, component, parent = None, id_ = None):

for parameter in component.parameters:
runnable.add_instance_variable(parameter.name, parameter.numeric_value)


for property in component.properties:
raise NotImplementedError("Property element is not stable in PyLEMS yet, see https://github.com/LEMS/pylems/issues/16")

derived_parameter_code = []

Expand Down
2 changes: 1 addition & 1 deletion testpy2.sh
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,4 @@ python2.7 examples/apitest.py
python2.7 examples/apitest2.py
python2.7 examples/loadtest.py
python2.7 lems/dlems/exportdlems.py
python2.7 pylems -I ../NeuroML2/NeuroML2CoreTypes ../NeuroML2/LEMSexamples/LEMS_NML2_Ex2_Izh.xml
python2.7 pylems -I ../NeuroML2/NeuroML2CoreTypes ../NeuroML2/LEMSexamples/LEMS_NML2_Ex5_DetCell.xml

0 comments on commit fc4e504

Please sign in to comment.