using System.Xml; using FluentAssertions; using Nop.Core.Domain.Attributes; using Nop.Core.Domain.Catalog; using Nop.Core.Domain.Common; using Nop.Core.Domain.Customers; using Nop.Core.Domain.Orders; using Nop.Core.Domain.Vendors; using Nop.Services.Attributes; using NUnit.Framework; namespace Nop.Tests.Nop.Services.Tests.Common; [TestFixture] public class AttributeParserTests : BaseNopTest { private string _attributesXml; private XmlDocument _xmlDoc; protected dynamic _parser; private IAttributeService _customerAttributeService; private IAttributeService _vendorAttributeService; private IAttributeService _addressAttributeService; private IAttributeService _checkoutAttributeService; private List _customerAttributeIds = new(); private List _customerAttributeValuesIds = new(); private List _vendorAttributeIds = new(); private List _vendorAttributeValuesIds = new(); private List _addressAttributeIds = new(); private List _addressAttributeValuesIds = new(); private List _checkoutAttributeIds = new(); private List _checkoutAttributeValuesIds = new(); protected void PrepareTestData(Type attributeType) { _attributesXml = $"<{attributeType.Name} ID=\"1\"><{attributeType.Name}Value>1<{attributeType.Name} ID=\"2\"><{attributeType.Name}Value>2"; if (attributeType == typeof(CustomerAttribute)) _parser = GetService>(); if (attributeType == typeof(VendorAttribute)) _parser = GetService>(); if (attributeType == typeof(AddressAttribute)) _parser = GetService>(); if (attributeType == typeof(CheckoutAttribute)) _parser = GetService>(); } [OneTimeSetUp] public async Task SetUp() { _xmlDoc = new XmlDocument(); _customerAttributeService = GetService>(); _vendorAttributeService = GetService>(); _addressAttributeService = GetService>(); _checkoutAttributeService = GetService>(); for (var i = 0; i < 2; i++) { BaseAttribute attribute = new CustomerAttribute { AttributeControlType = AttributeControlType.DropdownList, Name = "test" }; await _customerAttributeService.InsertAttributeAsync((CustomerAttribute)attribute); _customerAttributeIds.Add(attribute.Id); BaseAttributeValue attributeValue = new CustomerAttributeValue { AttributeId = attribute.Id, Name = "test" }; await _customerAttributeService.InsertAttributeValueAsync((CustomerAttributeValue)attributeValue); _customerAttributeValuesIds.Add(attributeValue.Id); attributeValue = new CustomerAttributeValue { AttributeId = attribute.Id, Name = "test" }; await _customerAttributeService.InsertAttributeValueAsync((CustomerAttributeValue)attributeValue); _customerAttributeValuesIds.Add(attributeValue.Id); attribute = new CustomerAttribute { AttributeControlType = AttributeControlType.DropdownList, Name = "test", IsRequired = true }; await _customerAttributeService.InsertAttributeAsync((CustomerAttribute)attribute); _customerAttributeIds.Add(attribute.Id); attribute = new VendorAttribute { AttributeControlType = AttributeControlType.DropdownList, Name = "test" }; await _vendorAttributeService.InsertAttributeAsync((VendorAttribute)attribute); _vendorAttributeIds.Add(attribute.Id); attributeValue = new VendorAttributeValue { AttributeId = attribute.Id, Name = "test" }; await _vendorAttributeService.InsertAttributeValueAsync((VendorAttributeValue)attributeValue); _vendorAttributeValuesIds.Add(attributeValue.Id); attributeValue = new VendorAttributeValue { AttributeId = attribute.Id, Name = "test" }; await _vendorAttributeService.InsertAttributeValueAsync((VendorAttributeValue)attributeValue); _vendorAttributeValuesIds.Add(attributeValue.Id); attribute = new VendorAttribute { AttributeControlType = AttributeControlType.DropdownList, Name = "test", IsRequired = true }; await _vendorAttributeService.InsertAttributeAsync((VendorAttribute)attribute); _vendorAttributeIds.Add(attribute.Id); attribute = new AddressAttribute { AttributeControlType = AttributeControlType.DropdownList, Name = "test" }; await _addressAttributeService.InsertAttributeAsync((AddressAttribute)attribute); _addressAttributeIds.Add(attribute.Id); attributeValue = new AddressAttributeValue { AttributeId = attribute.Id, Name = "test" }; await _addressAttributeService.InsertAttributeValueAsync((AddressAttributeValue)attributeValue); _addressAttributeValuesIds.Add(attributeValue.Id); attributeValue = new AddressAttributeValue { AttributeId = attribute.Id, Name = "test" }; await _addressAttributeService.InsertAttributeValueAsync((AddressAttributeValue)attributeValue); _addressAttributeValuesIds.Add(attributeValue.Id); attribute = new AddressAttribute { AttributeControlType = AttributeControlType.DropdownList, Name = "test", IsRequired = true }; await _addressAttributeService.InsertAttributeAsync((AddressAttribute)attribute); _addressAttributeIds.Add(attribute.Id); attribute = new CheckoutAttribute { AttributeControlType = AttributeControlType.DropdownList, Name = "test" }; await _checkoutAttributeService.InsertAttributeAsync((CheckoutAttribute)attribute); _checkoutAttributeIds.Add(attribute.Id); attributeValue = new CheckoutAttributeValue { AttributeId = attribute.Id, Name = "test" }; await _checkoutAttributeService.InsertAttributeValueAsync((CheckoutAttributeValue)attributeValue); _checkoutAttributeValuesIds.Add(attributeValue.Id); attributeValue = new CheckoutAttributeValue { AttributeId = attribute.Id, Name = "test" }; await _checkoutAttributeService.InsertAttributeValueAsync((CheckoutAttributeValue)attributeValue); _checkoutAttributeValuesIds.Add(attributeValue.Id); attribute = new CheckoutAttribute { AttributeControlType = AttributeControlType.DropdownList, Name = "test", IsRequired = true }; await _checkoutAttributeService.InsertAttributeAsync((CheckoutAttribute)attribute); _checkoutAttributeIds.Add(attribute.Id); } } [OneTimeTearDown] public async Task TearDown() { foreach (var id in _customerAttributeValuesIds) await _customerAttributeService.DeleteAttributeValueAsync(new CustomerAttributeValue { Id = id }); foreach (var id in _vendorAttributeValuesIds) await _vendorAttributeService.DeleteAttributeValueAsync(new VendorAttributeValue { Id = id }); foreach (var id in _addressAttributeValuesIds) await _addressAttributeService.DeleteAttributeValueAsync(new AddressAttributeValue { Id = id }); foreach (var id in _checkoutAttributeValuesIds) await _checkoutAttributeService.DeleteAttributeValueAsync(new CheckoutAttributeValue { Id = id }); foreach (var id in _customerAttributeIds) await _customerAttributeService.DeleteAttributeAsync(new CustomerAttribute { Id = id }); foreach (var id in _vendorAttributeIds) await _vendorAttributeService.DeleteAttributeAsync(new VendorAttribute { Id = id }); foreach (var id in _addressAttributeIds) await _addressAttributeService.DeleteAttributeAsync(new AddressAttribute { Id = id }); foreach (var id in _checkoutAttributeIds) await _checkoutAttributeService.DeleteAttributeAsync(new CheckoutAttribute { Id = id }); } [Test] [TestCase(typeof(CustomerAttribute))] [TestCase(typeof(VendorAttribute))] [TestCase(typeof(AddressAttribute))] [TestCase(typeof(CheckoutAttribute))] public void CanRemoveAttribute(Type attributeType) { PrepareTestData(attributeType); var xml = _parser.RemoveAttribute(_attributesXml, 1) as string; _xmlDoc.LoadXml(xml); var childNodes = _xmlDoc.SelectNodes($@"//Attributes/{attributeType.Name}"); childNodes?.Count.Should().Be(1); } [Test] [TestCase(typeof(CustomerAttribute))] [TestCase(typeof(VendorAttribute))] [TestCase(typeof(AddressAttribute))] [TestCase(typeof(CheckoutAttribute))] public async Task CanAddAttribute(Type attributeType) { PrepareTestData(attributeType); var attribute = (await _parser.ParseAttributesAsync(_attributesXml))[1]; (attribute as BaseAttribute).Should().NotBeNull(); var values = await _parser.ParseAttributeValuesAsync(_attributesXml); ((int)values.Count).Should().Be(2); var xml = _parser.AddAttribute(_attributesXml, attribute, "3") as string; values = await _parser.ParseAttributeValuesAsync(xml); ((int)values.Count).Should().Be(3); } [Test] [TestCase(typeof(CustomerAttribute))] [TestCase(typeof(VendorAttribute))] [TestCase(typeof(AddressAttribute))] [TestCase(typeof(CheckoutAttribute))] public void RemoveAttributeShouldReturnEmptyStringWhenAllChildrenIsRemoved(Type attributeType) { PrepareTestData(attributeType); var xml = _parser.RemoveAttribute(_attributesXml, 1) as string; xml = _parser.RemoveAttribute(xml, 2); xml.Should().BeEmpty(); } [Test] [TestCase(typeof(CustomerAttribute))] [TestCase(typeof(VendorAttribute))] [TestCase(typeof(AddressAttribute))] [TestCase(typeof(CheckoutAttribute))] public void RemoveAttributeShouldNotChangeXmlIfAttributeValueIdNotExists(Type attributeType) { PrepareTestData(attributeType); var xml = _parser.RemoveAttribute(_attributesXml, 3) as string; xml?.Equals(_attributesXml).Should().BeTrue(); } [Test] [TestCase(typeof(CustomerAttribute))] [TestCase(typeof(VendorAttribute))] [TestCase(typeof(AddressAttribute))] [TestCase(typeof(CheckoutAttribute))] public void CanParseAttributeIds(Type attributeType) { PrepareTestData(attributeType); var ids = _parser.ParseAttributeIds(_attributesXml) as IList; var existsId = new List { 1, 2 }; ids?.Count.Should().Be(2); ids?.All(existsId.Contains).Should().BeTrue(); } [Test] [TestCase(typeof(CustomerAttribute))] [TestCase(typeof(VendorAttribute))] [TestCase(typeof(AddressAttribute))] [TestCase(typeof(CheckoutAttribute))] public void CanParseAttributeIdsShouldReturnEmptyListIfXmlIsEmpty(Type attributeType) { PrepareTestData(attributeType); var ids = _parser.ParseAttributeIds(string.Empty) as IList; ids?.Count.Should().Be(0); } [Test] [TestCase(typeof(CustomerAttribute))] [TestCase(typeof(VendorAttribute))] [TestCase(typeof(AddressAttribute))] [TestCase(typeof(CheckoutAttribute))] public void CanParseAttributeIdsShouldReturnEmptyListIfXmlNotContainsRightAttributes(Type attributeType) { PrepareTestData(attributeType); var ids = _parser.ParseAttributeIds("Test 1Test 2") as IList; ids?.Count.Should().Be(0); ids = _parser.ParseAttributeIds("Test 1Test 2") as IList; ids?.Count.Should().Be(0); } [Test] [TestCase(typeof(CustomerAttribute))] [TestCase(typeof(VendorAttribute))] [TestCase(typeof(AddressAttribute))] [TestCase(typeof(CheckoutAttribute))] public void CanParseAttributeValues(Type attributeType) { PrepareTestData(attributeType); var values = _parser.ParseAttributeValuesAsync(_attributesXml).Result?.Count as int?; values.Should().Be(2); } [Test] [TestCase(typeof(CustomerAttribute))] [TestCase(typeof(VendorAttribute))] [TestCase(typeof(AddressAttribute))] [TestCase(typeof(CheckoutAttribute))] public async Task GetAttributeWarnings(Type attributeType) { PrepareTestData(attributeType); var attribute = (await _parser.ParseAttributesAsync(_attributesXml))[1]; (attribute as BaseAttribute).Should().NotBeNull(); var values = await _parser.GetAttributeWarningsAsync(_attributesXml); ((int)values.Count).Should().BeGreaterOrEqualTo(1); } }