opensourceBIM / python-mvdxml

A mvdXML checker and w3c SPARQL converter, as an IfcOpenShell submodule or stand-alone.
GNU Lesser General Public License v3.0
33 stars 12 forks source link

Problems with official MVDXML examples #5

Closed e3dEF closed 4 years ago

e3dEF commented 4 years ago

Hi, first, thank you for sharing this code. I find it very promising and wanted to test the code using the mvdXML files in the buildingSmart repo, but couldn't run most of them. Here are my results. https://github.com/buildingSMART/mvdXML/tree/master/mvdXML1.1

Example-CV100.xml return _ifcopenshell_wrapper.file_by_type(self, *args) RuntimeError: Entity with 'Slab' not found. Maybe entities = ifc_file.by_type(mvd_concept.name) should be entities = ifc_file.by_type(mvd_concept.entity)?

Example-CV104.xml: crashes. AttributeError: entity instance of type 'IfcRelVoidsElement' has no attribute 'RelatingElement' I think, that's an error in the mvdxml.

Example-CV100.xml: finishes, but no result in with my tested buildings.

mvdXMLv1-1_example2.xml concepts = sorted(mvd_concept.concepts(), key=is_applicability, reverse=True) AttributeError: 'template' object has no attribute 'concepts'

*mvdXMLv1-1_example1.xml, mvdXMLv1-1_example3.xml, mvdXMLv1-1_example4.xml, mvdXMLv1-1_example5.xml my_concept_object = list(ifcopenshell.mvd.concept_root.parse(filename))[0] IndexError: list index out of range. The list is empty

Is it planned to support the examples? What are the constrains to your code atm?

Kind regards

johltn commented 4 years ago

Thanks for your involvement in this project! Indeed, entities = ifc_file.by_type(mvd_concept.entity) is right, feel free to send a PR. Regarding the support of the official mvdXML examples, we're currently making the changes so it will be available shortly.

johltn commented 4 years ago

There was a bit of testing to make it work with the mvdXML files you mentioned. Hopefully with slight modifications of the traversal function we can get the expected output.

For testing, we can take the model here in IFC4 at http://openifcmodel.cs.auckland.ac.nz/Model/Details/307 and apply each of the mvdXML example files on it. Let's check what it gives with this code:

import ifcopenshell
from ifcopenshell.mvd import mvd

concept_roots = list(ifcopenshell.mvd.concept_root.parse(r"examples/Example-CV100.mvdxml"))
file = ifcopenshell.open(r"models\20160125Autodesk_Hospital_Parking Garage_2015 - IFC4.ifc")

for concept_root in concept_roots:
    print("ConceptRoot: ", concept_root.entity)
    example_entity = file.by_type(concept_root.entity)[0]

    concepts = sorted(concept_root.concepts(), key=mvd.is_applicability, reverse=True)
    for concept in concepts:
        print("Concept Name: ", concept.name)
        # print(concept.template().rules)

        if len(concept.template().rules) > 1:
            attribute_rules = []
            for rule in concept.template().rules:
                attribute_rules.append(rule)
            rules_root = ifcopenshell.mvd.rule("EntityRule", concept_root.entity, attribute_rules)
        else:
            rules_root = concept.template().rules[0]

        data = mvd.extract_data(rules_root, example_entity)
        print("Result from traversal:")
        for d in data:
            for k,v in d.items():
                print(k,v)
            print()

    print("\n")

Check the results for each file

mvdXML file : Example-CV100.mvdxml

Output:

ConceptRoot:  IfcSlab
Concept Name:  Material Layer Set Usage
Result from traversal:
<Rule AttributeRule Name> Nonexistent value
<Rule EntityRule IfcLabel> Concrete - Cast-in-Place Concrete
<Rule AttributeRule Description> Nonexistent value
<Rule AttributeRule Category> Nonexistent value
<Rule EntityRule IfcNonNegativeLengthMeasure> 0.416666666666667
<Rule EntityRule IfcLabel> Floor:Concrete Slab - 5"
<Rule AttributeRule Description> Nonexistent value
<Rule EntityRule IfcDirectionSenseEnum> POSITIVE
<Rule EntityRule IfcLayerSetDirectionEnum> AXIS3

mvdXML file : Example-CV104.mvdxml

Output:

ConceptRoot:  IfcDoor
Concept Name:  Filling
Result from traversal:
<Rule AttributeRule RelatingElement> Invalid attribute rule
<Rule AttributeRule HasFillings> (#202155=IfcRelFillsElement('0Si69GYL9A6xbtOWNjqWtl',#42,$,$,#202140,#146855),)

ConceptRoot:  IfcWindow
Concept Name:  Filling
Result from traversal:
<Rule AttributeRule RelatingElement> Invalid attribute rule
<Rule AttributeRule HasFillings> (#201069=IfcRelFillsElement('0X6Ca1x8T69QCRTO$M6YVl',#42,$,$,#201054,#39231),)

mvdXML file : Example-CV106.mvdxml

Output:

ConceptRoot:  IfcProject
Concept Name:  Project Context
Result from traversal:
<Rule AttributeRule ContextIdentifier> Nonexistent value
<Rule EntityRule IfcLabel> Model
<Rule EntityRule IfcDimensionCount> 3
<Rule EntityRule IfcAxis2Placement3D> #99=IfcAxis2Placement3D(#6,$,$)
<Rule EntityRule IfcDirection> #100=IfcDirection((0.999390827019095,0.0348994967025161))
<Rule EntityRule IfcLabel> Axis
<Rule EntityRule IfcLabel> Model

<Rule AttributeRule ContextIdentifier> Nonexistent value
<Rule EntityRule IfcLabel> Model
<Rule EntityRule IfcDimensionCount> 3
<Rule EntityRule IfcAxis2Placement3D> #99=IfcAxis2Placement3D(#6,$,$)
<Rule EntityRule IfcDirection> #100=IfcDirection((0.999390827019095,0.0348994967025161))
<Rule EntityRule IfcLabel> Body
<Rule EntityRule IfcLabel> Model

<Rule AttributeRule ContextIdentifier> Nonexistent value
<Rule EntityRule IfcLabel> Model
<Rule EntityRule IfcDimensionCount> 3
<Rule EntityRule IfcAxis2Placement3D> #99=IfcAxis2Placement3D(#6,$,$)
<Rule EntityRule IfcDirection> #100=IfcDirection((0.999390827019095,0.0348994967025161))
<Rule EntityRule IfcLabel> Box
<Rule EntityRule IfcLabel> Model

<Rule AttributeRule ContextIdentifier> Nonexistent value
<Rule EntityRule IfcLabel> Model
<Rule EntityRule IfcDimensionCount> 3
<Rule EntityRule IfcAxis2Placement3D> #99=IfcAxis2Placement3D(#6,$,$)
<Rule EntityRule IfcDirection> #100=IfcDirection((0.999390827019095,0.0348994967025161))
<Rule EntityRule IfcLabel> FootPrint
<Rule EntityRule IfcLabel> Model

Regarding mvdXMLv1-1_example1.mvdxml and mvdXMLv1-1_example12.mvdxml, those files

do not contain any Rules so there is currently nothing planned for this type of file.

For mvdXMLv1-1_example2.mvdxml, mvdXMLv1-1_example3.mvdxml, and mvdXMLv1-1_example4.mvdxml, those files are standalone Templates.

Using this snippet, we can get some results, for example querying the IfcWall ConceptRoot:

import ifcopenshell
from ifcopenshell.mvd import mvd

mvd_concept = mvd.open_mvd(r"examples/4.mvdxml")
file = ifcopenshell.open(r"models\20160125Autodesk_Hospital_Parking Garage_2015 - IFC4.ifc")

print("Concept Name: ", mvd_concept.name)
print("Rules:", mvd_concept.rules)

concept_root = "IfcWall"
example_entity = file.by_type(concept_root)[0]

if len(mvd_concept.rules) > 1:
    attribute_rules = []
    for rule in mvd_concept.rules:
        attribute_rules.append(rule)
    rules_root = ifcopenshell.mvd.rule("EntityRule", concept_root, attribute_rules)
else:
    rules_root = mvd_concept.rules[0]

data = mvd.extract_data(rules_root, example_entity)
print("Result from traversal:")
for d in data:
    for k, v in d.items():
        print(k, v)
    print()

mvdXML file : mvdXMLv1-1_example2.mvdxml

Output:

Concept Name:  Axis Geometry
Rules: [<Rule AttributeRule Representation>]
Result from traversal:
<Rule EntityRule IfcGeometricRepresentationContext> #105=IfcGeometricRepresentationSubContext('Axis','Model',*,*,*,*,#102,$,.GRAPH_VIEW.,$)
<Rule EntityRule IfcLabel> Axis
<Rule EntityRule IfcLabel> Curve2D
<Rule AttributeRule StyledByItem> empty data structure

<Rule EntityRule IfcGeometricRepresentationContext> #105=IfcGeometricRepresentationSubContext('Axis','Model',*,*,*,*,#102,$,.GRAPH_VIEW.,$)
<Rule EntityRule IfcLabel> Axis
<Rule Constraint [{None[Value]='Curve3D'}]> Curve2D
<Rule AttributeRule StyledByItem> empty data structure

<Rule EntityRule IfcGeometricRepresentationContext> #105=IfcGeometricRepresentationSubContext('Axis','Model',*,*,*,*,#102,$,.GRAPH_VIEW.,$)
<Rule Constraint [{None[Value]='Axis'}]> Axis
<Rule EntityRule IfcLabel> Curve2D
<Rule AttributeRule StyledByItem> empty data structure

<Rule EntityRule IfcGeometricRepresentationContext> #105=IfcGeometricRepresentationSubContext('Axis','Model',*,*,*,*,#102,$,.GRAPH_VIEW.,$)
<Rule Constraint [{None[Value]='Axis'}]> Axis
<Rule Constraint [{None[Value]='Curve3D'}]> Curve2D
<Rule AttributeRule StyledByItem> empty data structure

mvdXML file : mvdXMLv1-1_example3.mvdxml

Output:

Concept Name:  Port
Rules: [<Rule AttributeRule PredefinedType>, <Rule AttributeRule IsNestedBy>]
Result from traversal:
<Rule AttributeRule PredefinedType> NOTDEFINED
<Rule AttributeRule IsNestedBy> empty data structure

mvdXML file : mvdXMLv1-1_example4.mvdxml

Output:

Concept Name:  Beam
Rules: [<Rule AttributeRule HasAssociations>, <Rule AttributeRule Representation>]
Result from traversal:
<Rule AttributeRule RelatedMaterial> Invalid attribute rule
<Rule Constraint [{None[Value]='Body'}]> Body
<Rule Constraint [{None[Value]=MP}]> SweptSolid
<Rule AttributeRule SweptProfile> Invalid attribute rule

mvdXML file : mvdXMLv1-1_example5.mvdxml

I didn't have a file containing an IfcSensor instance but I replaced it by an IfcWall in and it works fine.

Output:

ConceptRoot:  IfcWall
Concept Name:  Port
Result from traversal:
<Rule AttributeRule PredefinedType> NOTDEFINED
<Rule AttributeRule IsNestedBy> empty data structure