diff --git a/CHANGELOG.md b/CHANGELOG.md index a7edaecb..26d9c5f7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,8 @@ ## Bug fixes: * Fix: Ambiguous steps reported wehn definition matches via more than one tag (#95) +* Fix incorrect binding language detection for Visual Studio extension (#104) + *Contributors of this release (in alphabetical order):* @clrudolphi # v2025.1.256 - 2025-03-07 diff --git a/Reqnroll.VisualStudio/Configuration/ReqnrollConfigDeserializer.cs b/Reqnroll.VisualStudio/Configuration/ReqnrollConfigDeserializer.cs index b18d4fc4..2f4c49a5 100644 --- a/Reqnroll.VisualStudio/Configuration/ReqnrollConfigDeserializer.cs +++ b/Reqnroll.VisualStudio/Configuration/ReqnrollConfigDeserializer.cs @@ -13,12 +13,12 @@ public void Populate(string jsonString, DeveroomConfiguration config) if (reqnrollJsonConfiguration.Language != null && reqnrollJsonConfiguration.Language.TryGetValue("feature", out var featureLanguage)) config.DefaultFeatureLanguage = featureLanguage; - if (reqnrollJsonConfiguration.Language != null && - reqnrollJsonConfiguration.Language.TryGetValue("binding", out var bindingCulture)) - config.DefaultFeatureLanguage = bindingCulture; if (reqnrollJsonConfiguration.BindingCulture != null && reqnrollJsonConfiguration.BindingCulture.TryGetValue("name", out var bindingCultureFromSpecFlow)) config.ConfiguredBindingCulture = bindingCultureFromSpecFlow; + if (reqnrollJsonConfiguration.Language != null && + reqnrollJsonConfiguration.Language.TryGetValue("binding", out var bindingCulture)) + config.ConfiguredBindingCulture = bindingCulture; if (reqnrollJsonConfiguration.Trace != null && reqnrollJsonConfiguration.Trace.TryGetValue("stepDefinitionSkeletonStyle", out var sdSnippetStyle)) { if (sdSnippetStyle == "CucumberExpressionAttribute") diff --git a/Tests/Reqnroll.VisualStudio.Tests/Configuration/ReqnrollConfigDeserializerTests.cs b/Tests/Reqnroll.VisualStudio.Tests/Configuration/ReqnrollConfigDeserializerTests.cs new file mode 100644 index 00000000..dcbb9880 --- /dev/null +++ b/Tests/Reqnroll.VisualStudio.Tests/Configuration/ReqnrollConfigDeserializerTests.cs @@ -0,0 +1,152 @@ +#nullable disable + +using FluentAssertions; +using Reqnroll.VisualStudio.Configuration; +using Xunit; + +namespace Reqnroll.VisualStudio.Tests.Configuration; + +public class ReqnrollConfigDeserializerTests +{ + [Fact] + public void Should_set_feature_language_from_reqnroll_json() + { + // Arrange + var deserializer = new ReqnrollConfigDeserializer(); + var config = new DeveroomConfiguration(); + var json = """ + { + "language": { + "feature": "hu-HU" + } + } + """; + + // Act + deserializer.Populate(json, config); + + // Assert + config.DefaultFeatureLanguage.Should().Be("hu-HU"); + config.ConfiguredBindingCulture.Should().BeNull(); + config.BindingCulture.Should().Be("hu-HU"); // Falls back to feature language + } + + [Fact] + public void Should_set_binding_culture_from_reqnroll_json() + { + // Arrange + var deserializer = new ReqnrollConfigDeserializer(); + var config = new DeveroomConfiguration(); + var json = """ + { + "language": { + "binding": "fr-FR" + } + } + """; + + // Act + deserializer.Populate(json, config); + + // Assert + config.DefaultFeatureLanguage.Should().Be("en-US"); // Should remain default + config.ConfiguredBindingCulture.Should().Be("fr-FR"); + config.BindingCulture.Should().Be("fr-FR"); + } + + [Fact] + public void Should_set_both_feature_and_binding_languages_from_reqnroll_json() + { + // Arrange + var deserializer = new ReqnrollConfigDeserializer(); + var config = new DeveroomConfiguration(); + var json = """ + { + "language": { + "feature": "en-US", + "binding": "fr-FR" + } + } + """; + + // Act + deserializer.Populate(json, config); + + // Assert + config.DefaultFeatureLanguage.Should().Be("en-US"); + config.ConfiguredBindingCulture.Should().Be("fr-FR"); + config.BindingCulture.Should().Be("fr-FR"); + } + + [Fact] + public void Should_keep_defaults_when_no_language_configuration() + { + // Arrange + var deserializer = new ReqnrollConfigDeserializer(); + var config = new DeveroomConfiguration(); + var json = """ + { + "trace": { + "stepDefinitionSkeletonStyle": "CucumberExpressionAttribute" + } + } + """; + + // Act + deserializer.Populate(json, config); + + // Assert + config.DefaultFeatureLanguage.Should().Be("en-US"); // Default + config.ConfiguredBindingCulture.Should().BeNull(); // Default + config.BindingCulture.Should().Be("en-US"); // Falls back to feature language + } + + [Fact] + public void Should_support_legacy_specflow_binding_culture_format() + { + // Arrange + var deserializer = new ReqnrollConfigDeserializer(); + var config = new DeveroomConfiguration(); + var json = """ + { + "bindingCulture": { + "name": "de-DE" + } + } + """; + + // Act + deserializer.Populate(json, config); + + // Assert + config.DefaultFeatureLanguage.Should().Be("en-US"); // Default + config.ConfiguredBindingCulture.Should().Be("de-DE"); + config.BindingCulture.Should().Be("de-DE"); + } + + [Fact] + public void Should_prioritize_language_binding_over_legacy_bindingCulture() + { + // Arrange + var deserializer = new ReqnrollConfigDeserializer(); + var config = new DeveroomConfiguration(); + var json = """ + { + "language": { + "binding": "fr-FR" + }, + "bindingCulture": { + "name": "de-DE" + } + } + """; + + // Act + deserializer.Populate(json, config); + + // Assert + config.DefaultFeatureLanguage.Should().Be("en-US"); // Default + config.ConfiguredBindingCulture.Should().Be("fr-FR"); // language.binding takes priority + config.BindingCulture.Should().Be("fr-FR"); + } +} \ No newline at end of file