After trudging around the net (and GitHub source and issues), I did find this SO post that describes essentially the same problem, and a "solution" for it (SHIFT+ENTER, which equates to "\r\n", in the Resx editor). This seems hackish and far less than ideal (I see it leading to inconsistent line terminations.)
However, while digging through the source to try and reproduce it or see if there was a known issue, I cloned the ms repo here.
git clone -b master https://github.com/aspnet/Localization.git
Master is important (dev wouldn't compile.) It does the upgrade for the project files (I am using VS2017, v15.2) without issue. Change "samples\LocalizationSample" to be the startup project.
I add a using System.Text
to the top of Startup.cs
and then by adding the following at original line 66...
const string HELLO = "Hello";
var name = "John Doe";
var sb = new StringBuilder($"{name}\n");
// Similiar to what I am currently using that is not working.
// However, tmplt gets the expected value here in this cloned repo!
// Yet, after the AppendFormat call below, it is back to escaped "\n" ("\\n")
var tmplt = SR[HELLO]; // A
// In my code that started this rabbit hole, tmplt gets the
// following via my injected _localizer/resx.
//var tmplt = "{0}:\\n Score: {1}\\n Pct: {2}\\n\\n"; // B
// Comment out above tmplt lines, and uncomment this and it works as expected
// This is the string that I have in my resx
//var tmplt = "{0}:\n Score: {1}\n Pct: {2}\n\n"; // C
string subj = "Subject";
int score = 100;
int? pct = 100;
sb.AppendFormat(
tmplt, // A = "\n"!, B = "\\n" (expected), C = "\n" (known good)
subj,
score,
pct.Value
);
// A = "\\n" :-(
// B = "\\n"
// C = "\n"
var msg = sb.ToString();
var just_a_place_to_set_a_breakpoint = true;
I then duplicate the Startup.es-ES.resx file as Startup.en-US.resx
, then change the value for the single key in my new resx to match my string shown in "C" above (// C
)
I can now set a breakpoint at just_a_place_to_set_a_breakpoint
and fire up the project.
It is able to correctly get the value out without the extra escape character before the newline from this project's localization data! I haven't figured out why that much works in this cloned/modified repo, but not in my original private repo.
However, once it gets to the ToString
call, it is back to the unwanted escaped newline ("\n") in both scenarios A and B! :-(
- How is it that the tmplt variable contains the correct representation in this hacked cloned repo when it pulls the localization string out, but not in mine?
- How is it that, regardless, by the time the StringBuilder.ToString is called, unless I supply a hardcoded string in the source directly, the "\n" characters ended up escaped ("\n") when it may not have been present in the string to be formatted?
Any help greatly appreciated, my eyeballs are about to fall out (and I fear this is something easy/documented and Google just failed to turn it up.)
UPDATE: I found the branch that I presume should match the version of the Microsoft.Extensions.Localization
my original project is using, v1.1.2... but it fails to build.