Getting Configuration Strings For Http Client - c#

I have five different HttpPost methods. Each one gets a client from the same end point. For this reason, I am repeating the code where I get the section, uri and endpoint values for the configuration.
I thought of getting these values with a method to simplify the code. But I can't decide on the return type of the method. Is there a special return type for this case?
public ? GetReportConfig(string sectionName, string host, string endpoint)
{
var section = this._configuration.GetSection(sectionName);
string uriString = section.GetValue<string>(host);
string endpointString = section.GetValue<string>(endpoint);
}

Related

1. Forward slash in routing parameter

I have a GET end point which will take user name as parameter. Below is the action
[Route("user/{userName}")]
public User GetUserByName([FromUri] string userName)
{
// logic here
}
This is how i make the request.
var restClient = new RestClient("uri");
var request = new RestRequest("user/" + userName);
var response = restClient.Execute(request);
It worked fine for all cases till a user with name containing forward slash came.
Eg: Akbar/Badhusha
Then the request will looks like user/Akbar/Badhusha
This causing the request to return Not Fount error
I tried to add the parameter with AddQueryParameter method. All returning Not found error.
I also tried HttpUtility.UrlEncode
Also tried replacing / with %2f
Also tried user?userName=Akbar/Badhusha
All of them failed.
Is there any way to make it work?
Try removing [FromUri] from the parameter as shown below,
[Route("user")]
public User GetUserByName(string userName)
{
// logic here
}
And the request may look like,
user?userName=Akbar/Badhush

Getting size of request in IActionFilter OnActionExecuting()

Project setup: Asp .NET core 2.1, Web Api on Docker environment.
I want to get size of the GET requests with query parameters on our API for logging purpose.
I have an action filter implementing IActionFilter in the project. OnActionExecuting() is the method where I interpret the request for the purpose.
But I am always getting null in context.HttpContext.Request.ContentLength property. Also, read the body by stream reader in a text variable which is is also empty.
Is this a valid place to check this or else am I referring to different property of the ActionExecutingContext ?
public void OnActionExecuting(ActionExecutingContext context)
{
string requestSize = "";
//Try 1:
requestSize = Convert.ToString(context.HttpContext.Request.ContentLength);
//Try 2:
//Since the Try 1 is null, following doesn't really matter. But still tried.
using (var bodyReader = new StreamReader(context.HttpContext.Request.Body))
{
var bodyAsText = bodyReader.ReadToEnd();
if (string.IsNullOrWhiteSpace(bodyAsText) == false)
{
requestSize = bodyAsText.Length;
}
}
// Console.WriteLine(requestSize );
}
Expecting some bytes number for the request size, but getting null.
Is this a valid place to check this
NO
GET requests do not have a BODY.
ContentLength being null and empty body stream are expected behavior for GET requests.
If you want access to query strings then you need to check the request and extract the query string
context.HttpContext.Request.QueryString

ASP.NET Web Api - multiple params 500 error

' trying to make an web api controller with two parameters: one model object and string.
public string AddDevice(Device device, [FromBody] string userName)
{
// Some operations here
}
When I try it with one parameter on fiddler:
For Device object (body request):
{
"DeviceName":"name,
"StolenFlag":false
}
For string "[FromBody] string userName" (body request):
"userName"
It works fine. I just do not know how to make this method works with those two parameters. When I try connecting request body on fiddler like that:
{
"DeviceName":"name,
"StolenFlag":false
}
"userName"
I get an 500 error. It means, that server finds correct controller method but can't handle request. Any ideas?
First add the following line to WebApiConfig.cs in your App_Start folder.
GlobalConfiguration.Configuration.IncludeErrorDetailPolicy = IncludeErrorDetailPolicy.Always;
It goes inside this function:
public static void Register(HttpConfiguration config)
Build your API and read the full error message from the Response. This should tell you exactly what's happening.
Since you can have only one parameter in the Request body you can change the method to accept username in the URI.
public string AddDevice([FromBody] Device device, string userName)
{
// Some operations here
return "";
}

C# Uri with username as "domainname\username"

I have a string like
<Scheme>:\\<domain>\<domainuser>:<EncryptedPassword>#servername\
I want to be able to create Uniform resource identifier (URI) and easy access the parts of the URI. For most part using C# Uri class works great. But I get invalid URI exceptions when user is provided as "domainname\domainuser".
How best to handle this in C#.
You must PercentEncode(/EscapeDataString) such strings.
Like in question above username "xyz_domain\abc_user" must be encoded to "xyz_domain%5Cabc_user" to before creating URI object.
Later after extracting you can do PercentDecode(/UnescapeDataString) of the string using UnescapeDataString method from Uri Class.You can use UnescapeDataString Method from C# Uri Class
Here is the code
public static string GetUsername(this Uri uri)
{
if (uri == null || string.IsNullOrWhiteSpace(uri.UserInfo))
return string.Empty;
var items = uri.UserInfo.Split(new[] { ':' });
//Replace precent encoding in the username.
var result = Uri.UnescapeDataString(items[0]);
return result.Length > 0 ? result : string.Empty;
}
Similar scheme can be applied to any part of the uri string. Just remember to UnescapeDataString the EscapeDataStrings.

WCF UriTemplate with large query strings

I'm working with a rather large query string(~30+ parameters) and am trying to pass them to a WCF service I've setup.
I've run into a few issues specifically with the UriTemplate field. This service is setup to access a third party Api, so the query string may or may not contain all parameters. I'm curious if the best approach is to build a query string and pass that to the WCF service or to pass each parameter(and in some cases String.Empty) individually.
I've currently tried to dynamically build up a query string, however have hit a wall with either a 403 error when I try to pass the entire string( "?prm1=val&prm2=val" ) into the uritemplate of "ApiTool.jsp{query}", or I hit an invalid uritemplate response due to the fact I don't have name/value pairs listed.
I am pretty sure you'll need to list the parameters individually. Otherwise, UriTemplate will end up escaping things for you:
var ut = new UriTemplate("Api.jsp{query}");
var u = ut.BindByName(new Uri("http://localhost"), new Dictionary<string, string>() { { "query", "?param1=a&param2=b" } });
Console.WriteLine(u); // http://localhost/Api.jsp%3Fparam1=a&param2=b
You can 'unescape' querystring with IClientMessageInspector.
public class UriInspector: IClientMessageInspector
{
public object BeforeSendRequest(ref Message request, IClientChannel channel)
{
// change/replace request.Headers.To Uri object;
return null;
}
}
See MSDN how to add this to your Endpoint object.

Categories

Resources