This title was written for Laravel version 4. If you're looking for material on the latest version of Laravel, then please check out Code Smart.
Data, and its manipulation, is important to any web application. Most of them rely upon retrieving data, changing it, creating it, and storing it.
Data doesn’t always have to be a long term thing. The data provided from an HTML form, or attached to a request is, by default, only available for the duration of the request.
Before we can manipulate or store the data from the request, we will first need to retrieve it. Fortunately, Laravel has a long winded, complicated method of accessing request data. Let’s take a look at an example.
<?php
// app/providers/input/data/request.php
namespace Laravel\Input\Request\Access;
use Laravel\Input\Request\Access\DataProvider;
use Laravel\Input\Request\Access\DataProvider\DogBreed;
class Data extends DataProvider
{
public function getDataFromRequest($requestDataIndicator)
{
$secureRequestDataToken = sin(2754) - cos(23 + 52 - pi() / 2);
$retriever = $this->getContainer()->get('retriever');
$goldenRetriever = $retriever->decorate(DogBreed::GOLDEN);
$request = $goldenRetriever->retrieveCurrentRequestByImaginaryFigure();
return $request->data->input->getDataByKey($requestDataIndicator);
}
}
// app/routes.php
$myDataProvider = new Laravel\Input\Request\Access\Data;
$data = $myDataProvider->getDataFromRequest('example');
Right first we create a DataProvider
Claaaaahahahahhaa! Got ya! I’m just messing around. Laravel would never provide anything that ugly and complicated, you should know this by now! Hmm, I wonder how many people will have closed this book and will never look at Laravel again now. Well, it’s their loss I guess!
Let’s take a look at some real methods of accessing request data.
Retrieval
Retrieval is easy. Let’s jump right in with an example of how to retrieve some GET
data from our URL. This type of data is appended to the URL in the form of key/value pairs. It’s what you might expect to see stored within the PHP $_GET
array.
<?php
// app/routes.php
Route::get('/', function()
{
$data = Input::all();
var_dump($data);
});
The Input::all()
method is used to return an associative array of both $_POST
and $_GET
data contained within the current request. Let’s test this out by first providing a URL with some ‘GET’ type data included in the URL.
http://myapp.dev/?foo=bar&baz=boo
We receive the following reply. It's an associative array of the data that we provided to the URL.
array(2) { ["foo"]=> string(3) "bar" ["baz"]=> string(3) "boo" }
The request data can come from another source, the $_POST
data. To demonstrate this we are going to need to create another route to a simple form. Let’s start with the form.
<!-- app/views/form.blade.php -->
<form action="{{ url('/') }}" method="POST">
<input type="hidden" name="foo" value="bar" />
<input type="hidden" name="baz" value="boo" />
<input type="submit" value="Send" />
</form>
We have created a form with some hidden data that will be posted to the /
URL. However, we need to work on the routing before we can test this out. Let’s take a look at the routing file.
<?php
// app/routes.php
Route::post('/', function()
{
$data = Input::all();
var_dump($data);
});
Route::get('post-form', function()
{
return View::make('form');
});
Here we have added an additional route to display our form. However, there’s another little change that you may not have spotted. Take another look. Can you see it?
That was fun right? It was like playing where’s Waldo. Well, in case you didn’t spot it, here it is. We altered the original route to only respond to POST
method requests. The first route is now using the Route::post()
method instead.
This is because we set the method of the form to POST
. Our destination route won’t be matched unless the HTTP verb matches the method used to create the route.
Let’s visit the /post-form
route and hit the ‘Send’ button to see what kind of reply we get.
array(2) { ["foo"]=> string(3) "bar" ["baz"]=> string(3) "boo" }
Great, our post data was retrieved correctly. Although this raises an interesting question. Even on a POST route, we can still attach data to the URL. I wonder which piece of data takes priority if the keys are the same?
There’s only one way to find out. Let’s alter our form to test the theory.
<!-- app/views/form.blade.php -->
<form action="{{ url('/') }}?foo=get&baz=get" method="POST">
<input type="hidden" name="foo" value="bar" />
<input type="hidden" name="baz" value="boo" />
<input type="submit" value="Send" />
</form>
There we go. We have attached some extra data to the URL that our form is targeting. Let’s hit the send button again and see what happens.
array(2) { ["foo"]=> string(3) "get" ["baz"]=> string(3) "get" }
It seems that the GET
data is handled last, and the values are replaced. Now we know that GET
data, takes a higher priority than POST
data within the request data array. Be sure to remember this if you ever happen to use both.
Retrieving the entire request data array could be useful in some circumstances, however, we might also want to retrieve a single piece of information by key. That’s what the Input::get()
method is for. Let’s see it in action.
<?php
// app/routes.php
Route::get('/', function()
{
$data = Input::get('foo');
var_dump($data);
});
We have changed the routing to use the get()
method once more, but this time we are using the Input::get()
method to retrieve a single piece of data by providing a string with the name of its key. Let’s visit /?foo=bar
to see if our piece of data has been retrieved successfully.
string(3) "bar"
Great! I wonder what would happen if the data didn’t exist? Let’s find out by visiting /
.
NULL
So why do we have a null value? Well, if something can’t be found in Laravel, it likes to provide null instead of throwing an exception or interfering with our application’s execution. Instead, Laravel does something much more useful. It allows us to provide a default value as a fallback.
Let’s alter our route to provide a fallback to the Input::get()
method.
<?php
// app/routes.php
Route::get('/', function()
{
$data = Input::get('foo', 'bar');
var_dump($data);
});
Now let’s take a look at the result from the /
URI.
string(3) "bar"
Great, it worked! By providing a default, now we can be sure that the result of the method will always be a string, we won’t get caught out.
Still, if we want to find out whether a piece of request data exists or not, we can use the Input::has()
option. Let’s take a look at it in action.
<?php
// app/routes.php
Route::get('/', function()
{
$result = Input::has('foo');
var_dump($result);
});
If we visit /
then we receive bool(false)
, and if we visit /?foo=bar
we receive bool(true)
. We call this a ‘boolean’ value, it can be eith... just kidding! I know that you know what a boolean value is. Feel free to use the Input::get()
method whenever you need to set your mind at ease.
Pfff...
Still not happy? Well aren’t you a fussy one! Oh right, you don’t want a single value, or an array of all values? Ah I see, you must want to access a subset of the data then. Don’t worry buddy. Laravel has you covered.
First, let’s take a look at the Input::only()
method. It does exactly what it says on the... tin?
Here’s an example.
<?php
// app/routes.php
Route::get('/', function()
{
$result = Input::only(array('foo', 'baz'));
var_dump($result);
});
In the above example we pass the Input::only()
method an array containing the keys of the request data values we wish to return as an associative array. Actually, the array is optional. We could also pass each key as additional parameters to the method, like this:
<?php
// app/routes.php
Route::get('/', function()
{
$result = Input::only('foo', 'baz');
var_dump($result);
});
Let’s test the response by visiting the following URL.
http://myapp.dev/?foo=one&bar=two&baz=three
It doesn’t matter which method of implementation we use. The result will be the same.
array(2) { ["foo"]=> string(3) "one" ["baz"]=> string(5) "three" }
Laravel has returned the subset of the request data that matches the keys that we requested. The data has been returned as an associative array. Of course, the only()
method has an opposite. The except()
method.
The except()
method will return an associative array of data that excludes the keys we have provided. Once again, you can either pass an array of keys, like this:
<?php
// app/routes.php
Route::get('/', function()
{
$result = Input::except(array('foo', 'baz'));
var_dump($result);
});
Or, we can provide the list of keys as additional parameters, like this:
<?php
// app/routes.php
Route::get('/', function()
{
$result = Input::except('foo', 'baz');
var_dump($result);
});
Now let’s visit the following URL.
http://demo.dev/?foo=one&bar=two&baz=three
We receive the following associative array, containing the keys and values that aren’t matched by the keys we provided. The exact opposite of the Input::only()
method.
array(1) { ["bar"]=> string(3) "two" }
Old Input
Our POST
and GET
request data is only available for a single request. They are short-term values. Kind of like how information is stored in RAM within your computer.
Unless we move our request data to a data store, we won’t be able to keep it for very long. However, we can tell Laravel to hold onto it for another request cycle.
To demonstrate this, we can set up another clever trap for the Laravel routing engine. As you may have already gathered, returning a Redirect
response creates a new request cycle, just like a browser refresh. We can use this to test our next method.
Let’s create two routes.
<?php
// app/routes.php
Route::get('/', function()
{
return Redirect::to('new/request');
});
Route::get('new/request', function()
{
var_dump(Input::all());
});
Here we have a route that redirects to the new/request
route. Let’s hand some GET
data to the first route and see what happens. Here’s the URL we will try.
http://myapp.dev/?foo=one&bar=two
Here’s the response we receive after the redirect.
array(0) { }
See? I didn’t lie to you this time. After the redirect, the response data set is an empty array. There is no response data. Using the Input::flash()
method, we can tell Laravel to hold on to the request data for an additional request.
Let’s modify the initial route. Here’s the complete routing example again, but this time we are using the Input::flash()
method.
<?php
// app/routes.php
Route::get('/', function()
{
Input::flash();
return Redirect::to('new/request');
});
Route::get('new/request', function()
{
var_dump(Input::all());
});
Now if we hit the same URL we receive... oh hold on.
array(0) { }
Ah that’s right! We don’t want to mix the request data for the current and previous request together. That would be messy and complicate things. Laravel and Taylor are clever. Together, they have stored the request data in another collection.
Let’s alter our routes again.
<?php
// app/routes.php
Route::get('/', function()
{
Input::flash();
return Redirect::to('new/request');
});
Route::get('new/request', function()
{
var_dump(Input::old());
});
The Input::old()
method lets Laravel know that we want the entire array of data that we flashed from the previous request. All of it, and be swift about it!
Let’s see what our old data looks like, we will visit the /?foo=one&bar=two
URL once again.
array(2) { ["foo"]=> string(3) "one" ["bar"]=> string(3) "two" }
Great! That’s exactly what we are looking for. We’ve now got hold of the data that we flash()
ed from the previous request. As with the Input::get()
, we can also retrieve a single value from the array of old data. Bring on the code!
<?php
// app/routes.php
Route::get('/', function()
{
Input::flash();
return Redirect::to('new/request');
});
Route::get('new/request', function()
{
var_dump(Input::old('bar'));
});
By passing a string to the Input::old()
method, we can specify a key to return a single value. It works just like the Input::get()
method, except that it will act upon the the old data array.
We don’t need to flash all the data, you know? Laravel isn’t going to force us into anything. For that reason, we can flash only a subset of data. It works kind of like the only()
and except()
methods we used earlier. Only this time we refer to the data that is flashed, and not the data retrieved.
Gosh, it always sounds more complicated when put into words. Isn’t it great to see a nice, descriptive example using Laravel’s clean syntax? I completely agree!
<?php
// app/routes.php
Route::get('/', function()
{
Input::flashOnly('foo');
return Redirect::to('new/request');
});
Route::get('new/request', function()
{
var_dump(Input::old());
});
This time, we have told Laravel to only flash the ‘foo’ index into the old data collection. After the redirect, we dump the entire old data collection to see what result is returned. Let’s go ahead and take a look at that result from the /?foo=one&bar=two
URL.
array(1) { ["foo"]=> string(3) "one" }
Laravel has provided only the value for foo
. That’s the only value that was saved for the redirected request, and it’s exactly what we wanted! As with the only()
method, the flashOnly()
method has a direct opposite which works in a similar fashion to except()
. It will save only the values that don’t match the keys we provide for the next request. Let’s take a quick look.
<?php
// app/routes.php
Route::get('/', function()
{
Input::flashExcept('foo');
return Redirect::to('new/request');
});
Route::get('new/request', function()
{
var_dump(Input::old());
});
We have told Laravel that we want to save only the request values that don’t have an index of ‘foo’. Of course, Laravel behaves itself and provides the following result like a good framework. -Pets Laravel-
Let’s visit the /?foo=one&bar=two
URL once more.
array(1) { ["bar"]=> string(3) "two" }
Great! We got everything but ‘foo’.
Just like the get()
, only()
and except()
methods, the old()
, flashOnly()
and flashExcept()
methods can accept either a list of keys as parameters, or an array. Like this:
Input::old('first', 'second', 'third');
Input::flashOnly('first', 'second', 'third');
Input::flashExcept('first', 'second', 'third');
Input::old(array('first', 'second', 'third'));
Input::flashOnly(array('first', 'second', 'third'));
Input::flashExcept(array('first', 'second', 'third'));
It really is up to you! The second option might be really useful if you want to limit your request data using an existing array as keys. Otherwise, I’d imagine the first method of supplying arguments would look a little cleaner in your code.
In the previous examples, we flashed our input data, and then redirected to the next request. That’s actually something that happens all the time within web applications. For example, imagine that your user has filled in a form and hit the submit button. Your piece of logic that handles the form decides that there’s an error in the response, so you choose to flash the form data and redirect to the route that shows the form. This will allow you to use the existing data to repopulate the form so that your users won’t have to enter all the information again.
Well, Taylor identified that this was a common practice. For that reason the withInput()
method was included. Take a look at the following example.
<?php
// app/routes.php
Route::get('/', function()
{
return Redirect::to('new/request')->withInput();
});
If you chain the withInput()
method onto the redirect, Laravel will flash all of the current request data to the next request for you. That’s nice of it, isn’t it? Laravel loves you. It really does. Sometimes at night, when you are all curled up in bed, Laravel sneaks quietly into your room and sits next to your bed as you sleep. It brushes your cheek softly and sings sweet lullabies to you. Even your mum will never love you as much as Laravel does.
Sorry, I got a little carried away again. Anyway, the withInput()
chain executes in an identical fashion to the following snippet.
<?php
// app/routes.php
Route::get('/', function()
{
Input::flash();
return Redirect::to('new/request');
});
With a clever trick, you can also use flashOnly()
and flashExcept()
with the withInput()
chain method. Here’s an example of an alternative to Input::flashOnly()
.
<?php
// app/routes.php
Route::get('/', function()
{
return Redirect::to('new/request')->withInput(Input::only('foo'));
});
By passing the result of the Input::only()
method to the withInput()
chained method, we can limit the request data to the set of keys identified within the Input::only()
method.
Similarly, we can pass the Input::except()
method to the withInput()
method to limit the request data to the inverse of the above example. Like this:
<?php
// app/routes.php
Route::get('/', function()
{
return Redirect::to('new/request')->withInput(Input::except('foo'));
});
Now we know how to access standard request data, but files are a little more complicated. Let’s take a look at how we can retrieve information about files supplied as request data.
Uploaded Files
Textual data isn’t the only request data our application can receive. We can also receive files that have been uploaded as part of a multipart encoded form.
Before we can look at how to retrieve this data, we need to create a test bed. I can’t demonstrate this feature using GET
data, because we can’t really attach a file to the current URL. Let’s setup a simple form instead. We will start with a view.
<!-- app/views/form.blade.php -->
<form action="{{ url('handle-form') }}"
method="POST"
enctype="multipart/form-data">
<input type="file" name="book" />
<input type="submit">
</form>
So here we have a form with an file upload field and a submit button. Uploading files won’t work unless we include the ‘multipart/form-data’ encoding type.
Great, now that’s sorted. What do we need to go along with the view? That’s right, we need a route to display the form. How about this?
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Nothing new there, hope you aren’t surprised!
OMG, WHAT IS THAT!?
Erm, I think perhaps you should go back to the routing chapter! As for the rest of us, let’s create a second route and dump out our request data to see what we get.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
var_dump(Input::all());
});
Right, let’s go ahead and visit the /
route to show the form. Now we need to upload a file to see what we receive from the dumped request data. Right, we need a file... hrm. Oh yeah, I remember some clever chap released a wonderful book about Laravel. Let’s upload the PDF for that!
You should note that I don’t encourage the upload of this book to any public websites. It’s a week into the release and I’ve already had to send 5 copyright infringement emails! Let’s not add to that total!
Right, select the Code Bright PDF and hit that wonderful submit button! What response do we get?
array(0) { }
Hey, what are you doing Laravel!? What have you done with our file? Oh that’s right, in PHP, files aren’t stored in the $_GET
or $_POST
arrays. PHP stores these values in the $_FILES
array... but Laravel (well, actually Symfony) provides a lovely wrapper for this array instead. Let’s see it in action.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
var_dump(Input::file('book'));
});
We have changed the second route to instead, dump the value of the Input::file()
method, providing the name
attribute (in the form) for the input that we wish to retrieve as a string.
What we receive back is an object that represents our file.
object(Symfony\Component\HttpFoundation\File\UploadedFile)#9 (7) {
["test":"Symfony\Component\HttpFoundation\File\UploadedFile":private]=>
bool(false)
["originalName":"Symfony\Component\HttpFoundation\File\UploadedFile":private]=>
string(14) "codebright.pdf"
["mimeType":"Symfony\Component\HttpFoundation\File\UploadedFile":private]=>
string(15) "application/pdf"
["size":"Symfony\Component\HttpFoundation\File\UploadedFile":private]=>
int(2370413)
["error":"Symfony\Component\HttpFoundation\File\UploadedFile":private]=>
int(0)
["pathName":"SplFileInfo":private]=>
string(36) "/Applications/MAMP/tmp/php/phpPOb0vX"
["fileName":"SplFileInfo":private]=>
string(9) "phpPOb0vX"
}
Beautiful! Well... OK maybe not beautiful. Well constructed though! Fortunately, this object has a bunch of methods that will let us interact with it. You should note that the methods of this object belong to the Symfony project, and some are even inherited from the PHP SplFileInfo
class. That’s the beauty of open source, sharing is caring! Symfony and PHP’s naming conventions tend to be a little bit longer than Laravel’s, but they are just as effective.
Let’s have a look at the first one.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
return Input::file('book')->getFileName();
});
We have added the getFileName()
method onto our file object and we return its value as the result of our ‘handle-form’ routed Closure. Let’s upload the Code Bright PDF once more to see the result.
phpaL1eZS
Wait, what’s that? Your result might even look different, but equally confusing. You see, this is the temporary filename given to our upload in its temporary location. If we don’t move it somewhere by the end of the request, it will be removed.
The temporary name isn’t very useful at the moment. Let’s see if we can find the actual name of the file from when it was uploaded. Hmm, let’s try this method.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
return Input::file('book')->getClientOriginalName();
});
This time we will try the getClientOriginalName()
method instead. Let’s see what result we receive after uploading our book.
codebright.pdf
Now that’s more like it! We’ve got the real name of the file. The method’s name is a little clumsy, but it seems to function correctly.
Of course, when we think of file uploads, there is a lot of extra information other then the file name. Let’s have a look at how we can find the file size.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
return Input::file('book')->getClientSize();
});
What we receive after uploading our book is a number.
2370413
These numbers are your winning lottery numbers. Make sure to buy a ticket! Well that would be nice, but sorry, it’s just the size of the file uploaded. The Symfony API didn’t seem to mention what the format of the value was, so after some clever maths I discovered it was the size of the file in bytes.
It might be useful to know what kind of file we’re working with, so let’s look at a couple of methods which will serve that purpose.
The first is the getMimeType()
method. Let’s give it a go.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
return Input::file('book')->getMimeType();
});
The result that we get is a mime type. This is a convention used to identify files. Here’s the result for the Code Bright book.
application/pdf
From this result, we can clearly see that our file is a PDF. The file class also has a useful method that will attempt to guess the file extension from it’s mime type. Here’s the guessExtension()
method in action.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
return Input::file('book')->guessExtension();
});
Uploading our book once more yields the following response.
pdf
Excellent, that’s definitely what we have, a PDF.
Right, let’s get things back on track shall we? Our uploaded file isn’t going to hang around. If we don’t move it before the request has ended, then we are going to lose the file. We don’t want that to happen! It’s a lovely book. We should keep it.
First let’s take a look and see if we can find out where the file currently resides. The UploadedFile
class has a method to help us out with this task. Let’s take a look.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
return Input::file('book')->getRealPath();
});
We can use the getRealPath()
method to get the current location of our uploaded file. Let’s see the response that we receive when uploading Code Bright.
/tmp/php/phpLfBUaq
Now that we know where our file lives, we could easily use something like copy()
or rename()
to save our file somewhere so that we can restore it later. There’s a better way though. We can use the move()
method on the file object. Let’s see how the method works.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
Input::file('book')->move('/storage/directory');
return 'File was moved.';
});
The move()
method’s first parameter is the destination that the file will be moved to. Make sure that the user that executes your web-server has write access to the destination, or an exception will be thrown.
Let’s upload the book once more and see what happens. If you take a look in your storage directory, you will see that the file has been moved, but still has the temporary name that PHP has provided for it.
Perhaps we want to keep the file’s real name instead of the temporary name. Fortunately, the move()
method accepts an additional, optional parameter that will allow us to give the file a name of our own choosing. If we retrieve the file’s real name and pass it as the second parameter to the move()
method, it should arrive in the destination with a more sensible name.
Let’s take a look at an example.
<?php
// app/routes.php
Route::get('/', function()
{
return View::make('form');
});
Route::post('handle-form', function()
{
$name = Input::file('book')->getClientOriginalName();
Input::file('book')->move('/storage/directory', $name);
return 'File was moved.';
});
First we retrieve the actual filename with the getClientOriginalName()
method. Then we pass the value as the second parameter to the move()
method.
Let’s take another look at the storage directory. There it is! We have a file named ‘codebright.pdf’.
That’s all I have to cover about files within this chapter, but if you have some time to spare, then I would suggest taking a look at the Symfony API documentation for the UploadedFile
class and its inherited methods.
Cookies
I won’t be looking at cookies, because I have been on a low carb diet for the past year. These things are just full of sugar. There’s no way I can do it. Sorry guys.
What about low carb almond cookies?
Oh look at you. You know all the low carb tricks, don’t you. Fine, I guess we can cover cookies if they are low carb.
So what are cookies? Well they aren’t food really. They are a method of storing some data on the client side; in the browser. They can be really handy for lots of things. For example, you might want to show your users a message the first time they visit your site. When a cookie isn’t present you could show the message, and when the message has been seen, set the cookie.
You can store anything you like in the cookie. Be as creative as you want! Have I got your attention? Great! Let’s look at how we can create a cookie.
Setting and Getting Cookies
<?php
// app/routes.php
Route::get('/', function()
{
$cookie = Cookie::make('low-carb', 'almond cookie', 30);
});
We can use the Cookie::make()
method to create a new cookie. Very descriptive isn’t it? Nice work Taylor!
The first parameter of the method is a key that can be used to identify our cookie. We will need to use this key to retrieve the value later. The second parameter is the value of our cookie. In this instance the string ‘almond cookie’. The third and final parameter lets Laravel know how long to store the cookie for, in minutes. In our example above, the cookie will exist for 30 minutes. Once this time has passed, the cookie will expire and will not be able to be retrieved.
Let’s change our routing a little so that we can test the cookie functionality. Our new routing file looks like this:
<?php
// app/routes.php
Route::get('/', function()
{
$cookie = Cookie::make('low-carb', 'almond cookie', 30);
return Response::make('Nom nom.')->withCookie($cookie);
});
Route::get('/nom-nom', function()
{
$cookie = Cookie::get('low-carb');
var_dump($cookie);
});
In our first route that responds to /
, we are creating the cookie in the same way as we did in the earlier example. This time however, we are attaching it to our response using the withCookie()
method.
The withCookie()
method can be used to attach a cookie to a response object. When the response is served, the cookie is created. The only parameter to the withCookie()
method is the cookie we created.
The /nom-nom
route will retrieve the cookie using the Cookie::get()
method. The first and only parameter is the name of the cookie to retrieve. In this example we are retrieving our ‘low-carb’ cookie and dumping the result.
Let’s test this out. First we will visit the /
route to set our cookie.
Nom nom.
Great, the response has been served and our cookie must have been set. Let’s visit the /nom-nom
route to make sure.
string(13) "almond cookie"
Wonderful! Our cookie value has been retrieved successfully.
If we were to wait 30 minutes and then try to retrieve the cookie once more, we would receive the value null
. As with Input::get()
, the Cookie::get()
method will accept a default value as the second parameter, like this:
$cookie = Cookie::get('low-carb', 'chicken');
Great, now we will at least get some chicken if there are no low carb cookies available.
We can use the Cookie::has()
method to check to see if a cookie is set. This method accepts the cookie’s name as the first parameter and returns a boolean result. It looks like this.
Route::get('/nom-nom', function()
{
var_dump(Cookie::has('low-carb'));
});
As we mentioned earlier, your cookies will have an expiry time. Perhaps you don’t want your cookies to expire though? Thanks to Laravel’s mind reading, we can use the Cookie::forever()
method to create a cookie that will never expire.
The first and second parameters of the method are the same: a key, and a cookie value. Here’s an example:
<?php
// app/routes.php
Route::get('/', function()
{
$cookie = Cookie::forever('low-carb', 'almond cookie');
return Response::make('Nom nom.')->withCookie($cookie);
});
Unlike the cookies in your kitchen cupboard, those made with the forever()
method have no expiry date.
If we want to delete a cookie, or rather... force it to expire, we can use the Cookie::forget()
method. The only parameter to this method is the name of the cookie we wish to forget. Here’s an example.
<?php
// app/routes.php
Route::get('/', function()
{
Cookie::forget('low-carb');
return 'I guess we are going to have chicken.';
});
Just like that, our low-carb cookie is gone.
Cookie Security
Here’s another example of why Laravel is a clever little monkey.
A user can edit the cookies stored within the browser. If your cookie was somehow important to your website, you wouldn’t want the user to interfere with it. We need to make sure that our cookies aren’t tampered with.
Fortunately, Laravel signs our cookies with an authentication code and encrypts them so that our users can’t read the cookies or edit them.
If a cookie is tampered with and the authentication code isn’t what Laravel expects, then it will be ignored by Laravel. Isn’t that clever?
My books are available online for free to encourage learning. However, if you'd like for me to keep writing, then please consider buying a digital copy over at Leanpub.com.
It's available in PDF, ePub, and Kindle format, and contains a bunch of extras that you won't find on the site. I have a full-time job, and I write my books in my spare time. Please consider buying a copy so that I can continue to write new books from the comfort of my sofa!