// Copyright (C) Stichting Deltares 2023. All rights reserved. // // This file is part of the application DAM - UI. // // DAM - UI is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation, either version 3 of the License, or // (at your option) any later version. // // This program is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License // along with this program. If not, see . // // All names, logos, and references to "Deltares" are registered trademarks of // Stichting Deltares and remain full property of Stichting Deltares at all times. // All rights reserved. using System; using System.Collections.Generic; using System.IO; using System.Linq; using Deltares.Dam.Data; using Deltares.Dam.TestHelper; using Deltares.Geotechnics.Soils; using Deltares.Geotechnics.SurfaceLines; using KellermanSoftware.CompareNetObjects; using NUnit.Framework; namespace Deltares.Dam.Tests { /// /// In this test the XML serialization is tested. /// - Can old projects be loaded; A test should be included for each release of the software /// - Can the project be saved and loaded with the current version of the source /// [TestFixture] public class LoadCompatiblityTest { CompareLogic compare; /// /// Code that is run before each test /// [SetUp] public void Initialize() { compare = new CompareLogic { Config = { MaxDifferences = 100, CompareChildren = false, DoublePrecision = 0.000001, MembersToIgnore = new List { "SurfaceLineId", "SheetPilePoint", "SheetPilePointX", "SheetPilePointY", "SheetPilePointZ", "LocalXZSheetPilePoint", "SurfaceLine", "LocalXZSurfaceLine", "SoilLayer1D", "SoildatabaseName", "SoilList", "MapForSoilGeometries2D" } } }; } [Test] [Category("Integration")] public void CanLoadVersion_1_3_3_1() { const string projectFilenameHhnk = @"..\..\..\..\..\data\Dam\V 1.3.3.1\HHNK\TPL_Hempolder.damx"; using (DamProjectData projectData = ProjectLoader.LoadProjectData(projectFilenameHhnk)) { Assert.AreEqual(DamProjectType.AssessOld, projectData.DamProjectType); Assert.AreEqual(0, projectData.Locations.Count); } } /// /// Determines whether version_1_5_1_7 can be loaded. /// [Test] [Category("Integration")] public void CanLoadVersion_1_5_1_7_ScenariosPLLineParameters() { const string projectFilenameTutorialDesign = @"..\..\..\..\..\data\Dam\V 1.5.1.7\Tutorial Design\DAM Tutorial Design (Old 1.5.1.7).damx"; using (DamProjectData projectData = ProjectLoader.LoadProjectData(projectFilenameTutorialDesign)) { foreach (Location location in projectData.Locations) { // surfaceline2 present with characteristic points ? Assert.NotNull(location.SurfaceLine2); Assert.AreEqual(location.Name, location.SurfaceLine2.Name); Assert.AreEqual(true, location.SurfaceLine2.CharacteristicPoints.GeometryMustContainPoint); Assert.AreEqual(true, location.SurfaceLine2.HasDike()); } } } [Test] [Category("Integration")] public void CanLoadVersion_1_5_2_1() { const string fullProjectFilename = @"..\..\..\..\..\data\Dam\V 1.5.2.1\HHNK\TPL_Hempolder.damx"; using (DamProjectData projectData = ProjectLoader.LoadProjectData(fullProjectFilename)) { Assert.AreEqual(DamProjectType.AssessOld, projectData.DamProjectType); Assert.AreEqual(0, projectData.Locations.Count); } } [Test] [Category("Integration")] [TestCase(@"HHNK\TPL_Hempolder.damx", @"HHNK\TPL_Hempolder0.soilmaterials.mdb", "TPL_Hempolder_0100")] public void CanLoadVersion_14_1_1_14(string projectFilename, string expectedSoilbaseName, string locationName) { const string dataFolder = @"..\..\..\..\..\data\Dam\V 14.1.1.14\"; string fullProjectFilename = Path.Combine(dataFolder, projectFilename); using (DamProjectData projectData = ProjectLoader.LoadProjectData(fullProjectFilename)) { if (projectData.DamProjectType == DamProjectType.AssessOld) { Assert.AreEqual(0, projectData.Locations.Count); } else { // Check data using (Location expectedLocation = CreateHhnkTplHempolder100()) { expectedLocation.SoildatabaseName = Path.Combine(dataFolder, expectedSoilbaseName); Location actualLocation = projectData.Locations.Single(s => s.Name == locationName); CompareSegments(expectedLocation, actualLocation); ComparisonResult result = compare.Compare(expectedLocation, actualLocation); Assert.AreEqual(0, result.Differences.Count, result.DifferencesString); CheckHempolderSurfaceline(actualLocation); } } } } [Test] [TestCase(@"HHNK\TPL_Hempolder.damx", @"HHNK\TPL_Hempolder0.soilmaterials.mdb", "TPL_Hempolder_0100")] [TestCase(@"HHNKRegionalDesign\HHNK HemPolder Regional Design.damx", @"HHNKRegionalDesign\HHNK HemPolder Regional Design0.soilmaterials.mdb", "TPL_Hempolder_0100")] public void CanLoadVersion_15_1_1_3(string projectFilename, string expectedSoilbaseName, string locationName) { const string dataFolder = @"..\..\..\..\..\data\Dam\V 15.1.1.3\"; string fullProjectFilename = Path.Combine(dataFolder, projectFilename); using (DamProjectData projectData = ProjectLoader.LoadProjectData(fullProjectFilename)) { if (projectData.DamProjectType == DamProjectType.AssessOld) { Assert.AreEqual(0, projectData.Locations.Count); } else { // Check data using (Location expectedLocation = CreateHhnkTplHempolder100()) { expectedLocation.SoildatabaseName = Path.Combine(dataFolder, expectedSoilbaseName); Location actualLocation = projectData.Locations.Single(s => s.Name == locationName); CompareSegments(expectedLocation, actualLocation); ComparisonResult result = compare.Compare(expectedLocation, actualLocation); Assert.AreEqual(0, result.Differences.Count, result.DifferencesString); CheckHempolderSurfaceline(actualLocation); } } } } /// Determines whether a project of version 18.1.3 is loaded correctly. /// This test fails, because the following properties were moved from Location to location.Scenarios[] /// - PolderLevel /// - HeadPl2 /// - HeadPl3 /// - HeadPl4 /// And this is not handled correctly /// /// The project filename. /// Expected name of the soilbase. /// Name of the location. [Test] [TestCase(@"HHNK\TPL_Hempolder.damx", @"HHNK\TPL_Hempolder0.soilmaterials.mdb", "TPL_Hempolder_0100")] [TestCase(@"HHNKRegionalDesign\HHNK HemPolder Regional Design.damx", @"HHNKRegionalDesign\HHNK HemPolder Regional Design0.soilmaterials.mdb", "TPL_Hempolder_0100")] public void CanLoadVersion_18_1_3(string projectFilename, string expectedSoilbaseName, string locationName) { const string dataFolder = @"..\..\..\..\..\data\Dam\V 18.1.3\"; string fullProjectFilename = Path.Combine(dataFolder, projectFilename); using (DamProjectData projectData = ProjectLoader.LoadProjectData(fullProjectFilename)) { if (projectData.DamProjectType == DamProjectType.AssessOld) { Assert.AreEqual(0, projectData.Locations.Count); } else { using (Location expectedLocation = CreateHhnkTplHempolder100()) { expectedLocation.SoildatabaseName = Path.Combine(dataFolder, expectedSoilbaseName); Location actualLocation = projectData.Locations.Single(s => s.Name == locationName); CompareSegments(expectedLocation, actualLocation); ComparisonResult result = compare.Compare(expectedLocation, actualLocation); Assert.AreEqual(0, result.Differences.Count, result.DifferencesString); result = compare.Compare(expectedLocation.Scenarios[0], actualLocation.Scenarios[0]); Assert.AreEqual(0, result.Differences.Count, result.DifferencesString); CheckHempolderSurfaceline(actualLocation); } } // Check data } } /// Determines whether a project of version 19.1.1 is loaded correctly. /// This test fails, because the following properties were moved from Location to location.Scenarios[] /// - PolderLevel /// - HeadPl2 /// And this is not handled correctly /// /// The project filename. /// Expected name of the soilbase. /// Name of the location. [Test] [Category("Integration")] [TestCase(@"HHNKRegionalDesign\HHNK HemPolder Regional Design.damx", @"HHNKRegionalDesign\HHNK HemPolder Regional Design0.soilmaterials.mdb", "TPL_Hempolder_0100")] public void CanLoadVersion_19_1_1(string projectFilename, string expectedSoilbaseName, string locationName) { const string dataFolder = @"..\..\..\..\..\data\Dam\V 19.1.1\"; string fullProjectFilename = Path.Combine(dataFolder, projectFilename); using (DamProjectData projectData = ProjectLoader.LoadProjectData(fullProjectFilename)) { if (projectData.DamProjectType == DamProjectType.AssessOld) { Assert.AreEqual(0, projectData.Locations.Count); } else { using (Location expectedLocation = CreateHhnkTplHempolder100()) { expectedLocation.SoildatabaseName = Path.Combine(dataFolder, expectedSoilbaseName); Location actualLocation = projectData.Locations.Single(s => s.Name == locationName); CompareSegments(expectedLocation, actualLocation); ComparisonResult result = compare.Compare(expectedLocation, actualLocation); Assert.AreEqual(0, result.Differences.Count, result.DifferencesString); result = compare.Compare(expectedLocation.Scenarios[0], actualLocation.Scenarios[0]); Assert.AreEqual(0, result.Differences.Count, result.DifferencesString); CheckHempolderSurfaceline(actualLocation); } } // Check data } } [Test] [Category("Integration")] [TestCase(@"..\..\..\..\..\data\Dam\V 15.1.1.3\HHNKRegionalDesign\", @"HHNK HemPolder Regional Design - Calculated.damx")] [TestCase(@"..\..\..\..\..\data\Dam\V 18.1.3\HHNKRegionalDesign\", @"HHNK HemPolder Regional Design - Calculated.damx")] [TestCase(@"..\..\..\..\..\data\Dam\V 15.1.1.3\TutorialDesign\", @"DAM Tutorial Design - Calculated.damx")] [TestCase(@"..\..\..\..\..\data\Dam\V 18.1.3\TutorialDesign\", @"DAM Tutorial Design - Calculated.damx")] public void GivenOldProjectFileWithCalculationResultsWhenLoadingThisFileThenResultsAreNotLoaded( string dataFolder, string projectFilename) { string fullProjectFilename = Path.Combine(dataFolder, projectFilename); using (DamProjectData projectData = ProjectLoader.LoadProjectData(fullProjectFilename)) { Assert.AreEqual(0, projectData.DesignCalculations.Count); } } /// /// Test if the project can be saved and loaded with the current version of the source /// - Load old project /// - save this project /// - load this project /// - compare for a specific location if the data is correct /// This test is based on the same data as in CanLoadVersion_15_1_1_3() /// [Test] [Category("Work_In_Progress")] [Ignore("project uses Bishop which is not yet supported for MacroStability kernel.")] public void CanSaveAndLoadCurrentVersion() { const string projectFilenameHhnk = @"..\..\..\..\..\data\Dam\V 15.1.1.3\HHNKRegionalDesign\HHNK HemPolder Regional Design.damx"; const string projectFilenameCurrentVersion = @".\TPL_HempolderCurrent.damx"; // HHNK (Hollands Noorderkwartier) using (DamProjectData projectData = ProjectLoader.LoadProjectData(projectFilenameHhnk)) { // Save in current XML format DamProject.SaveData(projectFilenameCurrentVersion, projectData); // Load from current XML format using (DamProjectData currentProjectData = ProjectLoader.LoadProjectData(projectFilenameCurrentVersion)) using (Location expectedLocation = CreateHhnkTplHempolder100()) // Check data { expectedLocation.SoildatabaseName = @".\TPL_HempolderCurrent0.soilmaterials.mdb"; Location actualLocation = currentProjectData.Locations.Single(s => s.Name == "TPL_Hempolder_0100"); ComparisonResult result = compare.Compare(expectedLocation, actualLocation); Assert.AreEqual(0, result.Differences.Count, result.DifferencesString); } } } /// /// Create expected location for "TPL_Hempolder_0100" /// /// private Location CreateHhnkTplHempolder100() { var location = new Location { AreLocalXZObjectsCreated = true, Name = "TPL_Hempolder_0100", DikeRingId = "TPL_Hempolder", Description = "", XRd = 111232.178664511, YRd = 507197.06382921, SegmentId = "234", XSoilGeometry2DOrigin = 0.0, // actual value DikeEmbankmentMaterial = "HHNK1_Bfg", ShoulderEmbankmentMaterial = "HHNK1_Bfl", DampingFactorPL3 = 0.0, // actual value DampingFactorPL4 = 0.0, // actual value PenetrationLength = 0.0, // actual value TrafficLoad = 5.0, PLLineCreationMethod = PLLineCreationMethod.ExpertKnowledgeRRD, StabilityShoulderGrowSlope = 0.333333333333333, StabilityShoulderGrowDeltaX = 2.0, StabilitySlopeAdaptionDeltaX = 2.0, MinimalCircleDepth = 1.5, DistanceToEntryPoint = 0.0, // actual value StabilityZoneType = MStabZonesType.NoZones, Segment = new Segment { Name = "234" } }; location.Scenarios.Add(new Scenario { LocationScenarioID = "1", RiverLevel = 0.98, RiverLevelLow = 0.98, DikeTableHeight = 2.31, PolderLevel = -1.3, HeadPl2 = -1.3, HeadPl3 = -1.6, HeadPl4 = null, PlLineOffsetBelowDikeTopAtRiver = 0.5, // actual value PlLineOffsetBelowDikeTopAtPolder = 1.5, // actual value PlLineOffsetBelowShoulderBaseInside = 0.1, PlLineOffsetBelowDikeToeAtPolder = 0.1, // actual value ModelFactors = new ModelFactors { UpliftCriterionPiping = 1.2, UpliftCriterionStability = 1.2, RequiredSafetyFactorStabilityInnerSlope = 1.16, RequiredSafetyFactorStabilityOuterSlope = 1.0 } }); var soilProfile = new SoilProfile1D { Name = "Segment_234_1D1", BottomLevel = -29 }; soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_kade" }, 30) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tfo" }, -1) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Ppp" }, -1.5) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tfg" }, -4) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tcs" }, -5.5) { IsAquifer = true }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Bss" }, -24) { IsAquifer = true }); location.Segment.AddSoilProfileProbability(soilProfile, 0.0, FailureMechanismSystemType.StabilityInside); location.Segment.SoilProfileProbabilities[0].Probability = 69.3; soilProfile = new SoilProfile1D { Name = "Segment_234_1D2", BottomLevel = -29 }; soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_kade" }, 30) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tfo" }, -1) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Ppp" }, -1.5) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tfg" }, -4) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tcc" }, -5.5) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tcs" }, -12.5) { IsAquifer = true }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Bss" }, -24) { IsAquifer = true }); location.Segment.AddSoilProfileProbability(soilProfile, 0.0, FailureMechanismSystemType.StabilityInside); location.Segment.SoilProfileProbabilities[1].Probability = 0.7; soilProfile = new SoilProfile1D { Name = "Segment_234_1D3", BottomLevel = -29 }; soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_kade" }, 30) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tfo" }, -1) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Ppp" }, -1.5) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tfg" }, -4) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tcs" }, -7) { IsAquifer = true }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Bss" }, -24) { IsAquifer = true }); location.Segment.AddSoilProfileProbability(soilProfile, 0.0, FailureMechanismSystemType.StabilityInside); location.Segment.SoilProfileProbabilities[2].Probability = 29.7; soilProfile = new SoilProfile1D { Name = "Segment_234_1D4", BottomLevel = -29 }; soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_kade" }, 30) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tfo" }, -1) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Ppp" }, -1.5) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tfg" }, -4) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tcc" }, -7) { IsAquifer = false }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Tcs" }, -14) { IsAquifer = true }); soilProfile.Layers.Add(new SoilLayer1D(new Soil { Name = "HHNK1_Bss" }, -24) { IsAquifer = true }); location.Segment.AddSoilProfileProbability(soilProfile, 0.0, FailureMechanismSystemType.StabilityInside); location.Segment.SoilProfileProbabilities[3].Probability = 0.3; return location; } /// /// Compares the soil profiles. /// /// The expected soilprofile1D. /// The actual soilprofile1D. void CompareSoilProfiles(SoilProfile1D expectedSoilProfile1D, SoilProfile1D actualSoilProfile1D) { int expectedLayerCount = expectedSoilProfile1D.Layers.Count; int actualLayerCount = expectedSoilProfile1D.Layers.Count; Assert.AreEqual(expectedLayerCount, actualLayerCount); for (var layerIndex = 0; layerIndex < expectedLayerCount; layerIndex++) { Assert.AreEqual(expectedSoilProfile1D.Layers[layerIndex].Soil.Name, actualSoilProfile1D.Layers[layerIndex].Soil.Name, String.Format("Non-matching name in layer {0}", layerIndex)); Assert.AreEqual(expectedSoilProfile1D.Layers[layerIndex].IsAquifer, actualSoilProfile1D.Layers[layerIndex].IsAquifer, String.Format("Non-matching isAquifer in layer {0}", layerIndex)); } } private static void CheckHempolderSurfaceline(Location actualLocation) { const double accuracy = 0.01; // quick check for surfaceline2 conversion Assert.NotNull(actualLocation.SurfaceLine2); Assert.AreEqual("TPL_Hempolder_0100", actualLocation.SurfaceLine2.Name); Assert.AreEqual(true, actualLocation.SurfaceLine2.CharacteristicPoints.GeometryMustContainPoint); Assert.AreEqual(true, actualLocation.SurfaceLine2.HasDike()); CharacteristicPoint dikeToeAtRiver = actualLocation.SurfaceLine2.CharacteristicPoints.FirstOrDefault(p => p.CharacteristicPointType == CharacteristicPointType.DikeToeAtRiver); Assert.NotNull(dikeToeAtRiver); Assert.AreEqual(111222.28, dikeToeAtRiver.X, accuracy); Assert.AreEqual(507206.24, dikeToeAtRiver.Y, accuracy); } /// /// Compares the segments. /// /// The expected location. /// The actual location. private void CompareSegments(Location expectedLocation, Location actualLocation) { for (var soilProfile1DIndex = 0; soilProfile1DIndex < expectedLocation.Segment.SoilProfileProbabilities.Count; soilProfile1DIndex++) { CompareSoilProfiles(expectedLocation.Segment.SoilProfileProbabilities[soilProfile1DIndex].SoilProfile, actualLocation.Segment.SoilProfileProbabilities[soilProfile1DIndex].SoilProfile); } } } }