private void Validate_Click(object sender, RoutedEventArgs e) { var dlg = new OpenFileDialog { CheckFileExists = true, CheckPathExists = true, Multiselect = false, Filter = "IFC File|*.ifc|IFC XML File|*.ifcxml", FilterIndex = 0, Title = "Select IFC model file for validation", FileName = App.Settings.LastModel, InitialDirectory = Path.GetDirectoryName(App.Settings.LastModel) }; if (dlg.ShowDialog() != true) { return; } App.Settings.LastModel = dlg.FileName; var fileName = dlg.FileName; var bcfPath = Path.ChangeExtension(fileName, ".bcf"); XbimSchemaVersion schema; using (var temp = File.OpenRead(fileName)) { schema = MemoryModel.GetStepFileXbimSchemaVersion(temp); } var mvd = GetMvd(true, schema); var logger = XbimLogging.CreateLogger("MvdValidator"); using (var ifcStream = File.OpenRead(fileName)) using (var model = MemoryModel.OpenReadStep21(ifcStream, logger, null, ignoreTypes, false, false)) { var results = MvdValidator .ValidateModel(mvd, model) .ToList(); if (results.All(r => r.Concept == null && r.Result == ConceptTestResult.DoesNotApply)) { MessageBox.Show("No applicable entities in the file", "Warning", MessageBoxButton.OK, MessageBoxImage.Warning); return; } var failed = results.Where(r => r.Result == ConceptTestResult.Fail).GroupBy(r => r.Entity).ToList(); var passed = results.Where(r => r.Result == ConceptTestResult.Pass).GroupBy(r => r.Entity).ToList(); var skipped = results.Where(r => r.Result == ConceptTestResult.DoesNotApply).GroupBy(r => r.Entity).ToList(); var bcf = new BCFArchive(); // store reports as documents bcf.Documents.Add(WriteResults("failed.csv", failed.SelectMany(g => g))); bcf.Documents.Add(WriteResults("passed.csv", passed.SelectMany(g => g))); bcf.Documents.Add(WriteResults("skipped.csv", skipped.SelectMany(g => g))); // store actual MVD as a document var mvdStream = new MemoryStream(); mvd.Serialize(mvdStream); bcf.Documents.Add(new DocumentFile { Name = "validation.mvdXML", Stream = mvdStream }); // create topics var failedConcepts = results.Where(r => r.Result == ConceptTestResult.Fail).GroupBy(r => r.Concept.name).ToList(); var actor = ContextSelector.Context.OfType <Actor>().FirstOrDefault()?.Name ?? Actors.FirstOrDefault()?.Name ?? "*****@*****.**"; foreach (var concept in failedConcepts) { var issueId = Guid.NewGuid(); var viewpointId = Guid.NewGuid(); var defViewpointId = Guid.NewGuid(); var components = concept.Select(c => c.Entity).OfType <IIfcRoot>().Select(e => new Component { IfcGuid = e.GlobalId, AuthoringToolId = e.OwnerHistory?.OwningApplication?.ApplicationIdentifier, OriginatingSystem = e.EntityLabel.ToString(), }).ToList(); var issue = new TopicFolder { Id = issueId, Markup = new Markup { Header = new List <HeaderFile> { new HeaderFile { isExternal = true, Filename = Path.GetFileName(fileName), IfcProject = model.Instances.FirstOrDefault <IIfcProject>()?.GlobalId } }, Topic = new Topic { CreationDate = DateTime.Now, Guid = issueId.ToString(), Title = $"Failed validation of {concept.Key}", Description = $"This is automatically generater error report for DSS. This topic refers to all entities which should have {concept.Key} but it wasn't found.", DocumentReference = new List <TopicDocumentReference> { new TopicDocumentReference { isExternal = false, ReferencedDocument = "../Documents/failed.csv" }, new TopicDocumentReference { isExternal = false, ReferencedDocument = "../Documents/validation.mvdXML" } }, CreationAuthor = actor }, Comment = new List <Comment> { new Comment { Date = DateTime.Now, Author = actor, Comment1 = $"Failed validation of {concept.Key}", Viewpoint = new CommentViewpoint { Guid = viewpointId.ToString() } } }, Viewpoints = new List <ViewPoint> { new ViewPoint { Index = 0, Guid = defViewpointId.ToString(), Viewpoint = "viewpoint.bcfv" }, new ViewPoint { Index = 1, Guid = viewpointId.ToString(), Viewpoint = $"{viewpointId.ToString()}.bcfv" } } }, ViewPoints = new List <VisualizationInfo> { new VisualizationInfo { Guid = defViewpointId.ToString(), Components = new Components { ViewSetupHints = new ViewSetupHints { OpeningsVisible = false, SpaceBoundariesVisible = false, SpacesVisible = false }, Selection = concept.Select(c => c.Entity).OfType <IIfcRoot>().Select(e => new Component { IfcGuid = e.GlobalId, AuthoringToolId = e.OwnerHistory?.OwningApplication?.ApplicationIdentifier, OriginatingSystem = e.EntityLabel.ToString(), }).ToList(), Visibility = new ComponentVisibility { DefaultVisibility = true, Exceptions = new List <Component>() }, Coloring = new List <ComponentColoringColor> { new ComponentColoringColor { Color = "FF00FF00", Component = components } } }, }, new VisualizationInfo { Guid = viewpointId.ToString(), Components = new Components { ViewSetupHints = new ViewSetupHints { OpeningsVisible = false, SpaceBoundariesVisible = false, SpacesVisible = false }, Selection = components, Visibility = new ComponentVisibility { DefaultVisibility = false, Exceptions = new List <Component>() } }, } } }; bcf.Topics.Add(issue); } using (var s = File.Create(bcfPath)) { bcf.Serialize(s); } if (!failed.Any()) { MessageBox.Show($"All {passed.Count} applicable entities are valid. {skipped.Count} entities not applicable. Reports are saved in '{bcfPath}'", "Information", MessageBoxButton.OK, MessageBoxImage.Information); } else { MessageBox.Show($"{failed.Count} applicable entities are invalid. {skipped.Count} entities not applicable. Reports are saved in '{bcfPath}'", "Invalid entities", MessageBoxButton.OK, MessageBoxImage.Warning); } } }
public void ValidateShed() { const string mvdFile = "Files/CCI_for_doors.mvdXML"; const string ifcFile = "Files/Bouda.ifc"; using (var file = File.OpenRead(ifcFile)) { var mvd = mvdXML.Deserialize(File.ReadAllText(mvdFile)); var result = MvdValidator.ValidateModel(mvd, file, NullLogger.Instance); // nothing matches applicability selectors Assert.IsTrue(result.All(r => r.Concept == null && r.Result == ConceptTestResult.DoesNotApply)); } var classified = Guid.NewGuid() + ".ifc"; var doorCount = 0; using (var model = MemoryModel.OpenRead(ifcFile, null)) { doorCount = model.Instances.OfType <IIfcDoor>().Count();; using (var txn = model.BeginTransaction("Classification")) { var c = new Create(model); c.RelDefinesByProperties(r => { r.RelatingPropertyDefinition = c.PropertySet(ps => { ps.Name = "CZ_DataTemplateDesignation"; ps.HasProperties.Add(c.PropertySingleValue(p => { p.Name = "DataTemplateID"; p.NominalValue = new IfcLabel("52459"); })); }); r.RelatedObjects.AddRange(model.Instances.OfType <IIfcDoor>()); }); txn.Commit(); } using var file = File.Create(classified); model.SaveAsIfc(file); } using (var file = File.OpenRead(classified)) { var mvd = mvdXML.Deserialize(File.ReadAllText(mvdFile)); var result = MvdValidator.ValidateModel(mvd, file, NullLogger.Instance); var doorResults = result.Where(r => r.Entity is IIfcDoor).ToList(); Assert.AreEqual(doorCount, doorResults.Count); Assert.IsTrue(doorResults.All(r => r.Result == ConceptTestResult.Fail)); } var withCCI = Guid.NewGuid() + ".ifc"; using (var model = MemoryModel.OpenRead(classified, null)) { using (var txn = model.BeginTransaction("Classification")) { var c = new Create(model); c.RelDefinesByProperties(r => { r.RelatingPropertyDefinition = c.PropertySet(ps => { ps.Name = "CZ_ClassificationSystemCCI"; ps.HasProperties.AddRange(new[] { c.PropertySingleValue(p => { p.Name = "CCICode"; p.NominalValue = new IfcLabel("XXX"); }), c.PropertySingleValue(p => { p.Name = "FunctionalSystem"; p.NominalValue = new IfcLabel("XXX"); }), c.PropertySingleValue(p => { p.Name = "ContructiveSystem"; p.NominalValue = new IfcLabel("XXX"); }), c.PropertySingleValue(p => { p.Name = "CodeComponent"; p.NominalValue = new IfcLabel("XXX"); }) }); }); r.RelatedObjects.AddRange(model.Instances.OfType <IIfcDoor>()); }); txn.Commit(); } using var file = File.Create(withCCI); model.SaveAsIfc(file); } using (var file = File.OpenRead(withCCI)) { var mvd = mvdXML.Deserialize(File.ReadAllText(mvdFile)); var result = MvdValidator.ValidateModel(mvd, file, NullLogger.Instance); var doorResults = result.Where(r => r.Entity is IIfcDoor).ToList(); Assert.AreEqual(doorCount, doorResults.Count); Assert.IsTrue(doorResults.All(r => r.Result == ConceptTestResult.Pass)); } }