Unable to catch CosmosException when token expired in Blazor WebAssembly - azure

I am using Azure CosmosDB with Blazor WebAssembly (client-side).
I want to catch CosmosException When connection token expires, But not getting cosmos exception for that, (Null exception found)
I have also tried same code in console application, In that I am able to catch cosmos exception that showing token expired.
Code sample :
using (CosmosClient client = new CosmosClient(account, token))
{
Database db = null;
db = client.GetDatabase("databaseName");
Container orgContainer = client.GetContainer("databaseName","containerName");
try
{
ItemResponse<CosmosException> response = await orgContainer.ReadItemAsync<CosmosException>("test", new PartitionKey("test"));
var data = response.Resource;
}
catch(CosmosException ex)
{
}
catch(Exception ex)
{
}
}
Exception Details of Console Application

This is probably because the exception occurs outside the try block. Also, make sure you do not instantiate a new cosmos client on each request. This does not perform well. Use singleton and keep alive between requests.

Related

How can I catch exception from backend server using IMobileServiceSyncTable - InsertAsync?

I'm using IMobileServiceSyncTable from Azure Mobile App. In InsertAsync operation, on the backend server side, I had some validations for the data and, if that validations failure, I want throw Exception from the server side. I tried return InternalServerError(), throw HttpResponseException, but never worked on the client side. I debbuged the Post method in server side, the server throws the exception or return InternalServerError, but in the mobile client, don't occurs error.
Can anyone help me?
Here is my code on the client side:
public async Task<bool> AddPaciente(Paciente novoPaciente)
{
//other things
try
{
await _pacienteTable.InsertAsync(novoPaciente);
}
catch (Exception e)
{
Debug.WriteLine(e.Message);
Debug.WriteLine(e.StackTrace);
throw new WebException(AppResources.MensagemFalhaConexaoServidorAzure);
}
await SyncPaciente();
return true;
}
Here is my post method on the backend server side
// POST tables/Paciente
public async Task<IHttpActionResult> PostPaciente(Paciente novoPaciente)
{
//other things
if (paciente != null)
{
var responseMessage = new HttpResponseMessage(HttpStatusCode.BadRequest)
{
Content = new StringContent("Já existe um paciente com esse token cadastrado.")
};
//throw new HttpResponseException(responseMessage);
return InternalServerError(new Exception("Já existe um paciente com esse token cadastrado."));
}
}
You should listen to the response status code.
var response = await _pacienteTable.InsertAsync(novoPaciente);
if (response.IsSuccessStatusCode) {
var content = await response.Content.ReadAsStringAsync ();
}
else
{
//Here handle the error code
throw new WebException(AppResources.MensagemFalhaConexaoServidorAzure);
}
I'm using IMobileServiceSyncTable from Azure Mobile App. In InsertAsync operation, on the backend server side, I had some validations for the data and, if that validations failure, I want throw Exception from the server side.
For IMobileServiceSyncTable, you are dealing with An Offline Client which means that IMobileServiceSyncTable<T>.InsertAsync would directly insert data into the local SQLite store on your mobile client-side. Until you manually call MobileServiceClient.SyncContext.PushAsync(), then your local data store would be pushed to your mobile backend. For this approach, I would recommend you make sure that you need to validate the inputs before you saving them into the local data store, otherwise your push operations would fail, then you need to force your client user to adjust the existing inputs even after it has been successfully added before.
If you use An Online Client as follows, then both your approaches for throwing the exception would be immediately returned to your client.
var mobileClient= new MobileServiceClient("https://{your-mobile-app-name}.azurewebsites.net");
var _pacienteTable= mobileClient.GetTable<Paciente>();
await _pacienteTable.InsertAsync(novoPaciente);
Moreover, I used the following code line for catching the exception:
try
{
await table.InsertAsync(item);
}
catch (MobileServiceInvalidOperationException ex)
{
//TODO:
//await ex.Response.Content.ReadAsStringAsync(); //get detailed response content
}
catch (Exception e)
{
//TODO: other uncaught exception
}
Also, for the similar issue, you could leverage Fiddler to capture the network traces to narrow down this issue, make sure your client-side could correctly receive the relevant response.

Azure App Service Error 405 - The request could not be completed. (Method Not Allowed)

I'm working with Azure App Service .NET backend with a Xamarin.iOS app. I am able to successfully register a new user and I can see the user's details in the database. I have a custom ApiController, which handles the registration and the I'm able to save the details with a successful POST call.
However, when I try to log into the app, I get the following error:
{Microsoft.WindowsAzure.MobileServices.MobileServiceInvalidOperationException: The request could not be completed. (Method Not Allowed)
Below is my code:
The RegistrationController in the backend which successfully makes a POST call
[MobileAppController]
[RoutePrefix("api/register")]
[AllowAnonymous]
public class RegisterController : ApiController
{
[HttpPost]
[Route("newuser")]
public HttpResponseMessage NewUser(RegistrationRequest request)
{
// Registration code in here
}
}
This is how I call this function on the client side:
public async Task<Result<UserProfile>> RegisterUser(RegistrationWrapper registrationrequest)
{
try
{
var registrationRequest = new JObject();
registrationRequest.Add("username", registrationrequest.username);
registrationRequest.Add("password", registrationrequest.password);
registrationRequest.Add("email", registrationrequest.email);
registrationRequest.Add("phone", registrationrequest.phone);
registrationRequest.Add("firstname", registrationrequest.firstname);
registrationRequest.Add("lastname", registrationrequest.lastname);
var result = await client.InvokeApiAsync("register/newuser", registrationRequest);
// Handle result here
}
catch (Exception ex)
{
return Result<UserProfile>.Failure(ex.Message + ex.StackTrace + ex.InnerException);
}
}
Custom AuthController which handles the login
This POST call fails with the error described above.
[MobileAppController]
[RoutePrefix("api/auth")]
public class AuthController : ApiController
{
public HttpResponseMessage Post(AuthenticationRequest credentials)
{
try
{
//Authentication code goes here
catch (Exception e)
{
Console.WriteLine("Ërror :" + e.Message);
Console.WriteLine(e.StackTrace);
return Request.CreateResponse(HttpStatusCode.InternalServerError, new
{
Stacktrace = e.StackTrace,
ErrorMessage = e.Message,
Credentials = credentials
});
}
}
How I invoke this function from the client side
async Task<Result<Account>> Login(string username, string password)
{
try
{
var credentials = new JObject();
credentials.Add("username", username);
credentials.Add("password", password);
var result = await client.InvokeApiAsync("auth", credentials);
//Handle result here
}
catch (Exception ex)
{
return Result<Account>.Failure(ex, ex.Message + ex.StackTrace);
}
}
}
I'm not sure why it's failing during the log in. Any ideas?
After trying tons of solutions found here on StackOverflow, the one that finally worked for me was this first answer found on a similar question.
It seems that the http POST call is redirected to https.
After enabling authentication on your App Service in the Azure portal, you need to change the url to https.
So I changed mine from this:
http//{my_site}.azurewebsites.net
To this:
https//{my_site}.azurewebsites.net
On the client side, and now used this new one to create my local sync tables.
Everything works as expected now.
The HTTP status code 405 is returned when an API endpoint is called with a wrong (Not Allowed) HTTP method. For example, if instead of a POST request the endpoint is called with a GET request.

MobileServiceInvalidOperationException is thrown on Xamarin.WindowsPhone 8.1 project

I'm trying to use Azure Mobile Services and Xamarin. I follow all instuctions of official tutorial, created Azure backend for application and downloaded sample quick-start app for Xamarin.Forms from Azure.
There is code in TodoItemManager.cs:
public async Task<ObservableCollection<TodoItem>> GetTodoItemsAsync(bool syncItems = false)
{
try
{
IEnumerable<TodoItem> items = await todoTable
.Where(todoItem => !todoItem.Done)
.ToEnumerableAsync();
return new ObservableCollection<TodoItem>(items);
}
catch (MobileServiceInvalidOperationException msioe)
{
Debug.WriteLine(#"Invalid sync operation: {0}", msioe.Message);
}
catch (Exception e)
{
Debug.WriteLine(#"Sync error: {0}", e.Message);
}
return null;
}
And I got MobileServiceInvalidOperationException with message "Invalid sync operation: The request could not be completed. (Not Found)".
I have tested Azure Backend on UWP App and it works fine. So looks like there is problem in WP8.1 project. Can anybody help with this exception?
So.. I forgot to enable internet connection on my Windows Phone

403 Forbidden error, while access the ClientRepresentation in keycloack

We use keycloak API in our application. When we try to retrieve the Client list of the realm it pass 403 forbidden error. Highly appreciate your comments for avoid this matter.
String authServer = UriUtils.getOrigin(httpRequest.getRequestURL().toString()) + AUTH_CONTEXT_PATH;
String token = httpRequest.getHeader("Authorization").replaceAll("Bearer ", "");
String realmClientsUrl = authServer+"/admin/realms/testrealm/clients/"+getClientRepresentationId(authServer,realm,token);
ClientRequest request = getClientRequest(realmClientsUrl,token);
ClientResponse<String> response;
ClientRepresentation clientRepresentation = null;
try{
response = request.get(String.class);
validateResponse(response,"CLIENT_REPRESENTATION");
clientRepresentation = response.getEntity(ClientRepresentation.class);
return clientRepresentation;
} catch (Exception e) {
e.printStackTrace();
}
Error which passed,
java.lang.Exception: ErrorStage:CLIENT_REPRESENTATION_ID,HTTP responseCode:403,StatusIno=Forbidden
You might get this error if the logged in user doesn't have the relevant Client Roles access. Add the client role access as "View Client" under realm-management.

ServiceStack/Funq not disposing RavenDB document session after request is complete

In trying to integrate RavenDB usage with Service Stack, I ran across the following solution proposed for session management:
A: using RavenDB with ServiceStack
The proposal to use the line below to dispose of the DocumentSession object once the request is complete was an attractive one.
container.Register(c => c.Resolve<IDocumentStore>().OpenSession()).ReusedWithin(ReuseScope.Request);
From what I understand of the Funq logic, I'm registering a new DocumentSession object with the IoC container that will be resolved for IDocumentSession and will only exist for the duration of the request. That seemed like a very clean approach.
However, I have since run into the following max session requests exception from RavenDB:
The maximum number of requests (30) allowed for this session has been
reached. Raven limits the number of remote calls that a session is
allowed to make as an early warning system. Sessions are expected to
be short lived, and Raven provides facilities like Load(string[] keys)
to load multiple documents at once and batch saves.
Now, unless I'm missing something, I shouldn't be hitting a request cap on a single session if each session only exists for the duration of a single request. To get around this problem, I tried the following, quite ill-advised solution to no avail:
var session = container.Resolve<IDocumentStore>().OpenSession();
session.Advanced.MaxNumberOfRequestsPerSession = 50000;
container.Register(p => session).ReusedWithin(ReuseScope.Request);
Here is a sample of how I'm using the resolved DocumentSession instance:
private readonly IDocumentSession _session;
public UsersService(IDocumentSession session)
{
_session = session;
}
public ServiceResponse<UserProfile> Get(GetUser request)
{
var response = new ServiceResponse<UserProfile> {Successful = true};
try
{
var user = _session.Load<UserProfile>(request.UserId);
if (user == null || user.Deleted || !user.IsActive || !user.IsActive)
{
throw HttpError.NotFound("User {0} was not found.".Fmt(request.UserId));
}
response.Data = user;
}
catch (Exception ex)
{
_logger.Error(ex.Message, ex);
response.StackTrace = ex.StackTrace;
response.Errors.Add(ex.Message);
response.Successful = false;
}
return response;
}
As far as I can see, I'm implementing SS + RavenDB "by the book" as far as the integration point goes, but I'm still getting this max session request exception and I don't understand how. I also cannot reliably replicate the exception or the conditions under which it is being thrown, which is very unsettling.

Resources