Currently, my Angular application consists of a significant number of submodules and components. Angular applications are quite sensitive to html rendering errors. For example, if we get a NULL object from an API and trying to get access to its property, it partially breaks rendering of the application.
It is quite difficult to handle and test such cases taking into account that the application is constantly growing. Do you know if it is possible to create a script that can log all error appearing in a console?
Here what I have got:
1) An http requests error handle to log broken requests from an API:
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);
};
}
2) Client-side logger but for whatever reason it only logs errors from crawlers :)
<script>
window.onerror = function(m,u,l,c) {
if (window.XMLHttpRequest) {
var xhr = new XMLHttpRequest();
var data = "msg="+encodeURIComponent(m)
+"&url="+encodeURIComponent(u)
+"&line="+l
+"&col="+c
+"&href="+encodeURIComponent(window.location.href);
xhr.open("GET", "logger.php?"+data, true);
xhr.setRequestHeader("Content-Type", "text/plain;charset=UTF-8");
xhr.send();
}
};
</script>
It would be very useful to get a script that can simply log all errors from console and
The simplest way to handle errors in Angular is to use Angular's HttpClient service along with RxJS operators throwError and catchError . Http request is made, and it returns the data with a response if anything wrong happens then it returns an error object with error status code.
One traditional way of handling errors in Angular is to provide an ErrorHandler class. This class can be extended to create your own global error handler. This is also a useful way to handle all errors that occur, but is mostly useful for tracking error logs.
console. log is a JavaScript function that logs messages to the developer's console or the browser console to the web page. This method helps Angular developers by informing them about the errors, warnings, and what is happening during the execution of their code.
Global Error Handling in Angular is handled by the Errorhandler class which is part of the @angular/core module. This is a global error handler class which catches all exceptions thrown by the application. In this approach, we create a class that will be implemented by the ErrorHandler class.
Logging in Angular Applications Programmers frequently use console.log to record errors or other informational messages in their Angular applications. Although this is fine while debugging your application, it's not a best practice for production applications.
You should see this: An error in an Angular application can either be a client-side error or server-side error: Client-side error: errors related to front-end code and the network — they throw 4xx status codes. Server-side error: errors related to back-end codes, database, and file system. They usually throw 5xx status codes.
Luckily, you can effectively log Angular errors by just integrating your application with Loupe Server. Loupe Server is a centralized logging platform with real-time log monitoring and a client-side logging agent designed explicitly for Angular applications. You can learn more about Loupe Server here, or try our free trial in the link below.
AngularJS has pretty good error handling and, within its context, will catch client-side errors and log them to the console allowing your application to continue. The problem, as outlined at the beginning of this article, is that the only person who knows the error occurred is the user sitting in front of the screen. So let’s fix this.
If you wish to catch and log all the errors (not only HTTP nature ones) in your Angular application I'd propose you the way that Sentry and other bug trackers use.
Angular has an ErrorHandler
class which provides a hook for centralized exception handling.
So your task would be to create your own error handler. I usually do it like this:
import {ErrorHandler, Injectable} from '@angular/core';
import {LoggerService} from './some/logger.service';
@Injectable()
export class CustomErrorHandlerService extends ErrorHandler {
constructor(private logger: LoggerService) {
super();
}
handleError(error) {
// Here you can provide whatever logging you want
this.logger.logError(error);
super.handleError(error);
}
}
The next step is to use your error handler by means of Dependency Injection. Just add it in your AppModule
like this:
import {CustomErrorHandlerService} from '~/app/_services/custom-error-handler.service';
@NgModule({
imports: [...],
declarations: [...],
providers: [
...
{provide: ErrorHandler, useClass: CustomErrorHandlerService},
],
bootstrap: [AppComponent]
})
That's it. The key feature of such implementation is that this service handles all possible errors, appearing in your application (just like you ask in your question) including HTTP errors and others.
Please, leave your comments if you have any additional questions.
When I started working with Angular, I found this article helpful: Angular: Adding Logging in Angular Applications.
If you follow the guidance, you end up with a LoggingService that you can configure to log errors to one of three (or all) locations:
What the article leaves out is how to catch the errors automatically. You can do this with an HttpInterceptor. Here's an example from an application I'm working on:
http-request-interceptor.ts
import { Injectable } from '@angular/core';
import { HttpEvent, HttpHandler, HttpRequest, HttpErrorResponse, HttpInterceptor } from '@angular/common/http';
import { Observable, throwError } from 'rxjs';
import { retry, catchError } from 'rxjs/operators';
import { Router } from '@angular/router';
import { LogService } from '../services/log.service';
@Injectable()
export class HttpRequestInterceptor implements HttpInterceptor {
constructor (private logService: LogService, private router: Router) { }
intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
const newReq = req.clone({
headers: req.headers.set('Content-Type', 'application/json'),
withCredentials: true
});
return next.handle(newReq)
.pipe(
retry(1),
catchError((error: HttpErrorResponse) => {
let displayError = '';
let serverError = '';
let clientError = '';
if (error.error instanceof ErrorEvent) {
// client-side error
clientError = `Error: ${error.error.message}`;
this.logService.error(clientError);
} else {
// server-side error
displayError = error.error;
serverError = `Error Code: ${error.status}\n${error.message}\n${error.error}`;
if (error.status === 401) {
this.logService.error(serverError);
this.router.navigate(['/unauthorized', { message: error.error}]);
}
if (error.status >= 500) {
this.logService.error(serverError);
this.router.navigate(['/error']);
}
}
return throwError(displayError);
})
);
}
}
HttpInterceptors are very powerful. This one does the following:
To register an HttpInterceptor in your application you need a module:
http-interceptor.module.ts
import { NgModule } from '@angular/core';
import { HTTP_INTERCEPTORS } from '@angular/common/http';
import { HttpRequestInterceptor } from './http-request-interceptor';
@NgModule({
providers: [
{ provide: HTTP_INTERCEPTORS,
useClass: HttpRequestInterceptor,
multi: true
}
]
})
export class HttpInterceptorModule { }
Then you register this module in your app.module.ts file and include it in the imports array.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With