I search in google and here but I got weird case.
I need to make an API, what get data from another service where I paste links to my API.
Links should be that:
1: https://myAPI/xxx/xxxx/optincallbackurl.php?email=$email$&key=sha1($email$security_parameter)
2: https://myAPI/xxx/xxxx/optincallbackurl.php?email=$email$&key=sha1($email$security_parameter)
Service in 2 options send me an email. How receive this data? Normal POST method API in c# should work for that callback?
I ask for advice how to make receiver from URI, I resolve my problem code below.
public class Kontakt
{
public string kEmail { get; set; }
}
public class optoutcallbackurlController : ApiController
{
public void Post([FromUri]string email)
{
Kontakt kontakt = new Kontakt();
kontakt.kEmail = email;
}
}
Now I got link like myAPI/conroler?email="email.test#gmail.com" and I receive email from URI to my API.
Related
I am trying to create a request in postman to upload files to a dotnet core endpoint that expects the following shape:
public class MyDto
{
public DateTime Time { get; set; }
public List<Logs> Files { get; set; } = null!;
public class Logs
{
public ServiceEnum Service { get; set; }
public List<IFormFile> LogFiles { get; set; }
}
}
Function signature of action:
[HttpPost("{id}/log")]
public async Task<ActionResult> SaveLogs([FromRoute] string id, [FromForm] MyDto myDto)
My postman request looks like this:
When I try debugging this I can see that myDto.Files[0].Service is set yet, myDto.Files[0].LogFiles in null.
I was expecting that uploading multiple files would be mapped into myDto.Files[0].LogFiles from the request. I might be formatting the keys in the request wrong but I have tried multiple different key formats at this point.
I test with other simple and complex types, they can use square brackets and post successfully(Except for IFormFile). Maybe it is by design in Postman. Any way, no matter what type it is. You can always post like xx.xx.xx.
Change your post data like below:
I'm trying to send a file from a postman to a web api, method on web api is expecting a list of type which contains doc type, file and folder name.. posted below:
Web api method:
[HttpPost("post-images")]
public async Task<IList<RepositoryItem>> PostAnImages (IList<PostRepoRequest> request)
{
// rest of the code
}
PostRepoRequest class:
public class PostRepoRequest
{
public FileType FileType { get; set; }
public IFormFile File { get; set; }
public string Folder { get; set; }
}
As it's possible to notice I've never received a file, its allways null,
I've tried also setting a header content-type as multipart/form-data but that didn't worked aswell..
What might be the trick here?
Thanks
Cheers
You need to change the request body with dot pattern like this:
Then you need to add [FromForm] attribute to the controller input parameter.
Also note that the variable names in the postman and controller must match.
[HttpPost("post-images")]
public async Task<IList<RepositoryItem>> PostAnImages ([FromForm]IList<PostRepoRequest> repositoryItems)
With these changes, you will be able to get the request correctly:
Try to send file as separated parameter
[HttpPost("post-images")]
public async Task<IList<RepositoryItem>> PostAnImages (IList<PostRepoRequest> request, [FromForm]List<IFormFile> files)
{
// rest of the code
}
and in client (assuming that can be Angular):
let input = new FormData();
for (var i = 0; i < this.filesToUpload.length; i++) {
input.append("files", this.filesToUpload[i]);
}
There is an invisible selectbox, just move your cursor to left and you'll see the selectable area. Then select it as a file.
And add [FromBody] at he beginnig of ypur method parameter like ([FromBody]IList<PostRepoRequest> request)
And last, update the Key to ...[0][file] (you've forgot [])
I need to know how to create API's dynamically by calling another API then passing [API name] and [API parameters], let's we assume that we have this API, like the one shown here:
[HttpPost("GenerateApi")]
[ProducesResponseType(200)]
[ProducesResponseType(500)]
public IActionResult GenerateApi(RootObject ro)
{
//Here I need piece of code to create API dynamically
return Ok(new { ro.apiName, ro.parameters });
}
Here are the models:
public class RootObject
{
public string apiName { get; set; }
public List<parameter> parameters { get; set; }
}
public class parameter
{
public string parameterName { get; set; }
public dynamic parameterType { get; set; }
}
Now what needs to be done, is to create dynamic API in controller.
So then we would have the API created they can be called from their URL like this
www.example.com/api/v1/[controller]/[apiName]/{[parameter1_value]}/{[parameter2_value]}
Can you please provide me some insight of this.
Found some thing can help in MVC. In case somebody else is looking for this, I need to overwrite the DefaultHttpControllerSelector. Here is a very nice article on the subject: link So basically for my use case mentioned above, I need to create a new AppDomain, start my service in it, and load my assemblies dynamically at runtime. I finally need to overwrite the DefaultHttpControllerSelector to catch the request. When the request arrive, it have then control on which controller I want to use. There I can update the controller dynamically by loading a new assembly, etc. Main thing to be careful on is that this is executed for each request so it could easily impact performance and memory. So I will implement my own caching of controller.
Okay so I'm trying to get data from Web API that I made in angular. Web API is working I tested it using Postman and Postman gets the data from Web API just fine here is the screenshot of Postman getting the data from Web API " http://prntscr.com/nr18ct ". That makes me certain that it is a problem with angular. And I'm sorry if I don't make sense or if the rest of the question / post is f**ed up first time asking a question here.
I did follow angular tutorial on Angular.io I really don't know what it could cause it, just to say it worked perfectly fine before I did the last part of the tutorial, that is trying to get data from Web API. My first thought was maybe I f**ed up something in PagedVehicleMake class in angular (typescript class) or VehicleMake class also in angular also typescript class
Web API part:
As you saw in the screen shot I sent before Web API sends that type of data.
public class PagedResult<T> : IPagedResult<T> where T : class
{
public int PageNumber { get; set; }
public int PageSize { get; set; }
public int TotalNumberOfPages { get; set; }
public IEnumerable<T> Results { get; set; }
}
and IEnumrable Results in this case is IEnumrable Results
and VehicleMakeVM is:
public class VehicleMakeVM
{
public int Id { get; set; }
public string Name { get; set; }
public string Abrv { get; set; }
}
Now for Angular part:
export class PagedVehicleMake{
Results : VehicleMake[];
TotalNumberOfPages : number;
PageSize : number;
PageNumber : number;
}
I tried to arrange PagedVehicleMake class the same way data is sent to Postman showed in a screenshot I sent. I thought maybe it had something to do with that.
export class VehicleMake {
Id : number;
Name : string;
Abrv : string;
}
and here is the VehicleMakeService class in angular:
export class VehicleMakeService {
constructor(private http: HttpClient, private messageService : MessageService) { }
private vehiclemakesUrl = "http://localhost:53282/api/VehicleMake"
/**GET vehiclemakes from the server */
getVehicleMakes() : Observable<PagedVehicleMake>{
this.messageService.add("VehicleMakeService : fetched VehicleMakes")
return this.http.get<PagedVehicleMake>(this.vehiclemakesUrl).pipe(
catchError(this.handleError<PagedVehicleMake>("getVehicleMakes", []))
);
}
/**
* Handle Http operation that failed.
* Let the app continue.
* #param operation - name of the operation that failed
* #param result - optional value to return as the observable result
*/
private handleError<T> (operation = 'operation', result?: T) {
return (error: any): Observable<T> => {
// TODO: send the error to remote logging infrastructure
console.error(error); // log to console instead
// TODO: better job of transforming error for user consumption
this.log(`${operation} failed: ${error.message}`);
// Let the app keep running by returning an empty result.
return of(result as T);
};
}
/** Log a VehicleMakeService message with the MessageService */
private log(message: string) {
this.messageService.add(`VehicleMakeService: ${message}`);
}
I expected it to just get the data from WebAPI but it somehow isn't capable of getting the data.
I figured out what was the problem. It was WebAPI actually I forgot to enable CORS, that's all.
I'm trying to setup Facebook Notification API.
I have an APi Controller with RealtimeUpdate() - Get, will be used just for verification of endpoint.
As is written in Fb Docs:
Firstly, Facebook servers will make a single HTTP GET to your callback
URL when you try to add or modify a subscription. A query string will
be appended to your callback URL with the following parameters:
hub.mode - The string "subscribe" is passed in this parameter
hub.challenge - A random string
hub.verify_token - The verify_token value you specified when you created the subscription
From here I have a problem - I have no idea how to handle this dots in query params names. I google a lot, and did not find the solution.
Can somebody please say to me how to get data from this hub.* values?
Thank you!
Update your method signature using the FromUri attributes, like this:
public string Get(
[FromUri(Name="hub.mode")]string mode,
[FromUri(Name="hub.challenge")]string challenge,
[FromUri(Name="hub.verify_token")]string verifyToken
)
{
/* method body */
}
The parameters will be bound from the query string using the specified names.
Slightly different form Steve's answer.
In case you need to have a normal controller instead of an Api one (if you are inheriting from Controller rather tha ApiController), the follow worked for me:
namespace Name
{
public class Hub
{
public string Mode { get; set; }
public string Challenge { get; set; }
// ReSharper disable once InconsistentNaming
public string Verify_Token { get; set; }
}
public class FacebookWebHooksController : Controller
{
[System.Web.Http.HttpGet, ActionName("Callback")]
[AllowAnonymous]
public ContentResult CallbackGet(Hub hub)
{
if (hub.Mode == "subscribe" && hub.Verify_Token == "YOUR_TOKEN")
return Content(hub.Challenge, "text/plain", Encoding.UTF8);
return Content(string.Empty, "text/plain", Encoding.UTF8);
}
}
[HttpPost]
[AllowAnonymous]
public ActionResult Callback()
{
Request.InputStream.Seek(0, SeekOrigin.Begin);
var jsonData = new StreamReader(Request.InputStream).ReadToEnd();
}
}
The Model Binder has some illegal characters, of which I believe '.' is a special character, used primarily to bind complex objects. When all else fails, you can look at Request.QueryString and Request.Form directly, just like in ASP.NET WebForms.
You can also try using a complex object that has a Property named hub with subproperties mode, challenge, and verify_token. This might just do the trick.