I have been through all of the posts about the Facebook deauthorization url and none of them address my issue. I an have ASP.Net Web Api 2 endpoint, but I cannot get the ping to come through correctly. Here is what my Route signature looks like:
[AllowAnonymous, Route("FacebookDeauthorize"), HttpPost]
public async Task<IHttpActionResult> FacebookDeauthorize(string signed_request)
{
//code for reading it
}
This results in a 404, so I tried changing the type to object and getting the type so i could figure out what it was coming through as. It threw a null reference exception when i tried access the object, so I think its just not coming through at all. Since this is Web API, I can't look to the request for a form to get the signed request from. Has anyone successfully gotten this to work with Web Api? Any help/pointers as to what the route signature should be?
For anyone else who finds this, here is the working endpoint for asp.net web api and the Facebook c# sdk, trick is to use a model and not a primitive:
public class FacebookDeauthModel
{
public string signed_request { get; set; }
}
[AllowAnonymous]
[Route("FacebookDeauthorize")]
[HttpPost]
public async Task<IHttpActionResult> FacebookDeauthorize(FacebookDeauthModel model)
{
FacebookClient fb = new FacebookClient();
dynamic signedRequest = JsonConvert.DeserializeObject(fb.ParseSignedRequest("YOUR_APP_SECRET", model.signed_request).ToString());
string FBUserID = signedRequest.user_id;
ApplicationUser user = UserManager.FindBy(x => x.FBAppID == FBUserID);
if (user != null)
{
user.IsActive = false;
user.InactiveReason = "Facebook deauthorized on " + DateTime.UtcNow;
await UserManager.UpdateAsync(user);
}
else
{
_tracer.Error(Request, "FacebookDeauthorize", "Facebook tried to deauthorize a user we do not have record of, FBAppID: {0}", FBUserID);
}
return Ok();
}
Related
I'm still learning ASP.NET, this middleware below is a authorized middleware, this will retrieve all the products in my database.
[Authorize]
// GET: api/ProductsApi
[HttpGet()]
public async Task<ActionResult<IEnumerable<Product>>> GetProduct()
{
return await _context.Product.Where(p => p.Favorite == false).ToListAsync();
}
This next middleware below is where i try calling the api middleware using it URL ("https://localhost:7009/api/ProductsApi")
and convert the returned data/products into a json and display the products in a razor view page.
public async Task<IActionResult> Index()
{
var client = _httpClientFactory.CreateClient();
var response = await client.GetAsync("https://localhost:7009/api/ProductsApi");
if (!response.IsSuccessStatusCode)
{
return RedirectToAction("Index", "Products");
}
var jsonData = await response.Content.ReadAsStringAsync();
List<Product> products = JsonConvert.DeserializeObject<List<Product>>(jsonData);
return View(products);
}
But i'm getting this error.
I did some debugging, the problem was, the api returns a login page but does not display it in my web browser, it instead gives me this error page.
Is there anyway to pass the current loggedin user's credentials inside the header or atleast display the login page so i can login instead of this error message?
I am working on ASP.NET Core 2.1 Web API project. I am trying to follow this article: https://www.c-sharpcorner.com/article/jwt-json-web-token-authentication-in-asp-net-core/ but I am stuck at Action. My model class just won't bind to the input.
[AllowAnonymous]
[HttpPost]
public IActionResult Login([FromBody] LoginVM loginVM)
{
IActionResult response = Unauthorized(); // cant reach this point, my breakpoint is here
var user = AuthenticateUser(new UserModel { });
if (user != null)
{
var tokenString = GenerateJSONWebToken(user);
response = Ok(new { token = tokenString });
}
return response;
}
public class LoginVM
{
public string Username { get; set; }
public string Password { get; set; }
}
You're posting as x-www-form-urlencoded, but you have the [FromBody] attribute applied to the action param. These two things are fundamentally incompatible. To accept x-www-form-urlencoded (or multipart/form-data) you must apply the [FromForm] attribute to the param. If you have [FromBody], as you do now, then you can only accept something like application/json or application/xml (if you also enable the XML serializers).
If the issue is that you want to be able to accept both application/json and x-www-form-urlencoded request bodies, that is not possible. You'll need a separate action for each request body encoding, though you can factor out the actual meat of the action into a private method on the controller that both actions can utilize.
Choose "raw" in Body and "Content-Type" as "application/json" in postman and then try.
I am beginning developer in asp.Net MVC5.
In my MVC project i use with web service that return me a string URL the URL is from another domain.
I want to move to the URL.
For clear myself:
The client fill form home page and press submit, in the server side i send a request web
service with parameters from the form and get URL with another domain and this URL i need to present as second page to the client
public class HomeController : Controller
{
public ActionResult Home()
{
return View("~/Views/Home/home.cshtml");
}
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult doSomething(Something obj)
{
//use web service and get string URL
string urlString = ;// get from the web service response.
return View();// want write in the ();
}
}
Also this is usefull for navigation in MVC.
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult doSomething(Something obj)
{
//use web service and get string URL
string urlString = ;// get from the web service response.
if (!string.IsNullOrEmpty(urlString))
{
//if the url is from within the domain.
return RedirectToAction(urlString);
//if the url is from other domain use this
//return Redirect(urlString);
}
//If the urlString is empty Return to a error page
return View("Error");
}
The url is from another site not the same domain
If you want to redirect to an external URL, you will need to use the Redirect() method.
Like so:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult DoSomething(Something obj)
{
// Use web service to get the string URL
string urlString = ...;
if (string.IsNullOrEmpty(urlString))
{
// If the urlString is empty, take the user to an Error View.
return View("Error");
}
// Redirect the user to the urlString
return Redirect(urlString);
}
I would recommend also doing some checking to ensure the URL is definitely valid. You can do this using the Uri static method, IsWellFormedUriString() - this returns a bool.
Like so:
if (!Uri.IsWellFormedUriString(urlString, UrlKind.Absolute))
{
// If the urlString is not a well-formed Uri, take the user to an Error View
return View("Error");
}
// Redirect the user to the urlString
return Redirect(urlString);
Alternatively, if you're redirecting to an internal Action, use the RedirectToAction() method, as #ankur suggested.
As an extra note: Ensure that your C# method names use PascalCase. Conserve camelCase for local variables/private fields.
So, you would use DoSomething(...), instead of doSomething(...) (I've done this in my example).
Hope this helps.
Using ASP.NET Core 2.0.0 Web API, I'm trying to build a controller to do a database insert. The information can be inserted into the database just fine, but returning a CreatedAtRoute throws an 'InvalidOperationException: No route matches the supplied values.' Everything I've found online so far says this was a bug with early pre-release versions of ASP.NET Core and has since been fixed, but I'm not really sure what to do about this. The following is my controller code:
[Produces("application/json")]
[Route("api/page")]
public class PageController : Controller
{
private IPageDataAccess _pageData; // data access layer
public PageController(IPageDataAccess pageData)
{
_pageData = pageData;
}
[HttpGet("{id}", Name = "GetPage")]
public async Task<IActionResult> Get(int id)
{
var result = await _pageData.GetPage(id); // data access call
if (result == null)
{
return NotFound();
}
return Ok(result);
}
[HttpPost]
public async Task<IActionResult> Create([FromBody] Page page)
{
if (page == null)
{
return BadRequest();
}
await _pageData.CreatePage(page); // data access call
// Return HTTP 201 response and add a Location header to response
// TODO - fix this, currently throws exception 'InvalidOperationException: No route matches the supplied values.'
return CreatedAtRoute("GetPage", new { PageId = page.PageId }, page);
}
Could anyone possibly shed some light on this for me?
The parameters need to match the route values of the intended action.
In this case you need id not PageId
return CreatedAtRoute(
actionName: "GetPage",
routeValues: new { id = page.PageId },
value: page);
i'm kinda new to programming c# and asp.net, i just want to build a rest api for my android app to sign in and sign up. but i face a problem for sign in (login).
the problem is i just wrote this codes below:
namespace CPanel.Controllers
{
public class DashboardController : Controller
{
// GET: Dashboard
public ActionResult CreateUser()
{
return View();
}
[HttpPost]
public ActionResult CreateUser(string username,string password)
{
CPanel.Models.CPanelEntities1 db = new Models.CPanelEntities1();
db.USP_AddUSer(username, password);
return View();
}
[HttpPost]
public ActionResult login(string username,string password)
{
CPanel.Models.CPanelEntities1 db = new Models.CPanelEntities1();
try
{
var user = db.USP_Authenticate(username, password).First();
return Json(new { UserId = user.UserId,Username=user.Username,IsAdmin=user.IsAdmin,Message="ok"});
}catch(Exception)
{
return Json(new { message = "error" });
}
}
}
}
the first part (CreateUser) work perfectly. but second part (login) only work on "Postman" chrome application.
i post a request on "Postman" -
localhost/dashboard/login?username=php&password=php
and i see a json:
{
"UserId": 29,
"Username": "php",
"IsAdmin": false,
"Message": "ok"
}
in localhost and wwwroot (iis) there in no chance and i face this error:
Server Error in '/' Application.
The resource cannot be found.
Description: HTTP 404. The resource you are looking for (or one of its
dependencies) could have been removed, had its name changed, or is
temporarily unavailable. Please review the following URL and make
sure that it is spelled correctly.
Requested URL: /dashboard/login
Version Information: Microsoft .NET Framework Version:4.0.30319;
ASP.NET Version:4.6.1586.0
When you enter the http://localhost/dashboard/login?username=php&password=php url to web browser it issues a GET request, however your controller only accepts POST requests.
There's another thing, as far as I understand you need a web api but your example is a standard ASP.NET MVC controller. You might want to take a look on the following tutorial: https://www.asp.net/web-api/overview/getting-started-with-aspnet-web-api/tutorial-your-first-web-api