WEBVTT

00:00.020 --> 00:05.600
Okay, now it's time to set up stripe on our client side of things and what we're going to use for this.

00:05.630 --> 00:11.720
If I just search for React and Stripe in Google, then we'll go to the react stripe reference.

00:11.750 --> 00:18.320
Stripe provides react components that we can use to help us configure our checkout, and it does come

00:18.320 --> 00:21.440
with some really quite excellent functionality.

00:21.440 --> 00:29.390
And the setup for this is really just to install the stripe react stripe js and stripe stripe js packages.

00:29.390 --> 00:32.480
And what this gives us is stripe elements.

00:32.480 --> 00:37.100
And stripe elements consist of lots of different components that we can utilize.

00:37.100 --> 00:41.660
And I'll just scroll down in here to take a look at the available element components.

00:41.660 --> 00:43.280
Some of them we will be using.

00:43.280 --> 00:51.140
We'll be using the address element, which allows us to collect address details for 236 regional formats.

00:51.410 --> 00:59.240
So depending on the country that the user selects, then it's going to format the address fields relevant

00:59.240 --> 01:04.540
for that particular country and that takes away a massive burden as a developer.

01:04.540 --> 01:10.030
Typically in a demonstration, I would just demonstrate US formatted addresses and not worry about any

01:10.030 --> 01:10.540
others.

01:10.540 --> 01:15.460
But if we use this address element, then this covers that for us.

01:15.460 --> 01:24.370
What this also gives us, if combined with the payment element that we'll also use is Google autocomplete

01:24.370 --> 01:26.170
for addresses as well.

01:26.170 --> 01:28.090
And that is very useful.

01:28.090 --> 01:35.590
So we'll be using the payment element which is here allows us to collect payment details for 25 plus

01:35.590 --> 01:38.410
different payment methods from around the globe.

01:38.410 --> 01:41.380
And we'll be utilizing those two components from here.

01:41.380 --> 01:44.110
We're not going to be using the other ones themselves.

01:44.170 --> 01:48.610
The card element that comes along with the payment element that we'll be using.

01:48.610 --> 01:55.930
And because of the autocomplete functionality, then we get the most functionality for the least amount

01:55.930 --> 01:56.380
of work.

01:56.380 --> 02:01.700
If we use the address element and the payment element inside here.

02:01.760 --> 02:09.530
Now one downside to using this and I'll just copy the npm install into my clipboard since I've got the

02:09.530 --> 02:12.740
docs open and copy this.

02:12.740 --> 02:19.520
But one downside, and what you might want to do is just right click, inspect your console, and just

02:19.520 --> 02:27.710
savor the moment of having a nice, clean, no warning console because this is going to be the last

02:27.710 --> 02:32.060
time we see it like this on this training course, thanks to stripe JavaScript.

02:32.090 --> 02:38.090
Now the JavaScript that stripe provides is very functional and it's secure.

02:38.180 --> 02:38.750
They've made it.

02:38.780 --> 02:44.240
They've added security elements inside here to prevent fraud and all of that good stuff that you would

02:44.240 --> 02:46.220
expect from a payment provider.

02:46.250 --> 02:51.770
However, what it also comes along with is warnings out of our control.

02:51.770 --> 02:54.080
So we'll see this as we encounter them.

02:54.080 --> 03:03.670
But I just want you to to take a look and gaze at a nice, clean, unblemished Console and say goodbye

03:03.670 --> 03:08.680
to it, because what's coming up now is really out of our control, and it's not going to be quite as

03:08.680 --> 03:10.150
clean in the future.

03:10.150 --> 03:17.290
So back to VSCode and let's open up our terminal and we'll go to the third tab, and we're going to

03:17.320 --> 03:23.050
install the stripe JavaScript and the react stripe stuff.

03:23.050 --> 03:23.740
We don't need that.

03:23.740 --> 03:28.540
Save doesn't do any harm, so I'm not going to worry about removing it and press return.

03:28.540 --> 03:31.570
I don't know if we're going to get the legacy peer dependencies here.

03:31.570 --> 03:32.440
We may do.

03:32.440 --> 03:36.220
And if that is the case, we'll just need to add on the normal switch.

03:36.250 --> 03:37.600
And of course we do.

03:37.600 --> 03:39.160
So I'm going to add on.

03:39.190 --> 03:44.290
In fact let's just clear this window so I don't add this code at the bottom of the screen.

03:44.290 --> 03:46.120
And I'll just repeat that command.

03:46.120 --> 03:54.730
But I will add on the legacy dash peer dash deps switch and press return and get this added.

03:54.730 --> 03:57.130
And now it is added.

03:57.130 --> 04:01.350
So we need to give our client stripe our publishable Key.

04:01.380 --> 04:03.510
That's the one that we can share with the client.

04:03.510 --> 04:09.960
And it's probably about time that we started looking at configuration in our react application.

04:09.960 --> 04:11.940
We haven't done so yet.

04:12.300 --> 04:20.490
And if we go back to the File explorer inside the client folder, then we can provide a dot env file

04:20.490 --> 04:26.550
where we can store key value pairs and environment variables and pass them to our client app.

04:26.580 --> 04:30.480
So at the root of this folder it has to be in a very specific place.

04:30.480 --> 04:32.070
We do not have this right now.

04:32.070 --> 04:39.090
Just right click client say new file and just call it dot env and press return.

04:39.090 --> 04:42.480
And notice it's automatically dimmed out.

04:42.480 --> 04:45.750
So this is automatically excluded from the.

04:45.750 --> 04:47.250
Gitignore file.

04:47.280 --> 04:53.220
Probably doesn't have to be but it is because we can't really store any actual secure secrets inside

04:53.220 --> 04:58.530
our client code because it's always going to be downloaded by the browser anyway.

04:58.530 --> 05:05.150
And anything we put inside here is going to be visible inside that JavaScript.

05:05.150 --> 05:07.670
So we don't put anything secret inside here.

05:07.670 --> 05:14.870
So just because it's excluded from git doesn't mean that we can put secret information in here and we

05:14.870 --> 05:15.980
are not going to.

05:16.010 --> 05:18.470
So we're going to add two things inside here.

05:18.470 --> 05:20.210
We're going to have a white underscore.

05:20.210 --> 05:24.080
And by the way because we're using beats I call it white.

05:24.080 --> 05:31.130
Then because we're using beats that means that if we want these to be passed to our client application

05:31.130 --> 05:34.490
we have to start with white underscore.

05:34.520 --> 05:35.930
That's compulsory.

05:35.990 --> 05:40.670
And then we can use I'll use API underscore URL as the first one.

05:40.670 --> 05:41.750
We say equals.

05:41.750 --> 05:52.550
And then we can use https colon forward slash forward slash localhost colon 5001 forward slash API and

05:52.550 --> 05:54.530
then forward slash.

05:55.520 --> 06:01.170
Please don't forget that forward slash or do we need that forward slash I'm just going to check the

06:01.170 --> 06:06.810
base API and see what we used inside here, because this is what we're going to use to replace it with.

06:06.900 --> 06:09.780
And inside here we do not have a forward slash.

06:09.780 --> 06:12.870
It basically needs to be the same as this without quotes.

06:12.870 --> 06:19.860
So just to be safe because I know this is working, I'll go back to the env file and I will replace

06:19.860 --> 06:22.410
what I have with what I've got in my clipboard.

06:22.410 --> 06:31.410
And the next thing we'll add is the white underscore stripe underscore PK for a publishable key.

06:31.620 --> 06:36.540
And we're going to set this equal to of course our stripe publishable key.

06:36.540 --> 06:39.450
So I'll go back to stripe go back to the home.

06:39.450 --> 06:43.260
And this is where we can get our publishable key from.

06:43.260 --> 06:46.170
So I'll copy that into my clipboard and paste it inside.

06:46.170 --> 06:52.110
Here we do not need quotes surrounding these key value pairs.

06:53.640 --> 07:01.250
So let's first of all test that this one works by using it inside our base API and make sure we still

07:01.250 --> 07:03.110
have the same functionality.

07:03.560 --> 07:09.470
So I'll go to the base API and instead of the hard coded value, then we can change this.

07:09.470 --> 07:19.370
And to use one of the environment variables inside Veet we use import dot meta dot env dot.

07:19.370 --> 07:24.380
And then we can use Veet underscore API underscore URL.

07:24.680 --> 07:31.580
And if I go back to the browser and I go back to the store page and I go back to the catalog, then

07:31.580 --> 07:35.360
what we should find is we're still making our request to the API.

07:35.390 --> 07:39.470
So it is getting that value from the environment.

07:39.500 --> 07:43.010
So let's go back and use the other one that we've added inside there.

07:43.010 --> 07:45.350
And we're going to go to our checkout page.

07:45.350 --> 07:53.810
And just above the checkout page component we'll use const stripe promise equals.

07:53.810 --> 07:58.910
And then we can use the load stripe function from stripe js.

07:59.030 --> 08:02.200
And inside here this takes our publishable key.

08:02.200 --> 08:05.290
So we can use import meta dot env.

08:05.590 --> 08:10.930
And then we can use our vite underscore stripe underscore pk.

08:11.140 --> 08:14.530
And this is going to load stripe into our application.

08:14.530 --> 08:20.380
And if we hover over this then this returns a promise which we're storing inside this variable.

08:20.380 --> 08:28.570
And with just that single line of code, if we go back to our application and we inspect and we go to

08:28.600 --> 08:36.850
our console, uh, Chrome is moving towards a new experience that allows users to choose to browse without

08:36.880 --> 08:38.890
third party cookies.

08:38.890 --> 08:42.040
And this is coming from stripe.

08:42.490 --> 08:44.260
We cannot fix this.

08:44.260 --> 08:47.110
This is Stripe's job to fix these warnings.

08:47.110 --> 08:51.190
There are a lot of them and I really don't like this.

08:51.190 --> 08:56.740
I can't express enough how much I do not like having warnings in the console.

08:56.740 --> 09:02.760
And I'll show you a way that we can filter these out, but there's not really much we can do about this.

09:02.850 --> 09:13.170
One day stripe will fix this, but that day is not today, so they don't cause our application any harm.

09:13.170 --> 09:19.050
It doesn't break any part of our application and they are just warnings, but they are noisy warnings

09:19.050 --> 09:20.730
and there are lots of them.

09:20.730 --> 09:25.770
So just something to live with until stripe eventually get around to fixing that.

09:25.800 --> 09:33.180
Now what we're going to use with this, we're going to wrap our checkout stepper inside an element's

09:33.990 --> 09:37.740
components we get from stripe.

09:37.740 --> 09:40.200
So we're going to surround it with this.

09:40.200 --> 09:42.240
And we'll add its closing tag.

09:42.240 --> 09:46.800
And we'll put the checkout stepper inside the elements there.

09:46.830 --> 09:51.930
Now the elements component this takes the stripe promise.

09:51.930 --> 09:53.220
So we specify stripe.

09:53.220 --> 09:56.310
And then we pass in our stripe promise.

09:56.520 --> 09:59.520
But what it also takes is some options.

09:59.520 --> 10:03.040
And we need to create the options, one of the options it needs.

10:03.040 --> 10:07.660
It needs the client secret that we have inside our basket.

10:07.660 --> 10:14.140
So we're going to use inside our checkout page here we're going to use our Usefetch basket query.

10:14.140 --> 10:20.830
So I'll specify data and give it a name of basket equals use fetch basket query.

10:21.280 --> 10:25.270
And then we can create some options that we can pass to our stripe elements.

10:25.270 --> 10:27.190
So I'll say const options.

10:27.430 --> 10:30.880
And we'll give this a type of stripe elements.

10:34.660 --> 10:36.220
Options.

10:38.920 --> 10:43.480
And stripe does come with excellent TypeScript support by the way as well.

10:43.480 --> 10:48.880
Everything that we use from stripe will have a type available and pretty straightforward to use.

10:48.880 --> 10:51.670
So we're going to use this in a very specific way.

10:51.670 --> 10:54.520
And we're going to use a hook that we haven't used yet.

10:54.520 --> 11:01.800
So our stripe elements options because we don't know if we've got the client secret at this point,

11:01.830 --> 11:04.200
our basket could have declined secret.

11:04.200 --> 11:05.400
It could not have it.

11:05.400 --> 11:10.800
So we'll make this possibly undefined as an alternative type.

11:10.800 --> 11:12.750
So we'll use a union type for that.

11:12.750 --> 11:16.170
And we're going to use something called a usememo.

11:17.310 --> 11:21.270
Now technically speaking what react have got coming up.

11:21.300 --> 11:26.730
This probably will not be required in future versions of react, because react have introduced something

11:26.730 --> 11:30.420
that's still in beta at the moment called a react compiler.

11:31.650 --> 11:39.840
But what this ensures when we use Usememo is if our check out page Rerenders for whatever reason, then

11:39.840 --> 11:46.650
if we store the results of what we're doing here inside Usememo, then this is Memoized.

11:46.980 --> 11:55.230
So only if one of the dependencies we supply to this Usememo will list options possibly be recreated.

11:55.830 --> 12:02.270
So it's just a way of ensuring that something doesn't change when something is rerendered And potentially

12:02.270 --> 12:03.680
this could change.

12:03.680 --> 12:07.250
So we use a use memo here which takes a callback function.

12:07.250 --> 12:09.530
So I'll add the callback inside here.

12:09.560 --> 12:10.640
Add curly brackets.

12:10.640 --> 12:13.640
And this takes some dependencies.

12:14.660 --> 12:23.510
And inside the callback function we're going to check to see if we do not have the basket and the client

12:23.510 --> 12:24.170
secrets.

12:24.170 --> 12:27.710
And we need to go back to our basket to add those properties as well.

12:27.710 --> 12:30.320
So let's go back to our baskets.

12:30.320 --> 12:35.600
And we're going to add to our baskets in the basket type.

12:35.600 --> 12:39.650
We're going to have the client secret make it optional which is going to be a string.

12:39.650 --> 12:44.000
And we'll have our payment intent ID again optional.

12:44.000 --> 12:45.950
And that's going to be a string as well.

12:45.950 --> 12:51.230
So back in our checkout page we're going to check for the presence of the client secrets.

12:51.260 --> 12:54.950
If we do not have it then we're going to return undefined.

12:54.950 --> 12:58.760
And that's the reason the options could be undefined.

12:58.790 --> 13:01.130
If we do have it we're going to return.

13:03.290 --> 13:12.080
And we'll put this inside an object and we'll specify the client secrets, colon baskets, client secrets.

13:12.110 --> 13:19.430
And our dependency for this usememo function is the baskets dot client secrets.

13:19.430 --> 13:24.710
So we need to check to see if we have the options before we can pass them to the elements.

13:24.710 --> 13:27.170
So just inside the grid we'll do a couple of checks.

13:27.200 --> 13:34.520
Actually we'll use not stripe promise because we need to check to see if we have the stripe promise

13:34.520 --> 13:37.250
or not options.

13:37.460 --> 13:43.160
And if we're missing either of those, we cannot load our checkout effectively because we have to have

13:43.160 --> 13:46.160
the client secret to load the stripe elements.

13:46.160 --> 13:48.350
So I'll specify a ternary here.

13:48.350 --> 13:51.470
So I'll add a question mark, open parentheses.

13:51.470 --> 13:55.400
And if we do not have either of those then we'll use typography.

13:57.290 --> 14:00.950
And we'll give it a variant of eight six.

14:00.980 --> 14:05.810
And we'll just say loading checkouts dot dot dot.

14:05.840 --> 14:09.200
And to the right of the parentheses we'll add a colon.

14:09.230 --> 14:16.820
Open more parentheses and we'll put our elements inside here.

14:19.490 --> 14:22.910
And we'll pass as well as the stripe promise to the elements.

14:22.910 --> 14:24.350
We need to pass through the options.

14:24.350 --> 14:27.980
And we'll pass it to the options we have just created.

14:28.010 --> 14:32.690
So what I'd expect to see at this point is we're going to be stuck loading the checkout, because we

14:32.690 --> 14:37.640
do not have the client secret for our basket yet, because we haven't set up that functionality.

14:37.640 --> 14:41.960
So if I go back to the browser, let's just refresh this page.

14:41.960 --> 14:48.170
And if I click on the basket and then I click on the checkout, then we're going to be stuck in the

14:48.170 --> 14:53.900
loading checkout because we're not able to get the client secret from our basket at this point.

14:53.900 --> 14:55.400
And we'll deal with that next.

14:55.400 --> 15:01.970
And we'll create a checkout API so that we can call our payments intent endpoint on the API.
