10.5: Building the Message Component in Angular

Now that we have the backend set up how we want it for the most part - let's start working on the interface in Angular.

Add a Message Interface

We'll start by adding a new interface to the SPA/src/app/models folder called Message.ts. This will be similar to our MessageToReturn DTO on the backend.

export interface Message {
    id: number;
    senderId: number;
    senderKnownAs: string;
    senderPhotoUrl: string;
    recipientId: number;
    recipientKnownAs: string;
    recipientPhotoUrl: string;
    content: string;
    isRead: boolean;
    dateRead: Date;
    dateSent: Date;
}

Add a Service Method

In user.service.ts - we'll add a new method called getMessages(). This will be similar to our getUsers() method.

getMessages(id: number, page?, itemsPerPage?, messageContainer?) {
    const paginatedResult: PaginatedResult<Message[]> = new PaginatedResult<Message[]>();
    let params = new HttpParams();

    params = params.append('MessageContainer', messageContainer);

    if (page != null && itemsPerPage != null) {
        params = params.append('pageNumber', page);
        params = params.append('pageSize', itemsPerPage);
    }

    return this._http.get<Message[]>(this.baseUrl + 'users/' + id + '/messages', { observe: 'response', params})
        .map(response => {
            paginatedResult.result = response.body;

            if (response.headers.get('Pagination') != null) {
                paginatedResult.pagination = JSON.parse(response.headers.get('Pagination'));
            }

            return paginatedResult;
        });
}

Add Message Resolver

In the resolvers folder, add a new class called message.resolver.ts. Again, this will be very similar to other resolvers we've written:

export class MessagesResolver implements Resolve<Message[]> {

    pageSize = 5;
    pageNumber = 1;
    messageContainer = 'Unread';

    constructor(
        private _userService: UserService,
        private _authService: AuthService,
        private _router: Router,
        private _alertify: AlertifyService) {}

    resolve(route: ActivatedRouteSnapshot): Observable<Message[]> {
        return this._userService.getMessages(this._authService.decodedToken.nameid,
            this.pageNumber, this.pageSize, this.messageContainer)
            .catch(error => {
            this._alertify.error('Problem retrieving data');
            this._router.navigate(['/home']);
            return Observable.of(null);
        });
    }
}

We, of course, need to add it to app.module.ts:

import { MessagesResolver } from './resolvers/message.resolver';

//  ...

providers: [
    //  ...
    MessagesResolver

Finally, we need to add the resolver to our routes.ts file:

{ path: 'messages', component: MessagesComponent, resolve: { messages: MessagesResolver} },

Update MessagesComponent

In our messages.component.ts file, we'll write it out very similarly to what we've done in other components.

export class MessagesComponent implements OnInit {
  messages: Message[];
  pagination: Pagination;
  messageContainer = 'Unread';

  constructor(
    private _userService: UserService,
    private _alertify: AlertifyService,
    private _route: ActivatedRoute,
    private _authService: AuthService
  ) { }

  ngOnInit() {
    this._route.data.subscribe(data => {
      this.messages = data['messages'].result;
      this.pagination = data['messages'].pagination;
    });
  }

  loadMessages() {
    this._userService
      .getMessages(this._authService.decodedToken.nameid, this.pagination.currentPage,
        this.pagination.itemsPerPage, this.messageContainer)
        .subscribe((res: PaginatedResult<Message[]>) => {
          this.messages = res.result;
          this.pagination = res.pagination;
        }, error => {
          this._alertify.error(error);
        });
  }

  pageChanged(event: any): void {
    this.pagination.currentPage = event.page;
    this.loadMessages();
  }

}

Verify Data is Loading

Even though our template is just the default messages works! - because of the resolver, we can still verify that the data is being loaded correctly.

Open up the app, login to one of the accounts with messages, and navigate to the Messages tab.

Open up your developer tools and the network tab. If you click on the 200 OK response from the messages endpoint and then click Preview - you should be able to see the correct data:

Setting up this component was very repetitive. But, if it's repetitive - it means you're getting the hang of it and would be able to implement similar functionality in your apps or extend this one without a problem!

Last updated