Skip to content

Commit 8f97572

Browse files
booking service updated to use auth tokens, readme updated
1 parent 6b866a9 commit 8f97572

File tree

4 files changed

+70
-29
lines changed

4 files changed

+70
-29
lines changed

README.md

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,16 @@ Code taken from course.
2323
* Burger side panel added with links to the discover places listings, your bookings and a logout button.
2424
* Bottom menu with 2 links to 'Discover' (default page upon loading) and 'Offers' that lists all the places available.
2525

26+
## [RxJS operators](http://reactivex.io/documentation/observable.html)
27+
28+
**switchMap** for http requests that emit just one value and for long-lived streams for Firebase real-time database and authentication. They do not need to be unsubscribed as they complete after emission. **switch:** because the result observable has switched from emitting the values of the first inner observable, to emitting the values of the newly created inner (derived) observable. The previous inner observable is cancelled and the new observable is subscribed. **map:** because what is being mapped is the emitted source value, that is getting mapped to an observable using the mapping function passed to switchMap. (The alternative operator is mergeMap).
29+
30+
**of** used with a single value for an 'emit once and complete' stream.
31+
32+
**take** tba
33+
34+
**tap** tba
35+
2636
## Screenshots
2737

2838
![page](./img/discover-places-page.png)

src/app/app.component.ts

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
11
import { Component, OnInit, OnDestroy } from '@angular/core';
22
import { Platform } from '@ionic/angular';
3-
import { Plugins, Capacitor } from '@capacitor/core';
3+
import { Plugins, Capacitor, AppState } from '@capacitor/core';
44

55
import { Router } from '@angular/router';
66

77
import { AuthService } from './auth/auth.service';
88
import { Subscription } from 'rxjs';
9+
import { take } from 'rxjs/operators';
910

1011

1112
@Component({
@@ -40,6 +41,7 @@ export class AppComponent implements OnInit, OnDestroy {
4041
}
4142
this.previousAuthState = isAuth;
4243
});
44+
Plugins.App.addListener('appStateChange', this.checkAuthOnResume.bind(this));
4345
}
4446

4547
onLogout() {
@@ -52,4 +54,17 @@ export class AppComponent implements OnInit, OnDestroy {
5254
}
5355
}
5456

57+
private checkAuthOnResume(state: AppState) {
58+
if (state.isActive) {
59+
this.authService
60+
.autoLogin()
61+
.pipe(take(1))
62+
.subscribe(success => {
63+
if (!success) {
64+
this.onLogout();
65+
}
66+
});
67+
}
68+
}
69+
5570
}

src/app/bookings/booking.service.ts

Lines changed: 42 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -41,16 +41,22 @@ export class BookingService {
4141
) {
4242
let generatedId: string;
4343
let newBooking: Booking;
44+
let fetchedUserId: string;
4445
return this.authService.userId.pipe(
4546
take(1),
4647
switchMap(userId => {
4748
if (!userId) {
4849
throw new Error('no user id found');
4950
}
51+
fetchedUserId = userId;
52+
return this.authService.token;
53+
}),
54+
take(1),
55+
switchMap(token => {
5056
newBooking = new Booking(
5157
Math.random().toString(),
5258
placeId,
53-
userId,
59+
fetchedUserId,
5460
placeTitle,
5561
placeImage,
5662
firstName,
@@ -61,49 +67,59 @@ export class BookingService {
6167
);
6268
return this.http
6369
.post<{ name: string }>(
64-
'https://ionic-angular-project-a9d42.firebaseio.com/bookings.json',
70+
`https://ionic-angular-project-a9d42.firebaseio.com/bookings.json?auth=${token}`,
6571
{ ...newBooking, id: null }
6672
);
67-
}),
68-
switchMap(resData => {
69-
generatedId = resData.name;
70-
return this.bookings;
71-
}),
72-
take(1),
73-
tap(bookings => {
74-
newBooking.id = generatedId;
75-
this._bookings.next(bookings.concat(newBooking));
76-
})
73+
}),
74+
switchMap(resData => {
75+
generatedId = resData.name;
76+
return this.bookings;
77+
}),
78+
take(1),
79+
tap(bookings => {
80+
newBooking.id = generatedId;
81+
this._bookings.next(bookings.concat(newBooking));
82+
})
7783
);
7884
}
7985

8086
cancelBooking(bookingId: string) {
81-
return this.http
82-
.delete(
83-
`https://ionic-angular-project-a9d42.firebaseio.com/bookings/${bookingId}.json`
84-
)
85-
.pipe(
86-
switchMap(() => {
87-
return this.bookings;
88-
}),
89-
take(1),
90-
tap(bookings => {
91-
this._bookings.next(bookings.filter(b => b.id !== bookingId));
92-
})
93-
);
87+
return this.authService.token.pipe(
88+
take(1),
89+
switchMap(token => {
90+
return this.http
91+
.delete(
92+
`https://ionic-angular-project-a9d42.firebaseio.com/bookings/${bookingId}.json?auth=${token}`
93+
);
94+
}),
95+
switchMap(() => {
96+
return this.bookings;
97+
}),
98+
take(1),
99+
tap(bookings => {
100+
this._bookings.next(bookings.filter(b => b.id !== bookingId));
101+
})
102+
);
94103
}
95104

96105
fetchBookings() {
106+
let fetchedUserId: string;
97107
return this.authService.userId.pipe(
98108
take(1),
99109
switchMap(userId => {
100110
if (!userId) {
101111
throw new Error('User not found');
102112
}
113+
fetchedUserId = userId;
114+
return this.authService.token;
115+
}),
116+
take(1),
117+
switchMap(token => {
103118
return this.http.get<{ [key: string]: BookingData }>(
104-
`https://ionic-angular-project-a9d42.firebaseio.com/bookings.json?orderBy="userId"&equalTo="${userId}"`
119+
`https://ionic-angular-project-a9d42.firebaseio.com/bookings.json?orderBy="userId"&equalTo="${fetchedUserId}"&auth=${token}`
105120
);
106121
}),
122+
107123
map(bookingData => {
108124
const bookings = [];
109125
for (const key in bookingData) {
Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
export const environment = {
22
production: true,
3-
googleMapsAPIKey: 'AIzaSyCUDGk4T7NVNxoksjRI4gRLTjMR78V_LeY',
4-
firebaseAPIKey: 'AIzaSyBhYIC4T8TR4IL4sroNYP3CcEP1GiKfrIs'
3+
googleMapsAPIKey: '',
4+
firebaseAPIKey: ''
55
};

0 commit comments

Comments
 (0)