Scroll down to the script below, click on any sentence (including terminal blocks!) to jump to that spot in the video!Cool, got it!
This Chapter isn't quite ready yet
Rest assured, the gnomes are hard at work on completing this video
There's one other performance enhancing that we can do and it relates to download
them. So right now if I hit download a, it works fine, but if you know, if these were
got, if these were bigger files, you would notice is that these would actually start
to slow down a little bit. And the reason is that in our
search for download, you remember we're actually, you're reading a stream
from S3 and sending that directly to the user. But this also, there's still
doesn't mean there's sort of a middleman or server has to stream from S3 and
then we have to send that to the user. There's no real reason to do that. We should
just be able to have the user download the file directly from S3. The problem is
that the, the URLs are not public number. These are private files. So if we just go
into our, um,
our bucket, I'll refresh the homepage of our bucket and go into article reference. We can click these files, they have a public URL, but if we go to it, it's not really public. It's access to tonight so it doesn't work. We can solve this by using something called a signed URL and this is a time when we're going to do something with our kind of remote filesystem that goes beyond what Flysystem to do can do. And so we're going to have to deal with directly with S3 a itself, which actually turns out to be pretty easy. Google for "S3 PHP client signed url" and you'll find their documentation about this. So it's pretty cool. You can basically do is you can say, hey S3 I want to make a get request to download this object. Um, and then you can basically say I want you to create a signed URL that is valid for 20 minutes switch you can do is you can create a download link that anyone can access to download a file but are only exists for a short amount of time. Now to do this, we need to interact directly with the S3 clients. And may remember that a few minutes ago we actually created an S3 client so that we can use it with Flysystem. So awesome. So we can just use that. The other thing we're going to need to do is we're going to need our bucket names that when we actually run this object code, here we have the bucket name.
So in article reference in
downloadArticleReference(), let's add another argument
$uploaderHelper we're actually not going to need that anymore. And
that's three and said say
S3Client $s3client. And then we're also going to need
string $s3BucketName and this will not auto wire. So I'm going to copy
that and go to my
services.yaml and add a bind for this. So I'm going to buy an
$s3BucketName: to our
And I'll need the bucket name. So I'll copy the environment variable syntax for that.
There we go. So now I can get the bucket name. Uh, next I want you to copy the
$disposition = line because we're going to put that back in a second. But otherwise
delete everything inside of here. And actually if you want to, I'll put the
disposition back. I'll come in and out cause I'm the copies and other stuff.
I'll put that back so that I can actually go and copy these a few lines of code from
their documentation. Perfect. So
$s3Client->getCommand('getObject', ) my bucket or
replace that with
$s3BucketName and then the key, that's like the path to the
file. So this is going to be
$request = $s3Client->createPresignedRequest(), you can use whatever
you want here. Um, it's a pretty small file. You don't need much time. And then
finally, what we also want to do is create a pre-sign URL. So we can do here is we
can take that request and we can turn that into a, you were out. So it's going to
give us a big long, you were held that will temporarily be valid to download that.
And what we're done going to do is actually just redirected user's browser to that
URL. So down here we can say
return new RedirectResponse(), and then the
code that they had over here was to typecast
and that should be it. Let's try it. Let's go back. We don't really need to refresh the page, but we'll do it to be safe and let's download our best practices. Boom. Well sort of first thing it did work. That's awesome. Um, but it didn't have as download it like we did before and that's because we lost the content disposition header that we were setting. But check this out. It's pretty cool. It's actually just the, you were out to our specific file, but then the sign you were l Amazon put a special signature on the end of this and that's going to make this URL a valid for only a short period of time. This is an awesome way to make private files temporarily public. All right, so what about our content disposition? Now you know where I can actually hit this and it says download what we can put that back.
One of the cool things is that there are lots of options you can pass to this, uh,
last argument. Um, and you also have options where you can control, well you want to
do is basically say, hey S3, I want you to allow the user to access his file.
And when you do, here are a few response headers that I want you to send to the
client. So for example, if we want, we can, one of the keys we can do here is we can
ResponseContentType as an option. They have to set the
and here we can use
$reference->getMimeType(). The other one we can do is
ResponseContentDisposition. And that's where I'll grab our disposition code down
here, move that back up above our command and we can set that to the
that should cause those same two headers to come back as they did before. It's now
when we hit download, boom, it actually downloads that. So that's the way that I
really recommend having users download files of any significant size from S3
You can also do the same thing with cloudfront. Cloudfront is another service that gives me even a faster access to S3 process is fair to similar, et Cetera, et cetera. I'll talk about that later.