Code4IT

The place for .NET enthusiasts, Azure lovers, and backend developers

C# Tip: How to temporarily change the CurrentCulture

2022-03-08 2 min read CSharp Tips
Just a second! 🫷
If you are here, it means that you are a software developer. So, you know that storage, networking, and domain management have a cost .

If you want to support this blog, please ensure that you have disabled the adblocker for this site. I configured Google AdSense to show as few ADS as possible - I don't want to bother you with lots of ads, but I still need to add some to pay for the resources for my site.

Thank you for your understanding.
- Davide

It may happen, even just for testing some functionalities, that you want to change the Culture of the thread your application is running on.

The current Culture is defined in this global property: Thread.CurrentThread.CurrentCulture. How can we temporarily change it?

An idea is to create a class that implements the IDisposable interface to create a section, delimited by a using block, with the new Culture:

public class TemporaryThreadCulture : IDisposable
{
	CultureInfo _oldCulture;

	public TemporaryThreadCulture(CultureInfo newCulture)
	{
		_oldCulture = CultureInfo.CurrentCulture;
		Thread.CurrentThread.CurrentCulture = newCulture;
	}

	public void Dispose()
	{
		Thread.CurrentThread.CurrentCulture = _oldCulture;
	}
}

In the constructor, we store the current Culture in a private field. Then, when we call the Dispose method (which is implicitly called when closing the using block), we use that value to restore the original Culture.

How to use it

How can we try it? An example is by checking the currency symbol.

Thread.CurrentThread.CurrentCulture = new CultureInfo("ja-jp");

Console.WriteLine(Thread.CurrentThread.CurrentCulture.NumberFormat.CurrencySymbol); //¥

using (new TemporaryThreadCulture(new CultureInfo("it-it")))
{
	Console.WriteLine(Thread.CurrentThread.CurrentCulture.NumberFormat.CurrencySymbol);//€
}

Console.WriteLine(Thread.CurrentThread.CurrentCulture.NumberFormat.CurrencySymbol); //¥

We start by setting the Culture of the current thread to Japanese so that the Currency symbol is ¥. Then, we temporarily move to the Italian culture, and we print the Euro symbol. Finally, when we move outside the using block, we get back to ¥.

Here’s a test that demonstrates the usage:

[Fact]
void TestChangeOfCurrency()
{
	using (new TemporaryThreadCulture(new CultureInfo("it-it")))
	{
		var euro = CultureInfo.CurrentCulture.NumberFormat.CurrencySymbol;
		Assert.Equal(euro, "€");

		using (new TemporaryThreadCulture(new CultureInfo("en-us")))
		{
			var dollar = CultureInfo.CurrentCulture.NumberFormat.CurrencySymbol;

			Assert.NotEqual(euro, dollar);
		}
		Assert.Equal(euro, "€");
	}
}

This article first appeared on Code4IT

Conclusion

Using a class that implements IDisposable is a good way to create a temporary environment with different characteristics than the main environment.

I use this approach a lot when I want to experiment with different cultures to understand how the code behaves when I’m not using English (or, more generically, Western) culture.

Do you have any other approaches for reaching the same goal? If so, feel free to share them in the comments section!

Happy coding!

🐧

About the author

Davide Bellone is a Principal Backend Developer with more than 10 years of professional experience with Microsoft platforms and frameworks.

He loves learning new things and sharing these learnings with others: that’s why he writes on this blog and is involved as speaker at tech conferences.

He's a Microsoft MVP 🏆, conference speaker (here's his Sessionize Profile) and content creator on LinkedIn.