So we have emails going out properly, but of course, the biggest problem with the email is the link
we have that is supposed to allow people to reset their password is just a link to a university, and
that's not helpful.
So we want to be able to send a link to the front end that will show a form that allows people to choose
a new password.
And of course, we want that to be absolutely secure.
In other words, we don't want to make that open to just anyone.
Now, obviously, we can have people log in to change the password because they don't know what the
password is.
So what we need is some means of securing that to make sure that the only people who have access to
the link are people who should have access to the link.
Now, there's a number of ways of doing this.
One really common method is to append a unique token to the email or to give them a token.
They have to enter into a form or something like that.
And of course, you look up that token in the database and verify that it's valid and so on and so forth.
And that seems like a lot of work.
What I'm going to suggest we do instead is to use signed emails, emails which have an actual hash or
some kind of code in the euro itself that will ensure that you are simply can't be changed.
And we'll also make sure that an email expires after a set length of time.
So let's get started doing that.
What I'm going to do is take you to a package, one that I've been using for years, and it works really,
really well.
And it's called right here, B.W. Marengo alone.
And as you might be able to tell from the actual picture here in the name of it, it's dangerous to
go alone.
Clearly, this is written by someone who really enjoys games that involve characters named Link and
Zelda.
Setting that aside, this is a really simple package and it works really, really well.
And you can go through the source code.
It's heavily commented and it's only a couple of hundred lines of code, but I'm going to use this package,
so let's go get it.
We'll find the installation link right here and go back to our ID and open our terminal and paste that
in.
Go get and then the link to the package.
OK, so it's installed now, it's real, it's relatively straightforward to use this package, and what
I'm going to do is create a new internal package that uses the functionality from the go alone package.
And that way, if I need to sign something either on the front end or on the back end, I can do so.
Now, if we go back and look at the documentation we need, as you can see right here, some kind of
secret key.
So we're obviously going to have to define that.
And of course, the easiest way to do that is either to use an environment variable or to use a command
line flag, and I'll use a command line flight.
Let's go back to our idea and think about what we're going to do here.
This link is going to be something like whatever the link to our front end is some kind of path and
then however it's signed.
So we're going to need two things here.
We're going to need that secret key.
And we're also going to need in our backend some reference to or some way of knowing what the world
to our front end is.
So let's go over to aiport, go and put that necessary logic in place.
So the first thing I'll do is go to our config struct and again, I'm on API go the main entry point
for the back end and I'll add two new members here, secret key,
which will be a string.
And also I'll call the next one the front end, which is sufficient for my purposes and it will be a
string.
So this will be the key that we use to sign our URLs and this will be the address for our front end.
OK, so we need to get that information.
So let's get down to the flag part and I'll just copy this one because it's a reading a string version
and I'll paste it twice and I'll give it default values, which will make it easier for me.
So I'm going to read into.
CFG secret key, and we'll give it the command line flag of secret, which is sufficient, I'll just
put some random characters in here just to make it work.
And of course, you can generate whatever you want for this.
And for the hint, we'll simply just call this secret key.
And for the next one, we want the front end URL, which is front end, and we'll call this front end.
That'll be the flag.
And in my case, it's called an localhost for four thousand.
And we'll give the hint of your URL to front and back.
So now we have a means of specifying our secret key and our front end, and we have sensible default
values that I can use for development so I don't have to type those in every time I want to run the
application.
Now, let's go over to our internal folder and I'll create a new package.
So a new folder and I'm going to call mine You URL seiner and I'll create a new filing there called
Sinor Dongo.
And of course, it is the package of old Sinar.
And we'll make this a very simple package to use, so the first thing we do is to find a type which
we can use to actually create this type of Zeiner.
That's what I'm calling it.
It's a struct and it only has one field secret.
If you look at the documentation, the secret has to be a slice of bytes.
Now, I'll create a few functions here and each one will have the receiver pointing to the sinor type.
So the first one as the receiver of Seiner and I'll call it, generate token from string.
And what this will do is take a string and sign it and hand back the sign strength so it takes some
data which is a string and it returns a string
and I'll just mixed up functions for the rest of them.
So we'll also have one with the receiver of Seiner and I'll call this one Verify Token.
And this is what we use to verify that the link people click on hasn't been changed in any way.
And it takes a token, which is a string and it returns bool, true or false.
And finally, we'll have another one with the receiver of S pointer designer.
And this one will check to see if tokenized expired because we can put expiry dates on these and it
takes a toll, which is a stream, and it takes minutes until they expire, which is a long name, but
it's very clear what it means.
And that's an integer.
And again, that returns a little.
So let's start on this one at a time.
So the first one, I'm going to create a variable, which I'll call you to sign, and it's just a string.
So there's a variable.
And now I'll call create a variable called
and it is assign the value of from the go alone package, which we just important.
We may have to manually import.
We'll find out shortly.
New.
Authorities found it, and that takes a secret, which is estcourt secret.
From our receiver, and it also takes a time stamp go along the time stamp.
That's just a constant.
Now, what kinds of users might we get?
What this package does?
And you can see it right on the homepage, is it will take a string and append a question mark and some
kind of value to it.
And what I want to do instead is allow us to sign new URLs that already have your URL parameters.
They already have a question mark.
So much you can do a little comparison here, a little check if from the strings package contains if
the string we want to sign contains.
So data is the first item and it contains a question mark, then I want to do one thing, otherwise
I want to do something else.
So if it contains that question mark, then I'll make Yoro to some equal to from the format package.
As per death
and my string is going to be.
S ampersand hash equals,
and I'll substitute data for my placeholder, so this will take care of the situation where I'm trying
to you, where all that already has your URL parameters.
But if it doesn't contain a question mark, then you URL to sign is equal to formatter as print f then
I get a string percent s questionmark hash equals.
And then data,
and now we need some bytes, so token bites.
This is the part where we're signing our email is Creped dot sign and we need to cast to a slice of
bytes.
You to sign,
and our token is equal to string looking votes, because we want to return to strength and we'll return,
the token and token has to have the assignment operator there.
So our token is not just a token.
It's a fully signed euro that ends with hash equals, plus the bit that we're going to use to validate
that you are up.
So there's our first one taken care of.
Now, our second one verified token is actually pretty simple.
Same thing.
We need our creped here.
Someone is going to copy this line and paste it in here and you get a response.
I'm going to ignore the actual first return parameter, but I am going to check for an error and we're
going to call Creped site.
And that require requires an actual token, which we receive.
It's a parameter here, but that needs to be a slice of bytes.
So slice of byte
and we check for an error.
If error is not equal to nil,
then I'll print out there just so we can see what's going on.
So format the print line error and I'll return false.
Otherwise we successfully verified it turned true.
And the third one where we check for an expiry date again, we need our creped, which I still have
on my clipboard, so I'll just pasted in there.
That gives us access to the go alone methods.
And this is dead simple test as a time stamp.
It's a sign the value of creped dot purse and we need to pass what we received in this function, which
is a token and that has to be Casta, a slice of white and it's token.
And we return time since not Saturday, since right from the time package, our time stamp to start
time stamp is greater than time, duration and its minutes until expire.
Times, time, up minute, so this will return true if the expiry date is OK and false if the expiry
date is not OK.
In other words, you only have 60 minutes to act on the link that you clicked on.
But sixty one minutes have gone by, so we're going to return false.
So there's our package now in the next lecture will actually use this package in our handler's dash
API and sign a valid email.