コード例 #1
0
def test_required_items():
    """
    Check that model can only be run if features and properties are
    well-defined
    """
    print()

    # ===== Specifications =====

    fspec_beam = FeatureSpec()
    fspec_beam.add_prop_spec('A', int, required=1, max_items=1)

    fspec_wing = FeatureSpec()
    fspec_wing.add_prop_spec('B', int, required=3, max_items=3)
    # fspec_wing.add_prop_spec('C', int, required=-1)

    mspec = ModelSpec()
    mspec.add_feature_spec('beam', fspec_beam, required=2)
    mspec.add_feature_spec('wing', fspec_wing, required=1)

    class Model(mspec.user_class):
        def run(self):
            super().run()
    beam_model = Model()

    # ===== User logic =====

    beam1 = beam_model.add_feature('beam')
    beam1.set('A', 2)

    beam2 = beam_model.add_feature('beam')
    beam2.set('A', 2)

    # Feature 'wing' needs to be defined
    with pytest.raises(RuntimeError):
        beam_model.run()

    wing1 = beam_model.add_feature('wing')

    # Property 'B' is needs to be defined
    with pytest.raises(RuntimeError):
        beam_model.run()

    wing1.add('B', 11)
    wing1.add('B', 22)
    wing1.add('B', 33)

    # Cannot add more items of type 'B'
    with pytest.raises(RuntimeError):
        wing1.add('B', 44)

    # Model is now well-defined
    beam_model.run()
コード例 #2
0
def test_from_dict():
    fspec1 = FeatureSpec()
    fspec1.add_prop_spec('a', int, max_items=1)
    fspec1.add_prop_spec('b', str, max_items=1)
    fspec1.add_prop_spec('c', {'type': bool}, max_items=1)

    fspec2 = FeatureSpec()
    fspec2.add_prop_spec('one', int, max_items=1)
    fspec2.add_prop_spec('two', str, max_items=1)
    fspec2.add_prop_spec('three', {'type': bool}, max_items=1)

    mspec = ModelSpec()
    mspec.add_feature_spec('A', fspec1, max_items=1)
    mspec.add_feature_spec('B', fspec2, max_items=1)

    class Model(mspec.user_class):
        def run(self):
            pass

    props1 = {
        'a': [42, ],
        'b': ['snake', ],
        'c': [True, ],
    }

    props2 = {
        'one': [43, ],
        'two': ['Snake', ],
        'three': [False, ],
    }

    model_dict = {
        'A': [props1, ],
        'B': [props2, ],
    }

    m = Model().from_dict(model_dict)
    m_fa = m.get('A')
    m_fb = m.get('B')

    assert m_fa.get('a') == 42
    assert m_fa.get('b') == 'snake'
    assert m_fa.get('c') is True

    assert m_fb.get('one') == 43
    assert m_fb.get('two') == 'Snake'
    assert m_fb.get('three') is False
コード例 #3
0
def test_model_doc():
    cross_section = FeatureSpec()
    cross_section.add_prop_spec('E', {
        'type': float,
        '>': 0
    },
                                doc="Young's modulus")
    cross_section.add_prop_spec('A', {'type': float, '>': 0}, doc="Area")

    geom = FeatureSpec()
    geom.add_prop_spec('point1', list, doc="Coordinates of point 1")
    geom.add_prop_spec('point2', list, doc="Coordinates of point 2")

    mspec = ModelSpec()
    mspec.add_feature_spec('CrossSection',
                           cross_section,
                           doc="Beam cross section")
    mspec.add_feature_spec('Geom', geom, doc="Beam geometry")

    docs = mspec.get_docs()

    assert docs['CrossSection']['main'] == "Beam cross section"
    assert docs['Geom']['main'] == "Beam geometry"

    assert docs['CrossSection']['sub']['E']['main'] == "Young's modulus"
    assert docs['CrossSection']['sub']['A']['main'] == "Area"
    assert docs['Geom']['sub']['point1']['main'] == "Coordinates of point 1"
    assert docs['Geom']['sub']['point2']['main'] == "Coordinates of point 2"
コード例 #4
0
def test_to_dict_and_documentation():
    """
    Test basic functionality of 'ModelSpec'
    """
    print()

    # ===== Specifications =====

    fspec_beam = FeatureSpec()
    fspec_beam.add_prop_spec('A', {
        'type': int,
        '>': 0
    },
                             doc='Something about property A',
                             max_items=1)
    fspec_beam.add_prop_spec('B', int, doc='Property B is also great')

    fspec_study = FeatureSpec()
    fspec_study.add_prop_spec('static', bool, max_items=1)

    mspec = ModelSpec()
    mspec.add_feature_spec('beam', fspec_beam, doc='A beam carries load')
    mspec.add_feature_spec('study',
                           fspec_study,
                           max_items=1,
                           doc='Specify the type of study to run')

    class Model(mspec.user_class):
        def run(self):
            pass

    beam_model = Model()

    # ===== User logic =====

    beam1 = beam_model.add_feature('beam')
    beam1.set('A', 1)
    beam1.add('B', 2)
    beam1.add('B', 3)

    beam2 = beam_model.add_feature('beam')
    beam2.set('A', 2)
    beam2.add('B', 4)
    beam2.add('B', 6)

    study = beam_model.set_feature('study')
    study.set('static', True)

    # ----- Serialization -----
    model_dict = beam_model.to_dict()
    with open('test.json', 'w') as fp:
        dump_pretty_json(model_dict, fp)

    beam_model = Model().from_dict(model_dict)
    beam1 = beam_model.get('beam')[0]
    assert beam1.get('A') == 1
    assert beam1.get('B') == [2, 3]
コード例 #5
0
def test_error_set_feature():
    """

    """
    print()

    fspec = FeatureSpec()
    mspec = ModelSpec()

    fspec.add_prop_spec('a', int, singleton=True)
    fspec.add_prop_spec('b', int, singleton=False)
    mspec.add_feature_spec('A', fspec, singleton=True)

    fspec.add_prop_spec('1', str, singleton=True)
    fspec.add_prop_spec('2', str, singleton=False)
    mspec.add_feature_spec('B', fspec, singleton=False)

    class Model(mspec.user_class):
        def run(self):
            pass

    m = Model()

    # Feature 'A' is non-singleton
    with pytest.raises(RuntimeError):
        m.add_feature('A')
    m.set_feature('A')

    # Feature 'B' is singleton
    with pytest.raises(RuntimeError):
        m.set_feature('B')
    m.add_feature('B')
    m.add_feature('B')
    m.add_feature('B')

    fa = m.get('A')
    fa.set('a', 2)

    fb = m.get('B')
    assert len(fb) == 3

    with pytest.raises(KeyError):
        for _ in m.iter('A'):
            pass

    for _ in m.iter('B'):
        pass
コード例 #6
0
def test_basic():
    """
    Test basic functionality of 'ModelSpec'
    """
    print()

    # ===== Specifications =====

    fspec_beam = FeatureSpec()
    fspec_beam.add_prop_spec('A', int)
    fspec_beam.add_prop_spec('B', int, singleton=False)

    fspec_study = FeatureSpec()
    fspec_study.add_prop_spec('static', bool)

    mspec = ModelSpec()
    mspec.add_feature_spec('beam', fspec_beam, singleton=False)
    mspec.add_feature_spec('study', fspec_study, singleton=True)

    class Model(mspec.user_class):
        def run(self):
            pass

    beam_model = Model()

    # ===== User logic =====

    beam1 = beam_model.add_feature('beam')
    beam1.set('A', 1)
    beam1.add('B', 2)
    beam1.add('B', 3)

    beam2 = beam_model.add_feature('beam')
    beam2.set('A', 2)
    beam2.add('B', 4)
    beam2.add('B', 6)

    study = beam_model.set_feature('study')
    study.set('static', True)

    # Beam 1 and 2 have different values for the same property
    assert beam1.get('A') == 1
    assert beam2.get('A') == 2

    # Beams are different, but the parent specification is the same
    assert beam1.uid != beam2.uid
    assert beam1._parent_uid == beam2._parent_uid
コード例 #7
0
ファイル: _model.py プロジェクト: jphkun/framat
from ._meshing import AbstractBeamMesh
from ._run import run_model
from ._util import Schemas as S

# Register custom 'schemadict' types
SchemadictValidators.register_type(AbstractBeamMesh)
SchemadictValidators.register_type(np.ndarray)

# TODO:
# - acceleration state (define on beam level, or 'global'?)

# =================
# ===== MODEL =====
# =================
mspec = ModelSpec()

tmp_doc = "The *{X}* feature is optional and allows to define sets of constant \
           {X} properties. When defining the properties for a specific beam \
           (or parts of it), you may refer to a {X} set using its UID. You may \
           define as many sets as you like."

# ===== Material =====
fspec = FeatureSpec()
fspec.add_prop_spec('E',
                    S.pos_number,
                    required=True,
                    doc="Young's modulus [N/m²]")
fspec.add_prop_spec('G',
                    S.pos_number,
                    required=True,
コード例 #8
0
ファイル: _model.py プロジェクト: jphkun/model-framework
#!/usr/bin/env python3
# -*- coding: utf-8 -*-m

# _model.py
from mframework import FeatureSpec, ModelSpec

from ._run import run_model

# Here, we only have numerical user input. We only allow positive floats.
SCHEMA_POS_FLOAT = {'type': float, '>': 0}

# ===== MODEL =====
mspec = ModelSpec()

# Create the first feature 'ambiance'
fspec = FeatureSpec()
fspec.add_prop_spec('g', SCHEMA_POS_FLOAT, doc='Gravitational acceleration')
fspec.add_prop_spec('a', SCHEMA_POS_FLOAT, doc='Speed of sound')
mspec.add_feature_spec('ambiance', fspec, doc='Ambient flight conditions')

# Feature 'aerodynamics'
fspec = FeatureSpec()
fspec.add_prop_spec('CL', SCHEMA_POS_FLOAT, doc='Cruise lift coefficient')
fspec.add_prop_spec('CD', SCHEMA_POS_FLOAT, doc='Cruise drag coefficient')
fspec.add_prop_spec('Mach', SCHEMA_POS_FLOAT, doc='Cruise Mach number')
mspec.add_feature_spec('aerodynamics', fspec, doc='Aerodynamic properties')

# Feature 'propulsion'
fspec = FeatureSpec()
fspec.add_prop_spec('cT',
                    SCHEMA_POS_FLOAT,
コード例 #9
0
def test_errors_add_feature_spec():
    """
    Test 'add_feature_spec()' method
    """

    fspec_door = FeatureSpec()
    fspec_door.add_prop_spec('color', str)

    fspec_motor = FeatureSpec()
    fspec_motor.add_prop_spec('type', str)

    mspec_car = ModelSpec()

    # ----- Wrong type: key -----
    with pytest.raises(TypeError):
        mspec_car.add_feature_spec(22, fspec_door)

    # ----- Wrong type: feature_spec -----
    with pytest.raises(TypeError):
        mspec_car.add_feature_spec('door', fspec_door.user_class)

    with pytest.raises(TypeError):
        mspec_car.add_feature_spec('door', fspec_door.user_class())

    # ----- Wrong type: singleton -----
    with pytest.raises(TypeError):
        mspec_car.add_feature_spec('door', fspec_door, singleton='yes')

    # Cannot add property twice...
    mspec_car.add_feature_spec('motor', fspec_motor)
    with pytest.raises(KeyError):
        mspec_car.add_feature_spec('motor', fspec_motor)
コード例 #10
0
ファイル: _model.py プロジェクト: airinnova/framat
    # Try to create directory if non-existent
    Path(value).mkdir(parents=True, exist_ok=True)
    if not os.access(value, os.W_OK):
        raise ValueError(f"{value!r} is not a valid directory")


# Register custom 'schemadict' types
SchemadictValidators.register_type(AbstractBeamMesh)
SchemadictValidators.register_type(np.ndarray)
SchemadictValidators.register_type(sparse.csr_matrix)
SchemadictValidators[str]['is_dir'] = is_dir

# =================
# ===== MODEL =====
# =================
mspec = ModelSpec()

tmp_doc = "The *{X}* feature is optional and allows to define sets of constant \
           {X} properties. When defining the properties for a specific beam \
           (or parts of it), you may refer to a {X} set using its UID. You may \
           define as many sets as you like."

# ===== Material =====
fspec = FeatureSpec()
fspec.add_prop_spec('E',
                    S.pos_number,
                    max_items=1,
                    doc="Young's modulus [N/m²]")
fspec.add_prop_spec('G', S.pos_number, max_items=1, doc="Shear modulus [N/m²]")
fspec.add_prop_spec('rho', S.pos_number, max_items=1, doc="Density [kg/m³]")
mspec.add_feature_spec(