Beispiel #1
0
        public void ParentChildRelationFinder_SmallHierarchy_ReturnsParentlessRelations()
        {
            // Arrange
            var builder = new ArdoqModelMappingBuilder(null, null, null);
            var m1      = builder.AddComponentMapping <Subscription>("Subscription");
            var m2      = builder.AddComponentMapping <ResourceGroup>("ResourceGroup")
                          .WithModelledHierarchyReference(rg => rg.Subscription, ModelledReferenceDirection.Child);

            var mappings = new Dictionary <Type, IBuiltComponentMapping>
            {
                [typeof(Subscription)]  = m1,
                [typeof(ResourceGroup)] = m2
            };

            var sub = new Subscription {
                Name = "NETT-MDM"
            };
            var resGroup = new ResourceGroup {
                Name = "MDM-RGdev", Subscription = sub
            };
            var objs = new List <object> {
                sub, resGroup
            };

            var finder = new ParentChildRelationFinder(mappings);

            // Act
            var relations = finder.FindRelations(objs).ToList();

            // Assert
            Assert.Equal(2, relations.Count);
            Assert.Contains(relations, r => r.Child == sub && r.Parent == null);
            Assert.Contains(relations, r => r.Child == resGroup && r.Parent == sub);
        }
Beispiel #2
0
        public void Build_ModelWithMultipleChildren_ComponentMappingsSorted()
        {
            // Arrange
            ArdoqModelMappingBuilder builder = Builder();

            // Act
            builder.AddComponentMapping <Role>("Role")
            .WithKey(s => s.Name);
            builder.AddComponentMapping <Department>("Department")
            .WithKey(s => s.Name);
            builder.AddComponentMapping <Office>("Office")
            .WithKey(s => s.Name);
            builder.AddComponentMapping <Employee>("Employee")
            .WithKey(s => s.Name)
            .WithModelledHierarchyReference(e => e.EmployedIn, ModelledReferenceDirection.Child)
            .WithModelledHierarchyReference(e => e.Roles, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(e => e.Office, ModelledReferenceDirection.Parent);
            builder.Build();

            // Assert
            var list = builder.ComponentMappings.ToList();

            Assert.Equal("Department", list[0].ArdoqComponentTypeName);
            Assert.Equal("Employee", list[1].ArdoqComponentTypeName);
            Assert.Equal(new HashSet <string> {
                "Role", "Office"
            }, new HashSet <string> {
                list[2].ArdoqComponentTypeName, list[3].ArdoqComponentTypeName
            });
        }
Beispiel #3
0
        public void Build_ProperModel_ParentsComputedCorrectly()
        {
            // Arrange
            ArdoqModelMappingBuilder builder = Builder();

            // Act
            builder.AddComponentMapping <Department>("Department")
            .WithKey(s => s.Name);
            builder.AddComponentMapping <Employee>("Employee")
            .WithKey(s => s.Name)
            .WithModelledHierarchyReference(e => e.EmployedIn, ModelledReferenceDirection.Child)
            .WithModelledHierarchyReference(e => e.Roles, ModelledReferenceDirection.Parent);
            builder.AddComponentMapping <Role>("Role")
            .WithKey(s => s.Name);
            builder.Build();

            // Assert
            var list = builder.ComponentMappings.ToList();

            Assert.Equal("Department", list[0].ArdoqComponentTypeName);
            Assert.Null(list[0].GetParent()?.ArdoqComponentTypeName);
            Assert.Equal("Employee", list[1].ArdoqComponentTypeName);
            Assert.Equal("Department", list[1].GetParent().ArdoqComponentTypeName);
            Assert.Equal("Role", list[2].ArdoqComponentTypeName);
            Assert.Equal("Employee", list[2].GetParent().ArdoqComponentTypeName);
        }
Beispiel #4
0
        public void Configure(ArdoqModelMappingBuilder builder)
        {
            // Subscription
            builder.AddComponentMapping <Subscription>("Subscription")
            .WithKey(s => s.Name)
            .WithModelledHierarchyReference(s => s.ResourceGroups, ModelledReferenceDirection.Parent);

            // Resource Group
            builder.AddComponentMapping <ResourceGroup>("Resource group")
            .WithKey(rg => rg.Name)
            .WithTags(rg => rg.Tags)
            .WithModelledHierarchyReference(rg => rg.SqlServers, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.StorageAccounts, ModelledReferenceDirection.Parent);

            // SQL
            builder.AddComponentMapping <SqlServer>("SQL server")
            .WithKey(s => s.Name)
            .WithModelledHierarchyReference(s => s.Databases, ModelledReferenceDirection.Parent);

            builder.AddComponentMapping <SqlDatabase>("SQL database")
            .WithKey(s => s.Name)
            .WithTags(s => s.Tags)
            .WithField(s => s.Uri, "Uri");

            // Storage
            builder.AddComponentMapping <StorageAccount>("Storage account")
            .WithTags(s => s.Tags)
            .WithKey(s => s.Name);
        }
Beispiel #5
0
        public void Run_WorkspaceDoesNotExistAndNoTemplateSet_ThrowsException()
        {
            // Arrange
            string folderName = "MyFolder";

            _readerMock.Setup(r => r.GetFolder(folderName))
            .Returns(Task.FromResult(new Folder(folderName, "My folder")
            {
                Workspaces = new List <string>()
            }));

            var builder = new ArdoqModelMappingBuilder(null, null, null)
                          .WithWorkspaceNamed("Test")
                          .WithFolderNamed(folderName)
                          .WithReader(_readerMock.Object)
                          .WithWriter(_writerMock.Object)
                          .WithSearcher(_searcherMock.Object);

            var session = builder.Build();

            // Act
            var ex = Assert.Throws <AggregateException>(() => session.Run(_modelProviderMock.Object).Wait());

            Assert.True(ex.InnerExceptions.First() is InvalidOperationException);
            var inner = ex.InnerExceptions.First();

            Assert.Equal("Template name must be set when creating workspace.", inner.Message);
        }
    public static void Main(string[] args)
    {
        var ardoqUrl          = "https://app.ardoq.com/";
        var ardoqToken        = "<secret-ardoq-token>";
        var ardoqOrganization = "<ardoq-org>";
        var workspace         = "<ardoq-workspace>";
        var folder            = "<ardoq-folder>";

        // Create a builder
        var builder =
            new ArdoqModelMappingBuilder(ardoqUrl, ardoqToken, ardoqOrganization)
            .WithWorkspaceNamed(workspace)
            .WithFolderNamed(folder);

        // Add your structured model. This must match the model in Ardoq.
        builder.AddComponentMapping <MyComponent>("MyComponent")
        .WithKey(s => s.MyKey);

        // Create the source model provider. This supplies the objects which will be documented in Ardoq.
        ISourceModelProvider sourceModelProvider = new MySourceModelProvider();

        // Build and run
        var session = builder.Build();

        session.Run(sourceModelProvider).Wait();
    }
Beispiel #7
0
        public void FindRelations_DeclaredReferenceButNullReference_ReturnsChildReference()
        {
            // Arrange
            var builder = new ArdoqModelMappingBuilder(null, null, null);
            var m1      = builder.AddComponentMapping <Department>("Department")
                          .WithKey(d => d.Name);
            var m2 = builder.AddComponentMapping <Employee>("Employee")
                     .WithKey(e => e.EmployeeNumber)
                     .WithModelledHierarchyReference(e => e.EmployedIn, ModelledReferenceDirection.Child);

            var mappings = new Dictionary <Type, IBuiltComponentMapping>
            {
                [typeof(Department)] = m1,
                [typeof(Employee)]   = m2
            };

            var employee = new Employee {
                Name = "Bjørn Borg"
            };
            var objs = new List <object> {
                employee
            };

            var finder = new ParentChildRelationFinder(mappings);

            // Act
            var relations = finder.FindRelations(objs).ToList();

            // Assert
            Assert.Single(relations);
            var r = relations.First();

            Assert.Null(r.Parent);
            Assert.Same(employee, r.Child);
        }
Beispiel #8
0
        public void ParentChildRelationFinder_SingleObjectWithPreexistingHierarchyReference_RelationHasPreexistingHierarchyReference()
        {
            // Arrange
            var builder = new ArdoqModelMappingBuilder(null, null, null);
            var m2      = builder.AddComponentMapping <ResourceGroup>("ResourceGroup");

            m2.WithPreexistingHierarchyReference("ResourceGroups");
            var mappings = new Dictionary <Type, IBuiltComponentMapping>
            {
                [typeof(ResourceGroup)] = m2
            };

            var objs = new List <object> {
                new ResourceGroup {
                    Name = "MDM-RGprod"
                }
            };

            var finder = new ParentChildRelationFinder(mappings);

            // Act
            var relations = finder.FindRelations(objs).ToList();

            // Assert
            Assert.Single(relations);
            var r = relations.Single();

            Assert.Equal("ResourceGroups", r.PreexistingHierarchyReference);
        }
Beispiel #9
0
        public void Configure_HappyDays_NoExceptions()
        {
            // Arrange
            var builder = new ArdoqModelMappingBuilder(null, null, null);
            var module  = new AzureMaintenanceModule();

            // Act
            module.Configure(builder);
        }
Beispiel #10
0
        public void SampleConfig()
        {
            var builder = new ArdoqModelMappingBuilder(null, null, null)
                          .WithWorkspaceNamed("Blank Workspace")
                          .WithFolderNamed("Ståle");

            builder.AddComponentMapping <Employee>("Employee")
            .WithKey(e => e.EmployeeNumber)
            .WithPreexistingHierarchyReference("Employees");
        }
Beispiel #11
0
        public void Build_EmptyModel_ReturnsEmptyMap()
        {
            // Arrange
            ArdoqModelMappingBuilder builder = Builder();

            // Act
            builder.Build();

            // Assert
            Assert.Empty(builder.ComponentMappings);
        }
Beispiel #12
0
        public void AddComponentMapping_SameClassTwice_ThrowsArgumentException()
        {
            // Arrange
            var builder = new ArdoqModelMappingBuilder(null, null, null);

            // Act
            builder.AddComponentMapping <Employee>("Employee")
            .WithPreexistingHierarchyReference("Employees");

            // Assert
            var ex = Assert.Throws <ArgumentException>(() => builder.AddComponentMapping <Employee>("Employee2"));

            Assert.Equal("Source type ModelMaintainer.Tests.Model.Employee already registered.", ex.Message);
        }
Beispiel #13
0
        public void WithSafeMode_NotSpecified_IsNotSafeMode()
        {
            // Arrange
            var builder = new ArdoqModelMappingBuilder(null, null, null);

            // Act
            builder
            .WithReader(_readerMock.Object)
            .WithWriter(_writerMock.Object)
            .WithSearcher(_searcherMock.Object);

            var session = builder.Build();

            // Assert
            Assert.False(session.IsSafeMode);
        }
Beispiel #14
0
        public void WithKey_HappyDays_KeySetInBuilder()
        {
            // Arrange
            var builder = new ArdoqModelMappingBuilder(null, null, null);

            // Act
            builder.AddComponentMapping <Role>("Role")
            .WithPreexistingHierarchyReference("Roles")
            .WithKey(s => s.Name);

            // Assert
            var mapping = builder.GetBuildableComponentMapping <Role>();

            Assert.NotNull(mapping.KeyGetter);
            Assert.Equal("Name", mapping.KeyGetter.Name);
        }
Beispiel #15
0
        public void Build_ModelNotValid_ThrowsException()
        {
            // Arrange
            ArdoqModelMappingBuilder builder = Builder();

            // Act
            builder.AddComponentMapping <Role>("Role")
            .WithKey(s => s.Name);
            builder.AddComponentMapping <Employee>("Employee")
            .WithKey(s => s.Name)
            .WithModelledHierarchyReference(e => e.EmployedIn, ModelledReferenceDirection.Child)
            .WithModelledHierarchyReference(e => e.Roles, ModelledReferenceDirection.Parent);

            // Assert
            Assert.ThrowsAny <Exception>(() => builder.Build());
        }
Beispiel #16
0
        public void GetComponentType_TypeNotRegistered_ReturnsNull()
        {
            // Arrange
            var builder = new ArdoqModelMappingBuilder(null, null, null)
                          .WithReader(_readerMock.Object)
                          .WithWriter(_writerMock.Object)
                          .WithSearcher(_searcherMock.Object);

            var session = builder.Build();

            // Act
            var comType = session.GetComponentType(typeof(Employee));

            // Assert
            Assert.Null(comType);
        }
Beispiel #17
0
        public void GetComponentType_AfterRegistration_GetsExpectedComponentType()
        {
            // Arrange
            var componentTypeEmployee = "EmployeeCompType";
            var builder = new ArdoqModelMappingBuilder(null, null, null)
                          .WithReader(_readerMock.Object)
                          .WithWriter(_writerMock.Object)
                          .WithSearcher(_searcherMock.Object);

            builder.AddComponentMapping <Employee>(componentTypeEmployee);

            var session = builder.Build();

            // Act
            var comType = session.GetComponentType(typeof(Employee));

            // Assert
            Assert.Equal(componentTypeEmployee, comType);
        }
Beispiel #18
0
 public MaintainenceSession(
     ArdoqModelMappingBuilder builder,
     IArdoqReader reader,
     IArdoqWriter writer,
     IArdoqWorkspaceCreator workspaceCreator,
     IExternalLinkageService externalLinkageService,
     IArdoqSearcher searcher,
     bool safeMode,
     ILogger logger)
 {
     _builder                = builder;
     _reader                 = reader;
     _writer                 = writer;
     _workspaceCreator       = workspaceCreator;
     _externalLinkageService = externalLinkageService;
     _searcher               = searcher;
     _safeMode               = safeMode;
     _logger                 = logger;
 }
Beispiel #19
0
        public void GetKeyForInstance_NotRegistered_ReturnsNull()
        {
            var builder = new ArdoqModelMappingBuilder(null, null, null)
                          .WithReader(_readerMock.Object)
                          .WithWriter(_writerMock.Object)
                          .WithSearcher(_searcherMock.Object);

            var employeeNumber = "007";
            var employee       = new Employee {
                EmployeeNumber = employeeNumber
            };

            var session = builder.Build();

            // Act
            var key = session.GetKeyForInstance(employee);

            // Assert
            Assert.Null(key);
        }
Beispiel #20
0
        public void Run_WorkspaceDoesNotExistHasTemplate_CreatesNewWorkspace()
        {
            // Arrange
            string workspaceName  = "Test";
            string folderName     = "MyFolder";
            string componentModel = "5bab5cc8b3da08632a73ed2f";
            string folderId       = "folder-id";

            var folder = new Folder(folderName, "My folder")
            {
                Id = folderId, Workspaces = new List <string>()
            };

            _readerMock.Setup(r => r.GetFolder(folderName))
            .Returns(Task.FromResult(folder));

            _readerMock.Setup(r => r.GetTemplateByName(componentModel))
            .Returns(Task.FromResult((IArdoqModel) new ArdoqModel(new global::Ardoq.Models.Model()
            {
                Id = "666"
            })));

            _writerMock.Setup(w => w.CreateWorkspace(It.IsAny <Workspace>()))
            .Returns(Task.FromResult(new Workspace(workspaceName, "")));

            var builder = new ArdoqModelMappingBuilder(null, null, null)
                          .WithWorkspaceNamed(workspaceName)
                          .WithFolderNamed(folderName)
                          .WithTemplate(componentModel)
                          .WithReader(_readerMock.Object)
                          .WithWriter(_writerMock.Object)
                          .WithSearcher(_searcherMock.Object);

            var session = builder.Build();

            // Act
            session.Run(_modelProviderMock.Object).Wait();

            // Assert
            _writerMock.Verify(w => w.CreateWorkspace(It.IsAny <Workspace>()));
        }
Beispiel #21
0
        public static void Main(string[] args)
        {
            var config   = IoC.GetConfiguration();
            var provider = IoC.Resolve <ISourceModelProvider>();

            var builder =
                new ArdoqModelMappingBuilder(config["Ardoq:url"], config["Ardoq:token"], config["Ardoq:organization"])
                .WithWorkspaceNamed(config["Ardoq:workspaceName"])
                .WithFolderNamed(config["Ardoq:folderName"])
                .WithTemplate(config["Ardoq:templateName"]);

            var module = new AzureMaintenanceModule();

            module.Configure(builder);

            var session = builder.Build();

            session.Run(provider).Wait();

            Task.Delay(1000).Wait();
        }
Beispiel #22
0
        public void ParentChildRelationFinder_NoHierarchy_ReturnsParentlessRelations()
        {
            // Arrange
            var builder  = new ArdoqModelMappingBuilder(null, null, null);
            var m1       = builder.AddComponentMapping <Subscription>("Subscription");
            var m2       = builder.AddComponentMapping <ResourceGroup>("ResourceGroup");
            var mappings = new Dictionary <Type, IBuiltComponentMapping>
            {
                [typeof(Subscription)]  = m1,
                [typeof(ResourceGroup)] = m2
            };

            var o1 = new Subscription {
                Name = "NETT-MDM"
            };
            var o2 = new ResourceGroup {
                Name = "MDM-RGdev"
            };
            var o3 = new ResourceGroup {
                Name = "MDM-RGtest"
            };
            var o4 = new ResourceGroup {
                Name = "MDM-RGprod"
            };
            var objs = new List <object> {
                o1, o2, o3, o4
            };

            var finder = new ParentChildRelationFinder(mappings);

            // Act
            var relations = finder.FindRelations(objs).ToList();

            // Assert
            Assert.Equal(4, relations.Count());
            Assert.Contains(relations, r => r.Child == o1);
            Assert.Contains(relations, r => r.Child == o2);
            Assert.Contains(relations, r => r.Child == o3);
            Assert.Contains(relations, r => r.Child == o4);
        }
Beispiel #23
0
        public void GetKeyForInstance_RegisteredType_ReturnsExpectedKey()
        {
            var componentTypeEmployee = "EmployeeCompType";
            var builder = new ArdoqModelMappingBuilder(null, null, null)
                          .WithReader(_readerMock.Object)
                          .WithSearcher(_searcherMock.Object)
                          .WithWriter(_writerMock.Object);

            builder.AddComponentMapping <Employee>(componentTypeEmployee)
            .WithKey(emp => emp.EmployeeNumber);

            var employeeNumber = "007";
            var employee       = new Employee {
                EmployeeNumber = employeeNumber
            };

            var session = builder.Build();

            // Act
            var key = session.GetKeyForInstance(employee);

            // Assert
            Assert.Equal(employeeNumber, key);
        }
Beispiel #24
0
        public void Configure(ArdoqModelMappingBuilder builder)
        {
            // Subscription
            builder.AddComponentMapping <Subscription>("Subscription")
            .WithKey(s => s.Name)
            .WithModelledHierarchyReference(s => s.ResourceGroups, ModelledReferenceDirection.Parent);

            // Resource Group
            builder.AddComponentMapping <ResourceGroup>("Resource group")
            .WithKey(rg => rg.Name)
            .WithModelledHierarchyReference(rg => rg.EventHubsNamespaces, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.SqlServers, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.StorageAccounts, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.ServiceBusNamespaces, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.SearchServices, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.CosmosDBAccounts, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.RedisCaches, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.KeyVaults, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.AccessManagements, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.AlertRules, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.ApplicationGateways, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.AutoscaleSettings, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.AvailabilitySets, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.BatchAccounts, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.CdnProfiles, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.ComputeSkus, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.Disks, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.DnsZones, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.LoadBalancers, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.NetworkSecurityGroups, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.PublicIPAddresses, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.Snapshots, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.TrafficManagerProfiles, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.VirtualMachines, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.VirtualMachineCustomImages, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.VirtualMachineScaleSets, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rg => rg.VirtualNetworks, ModelledReferenceDirection.Parent)
            .WithTags(Tags.FromExpression <ResourceGroup>(
                          rg => rg.Tags?.Select(t => $"{t.Key}-{t.Value}") ?? new List <string>()));

            // Event Hubs Namespace
            builder.AddComponentMapping <EventHubsNamespace>("Event Hubs Namespace")
            .WithKey(ehn => ehn.Name)
            .WithModelledHierarchyReference(ehn => ehn.EventHubs, ModelledReferenceDirection.Parent)
            .WithTags(Tags.FromExpression <EventHubsNamespace>(
                          rg => rg.Tags?.Select(t => $"{t.Key}-{t.Value}") ?? new List <string>()));

            builder.AddComponentMapping <EventHub>("Event Hub")
            .WithKey(eh => eh.Name)
            .WithModelledHierarchyReference(eh => eh.ConsumerGroups, ModelledReferenceDirection.Parent);

            builder.AddComponentMapping <ConsumerGroup>("Consumer Group")
            .WithKey(cg => cg.Name);

            // SQL
            builder.AddComponentMapping <SqlServer>("SQL server")
            .WithKey(s => s.Name)
            .WithModelledHierarchyReference(s => s.Databases, ModelledReferenceDirection.Parent)
            .WithTags(Tags.FromExpression <SqlServer>(
                          rg => rg.Tags?.Select(t => $"{t.Key}-{t.Value}") ?? new List <string>()));

            builder.AddComponentMapping <SqlDatabase>("SQL database")
            .WithKey(s => s.Name);

            // Storage
            builder.AddComponentMapping <StorageAccount>("Storage account")
            .WithKey(s => s.Name)
            .WithTags(Tags.FromExpression <StorageAccount>(
                          rg => rg.Tags?.Select(t => $"{t.Key}-{t.Value}") ?? new List <string>()));

            // Service Bus
            builder.AddComponentMapping <ServiceBusNamespace>("Service Bus Namespace")
            .WithKey(sbn => sbn.Name)
            .WithField(sbn => sbn.EndpointUrl, "uri")
            .WithModelledHierarchyReference(sbn => sbn.Queues, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(sbn => sbn.Topics, ModelledReferenceDirection.Parent)
            .WithTags(Tags.FromExpression <ServiceBusNamespace>(
                          rg => rg.Tags?.Select(t => $"{t.Key}-{t.Value}") ?? new List <string>()));

            builder.AddComponentMapping <ServiceBusTopic>("Topic")
            .WithKey(t => t.Name);

            builder.AddComponentMapping <ServiceBusQueue>("Queue")
            .WithKey(q => q.Name);

            // Search
            builder.AddComponentMapping <SearchService>("Search Service")
            .WithKey(s => s.Name)
            .WithModelledHierarchyReference(s => s.Indexes, ModelledReferenceDirection.Parent)
            .WithTags(Tags.FromExpression <SearchService>(
                          rg => rg.Tags?.Select(t => $"{t.Key}-{t.Value}") ?? new List <string>()));

            builder.AddComponentMapping <SearchServiceIndex>("Search Service Index")
            .WithKey(s => s.Name);

            // Cosmos DB
            builder.AddComponentMapping <CosmosDBAccount>("Cosmos DB account")
            .WithKey(c => c.Name)
            .WithTags(Tags.FromExpression <CosmosDBAccount>(
                          rg => rg.Tags?.Select(t => $"{t.Key}-{t.Value}") ?? new List <string>()));

            // Redis
            builder.AddComponentMapping <RedisCache>("Redis Cache")
            .WithKey(r => r.Name)
            .WithTags(Tags.FromExpression <RedisCache>(
                          rg => rg.Tags?.Select(t => $"{t.Key}-{t.Value}") ?? new List <string>()));

            // Key Vault
            builder.AddComponentMapping <KeyVault>("Key vault")
            .WithKey(kv => kv.Name)
            .WithField(kv => kv.Uri, "uri")
            .WithTags(Tags.FromExpression <KeyVault>(
                          rg => rg.Tags?.Select(t => $"{t.Key}-{t.Value}") ?? new List <string>()));

            // HERIFRA!!
            // Access Management
            builder.AddComponentMapping <AccessManagement>("Access Management")
            .WithKey(am => am.Name)
            .WithModelledHierarchyReference(am => am.ActiveDirectoryGroups, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(am => am.ActiveDirectoryApplications, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(am => am.ActiveDirectoryUsers, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(am => am.RoleAssignments, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(am => am.RoleDefinitions, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(am => am.ServicePrincipals, ModelledReferenceDirection.Parent);

            builder.AddComponentMapping <ActiveDirectoryGroup>("Active Directory Group")
            .WithKey(adg => adg.Name);
            builder.AddComponentMapping <ActiveDirectoryApplication>("Active Directory Application")
            .WithKey(ada => ada.Name);
            builder.AddComponentMapping <ActiveDirectoryUser>("Active Directory User")
            .WithKey(adu => adu.Name);
            builder.AddComponentMapping <RoleAssignment>("Role Assignment")
            .WithKey(ra => ra.Name);
            builder.AddComponentMapping <RoleDefinition>("Role Definition")
            .WithKey(rd => rd.Name);
            builder.AddComponentMapping <ServicePrincipal>("Service Principal")
            .WithKey(sp => sp.Name);

            // AlertRule
            builder.AddComponentMapping <AlertRule>("Alert Rule")
            .WithKey(rd => rd.Name)
            .WithModelledHierarchyReference(rd => rd.MetricAlerts, ModelledReferenceDirection.Parent)
            .WithModelledHierarchyReference(rd => rd.ActivityLogAlerts, ModelledReferenceDirection.Parent);

            builder.AddComponentMapping <MetricAlert>("Metric Alert")
            .WithKey(ma => ma.Name);
            builder.AddComponentMapping <ActivityLogAlert>("Activity Log Alert")
            .WithKey(ala => ala.Name);

            // ApplicationGateway
            builder.AddComponentMapping <ApplicationGateway>("Application Gateway")
            .WithKey(ag => ag.Name);

            // AutoscaleSetting
            builder.AddComponentMapping <AutoscaleSetting>("Autoscale Setting")
            .WithKey(ass => ass.Name);

            // AvailabilitySet
            builder.AddComponentMapping <AvailabilitySet>("Availability Set")
            .WithKey(avs => avs.Name);

            // BatchAccount
            builder.AddComponentMapping <BatchAccount>("Batch Account")
            .WithKey(ba => ba.Name);

            // CdnProfile
            builder.AddComponentMapping <CdnProfile>("Cdn Profile")
            .WithKey(cp => cp.Name);

            // ComputeSku
            builder.AddComponentMapping <ComputeSku>("Compute Sku")
            .WithKey(cs => cs.Name);

            // Deployment
            builder.AddComponentMapping <Deployment>("Deployment")
            .WithKey(d => d.Name);

            // Disk
            builder.AddComponentMapping <Disk>("Disk")
            .WithKey(d => d.Name);

            // DnsZone
            builder.AddComponentMapping <DnsZone>("Dns Zone")
            .WithKey(dz => dz.Name);

            // LoadBalancer
            builder.AddComponentMapping <LoadBalancer>("Load Balancer")
            .WithKey(lb => lb.Name);

            // NetworkSecurityGroup
            builder.AddComponentMapping <NetworkSecurityGroup>("Network SecurityGroup")
            .WithKey(nsg => nsg.Name)
            .WithModelledHierarchyReference(nsg => nsg.NetworkInterfaces, ModelledReferenceDirection.Parent);

            builder.AddComponentMapping <NetworkInterface>("Network Interface")
            .WithKey(li => li.Name);

            // PublicIPAddress
            builder.AddComponentMapping <PublicIPAddress>("Public IP Address")
            .WithKey(pipa => pipa.Name);

            // Snapshot
            builder.AddComponentMapping <Snapshot>("Snapshot")
            .WithKey(ss => ss.Name);

            // TrafficManagerProfile
            builder.AddComponentMapping <TrafficManagerProfile>("Traffic Manager Profile")
            .WithKey(tmp => tmp.Name);

            // VirtualMachine
            builder.AddComponentMapping <VirtualMachine>("Virtual Machine")
            .WithKey(vm => vm.Name);

            // VirtualMachineCustomImage
            builder.AddComponentMapping <VirtualMachineCustomImage>("Virtual Machine Custom Image")
            .WithKey(vmci => vmci.Name);

            // VirtualMachineScaleSet
            builder.AddComponentMapping <VirtualMachineScaleSet>("Virtual Machine Scale Set")
            .WithKey(vmss => vmss.Name);

            // VirtualNetwork
            builder.AddComponentMapping <VirtualNetwork>("Virtual Network")
            .WithKey(vn => vn.Name);
        }