Angular State Management in RxJS Services
Published: 2020-03-05 22:10:21

---
title: Angular State Management in RxJS Services
published: true
date: 2020-03-03 07:00:00 UTC
tags: 
canonical_url: https://www.prestonlamb.com/blog/angular-state-management-in-rxjs-services
---

## [tldr;](#tldr)

Most Angular applications need some amount of state management. In some applications, a state management library like NgRX or Akita might make sense. But many times storing application state in RxJS services will work perfectly. We’ll go over how to do this using RxJS `BehaviorSubjects` and `Observables`.

## [BehaviorSubjects](#behavior-subjects)

Before jumping in to examples, let’s talk about `BehaviorSubjects`. `BehaviorSubjects` are a variant of RxJS `Subjects`. Components can subscribe to a `BehaviorSubject` and get updates when something changes. They do need to be primed with an initial value, but that value can be `null` if desired. There is one difference, though, between `Subjects` and `BehaviorSubjects`. If you subscribe to a `Subject`, you will only receive values that are emitted _after_ subscribing. But if you subscribe to a `BehaviorSubject`, you will get the last emitted value and all future emitted values. `Subjects` are great for many situations, but when managing state in an application I’ve found that `BehaviorSubjects` are better suited.

## [Managing State](#managing-state)

Okay, now that we are familiar with `BehaviorSubjects`, let’s look at an example of how to leverage those to manage state in an application.

I was recently working on an application that used information about the logged in person (a `Member`) throughout the app. The information didn’t update frequently, so I was able to get the information once and store it in a `BehaviorSubject` so that the app could store that information and give it out as needed. If it did update, I could push the new value into the `BehaviorSubject` and all subscribers were updated automatically. Here’s some skeleton code:

```ts
export class MyService {
	private memberBS: BehaviorSubject<Member> = new BehaviorSubject<Member>(null);
	public member$: Observable<Member> = this.memberBS.asObservable().pipe(filter(val => !!val));
}
```

The first line here in this service shows how I created the `BehaviorSubject`. I declared it as private, so it can’t be used outside the service, and I primed the `BehaviorSubject` with a `null` value. Because the `BehaviorSubject` is private, it is not actually accessible to any components that use this service. This is good though, because we don’t want every component to be able to update the `BehaviorSubject`. We want to control how new values are emitted, so making it private is a good start. So how do we access the value from the `BehaviorSubject`? That’s where the second line from above comes in to play. One of the methods of the `BehaviorSubject` is `asObservable`. It takes the `BehaviorSubject` and creates an observable. Components can then subscribe to that observable, and it will still get any new values that are emitted from the `BehaviorSubject`.

Here are a couple sample methods on the service for getting new data:

```ts
export class MyService {
	// Previous stuff

	getDataFromServer() {
		return this._http.get('...');
	}

	initializeObservable() {
		this.updateMemberObservableData().subscribe();
	}

	updateMemberObservableData() {
		return this.getDataFromServer().pipe(
			tap((data: Member) => {
				this.memberBs.next(data);
			}),
		);
	}
}
```

These are just a couple examples, but `getDataFromServer` is a stubbed out function for calling some server to get the data that you will need for the `Member`. `updateMemberObservableData()` gets the data from the server and then emits the data through the `BehaviorSubject`. `initializeObservable` just makes a call to and subscribes to the `updateMemberObservableData` method. This function could be called from anywhere really, but I’ve been calling it from the root `AppComponent` for my application. Then, as needed, I’ll call the `updateMemberObservableData()` from other components.

Once the `Member` data is in the service, it’s usable all throughout the application. When a new component comes on the screen that needs the `Member` data, it subscribes to the `member$` observable and is on its way. It’s also made the application feel much faster as well. There’s a little delay when waiting for the member data the first time, but from then on it’s really snappy and fast.

What I really like about this way of managing state is that every component that needs that information about the member can subscribe to the observable and get the data. You don’t have to make several calls to the database to get the same information. You also don’t have to pull in a large library to manage this little piece of state for your app.

## [Conclusion](#conclusion)

Storing application state in `BehaviorSubjects` and exposing those as observables through a service is a great way to manage state in an Angular application. RxJS is really powerful and the more I learn about it the more I’ve found how useful it is. This same pattern can be used for other server data (like order history, for example), but it can also be used for UI state management too. An example of that would be if a navigation menu is open or closed. This pattern works for any type of state management issue. Let me know if you’ve done something similar and how it worked for you!