I needed to write a quick POST
request in C# and decided to copy-paste a random piece of code from the internet. Everything worked fine however the syntax is so strange that I did not expect it to compile at all:
var request = new HttpRequestMessage
{
Method = HttpMethod.Post,
RequestUri = new Uri("https://www.random-api.com/api/random"),
Headers = {
{ "Accept-Encoding", "application/gzip" },
{ "Content-Type", "text/plain" },
},
Content = new FormUrlEncodedContent(new Dictionary<string, string>
{
{ "q", "Lorem ipsum" },
}),
};
The part that I don't understand is:
Headers = {
{ "Accept-Encoding", "application/gzip" },
{ "Content-Type", "text/plain" },
},
One of the things that bugs me is the fact that Headers is a readonly property that is being set outside the HttpRequestMessage
's constructor and the other thing is the value that is used - {{"key", "value"}}
much like a Dictionary<string,string>
that is instantiated with an initial value.
CodePudding user response:
This is called inline initialization of objects using an object initializer. It's possible because the HttpRequestMessage
class has a public no-arg constructor and the properties being set have public access modifiers.
You can read more about this technique over at Microsoft's documentation of this feature: https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/how-to-initialize-objects-by-using-an-object-initializer
Here's the documentation for the HttpRequestMessage
class: https://docs.microsoft.com/en-us/dotnet/api/system.net.http.httprequestmessage?view=net-6.0
CodePudding user response:
What you see there done with the Headers
property is called a "collection initializer". As per documentation:
var moreNumbers = new Dictionary<int, string>
{
{19, "nineteen" },
{23, "twenty-three" },
{42, "forty-two" }
};
This initializer example calls Add(TKey, TValue) to add the three items into the dictionary.
Thus, all that is required for this particular flavor of a collection initializer to work is that the object to be initialized offers an Add(TKey, TValue) method. (The authoritative and more detailed specification can be found in the C# language specification, §11.7.15.4 Collection initializers.)
With respect to your question, the Headers property is of type HttpRequestHeaders.
So, does HttpRequestHeaders have a Add(string, string) method required for this collection initializer to work? Yes, it does (declared by HttpRequestHeaders' base class HttpHeaders).