I'm using a CMS-framework that initates session_start() upon page creation, however 90% of the site visitors are guests without the need for sessions, resulting in an awful lot of empty session-variables at server.
What's the best practice here? IF logged in, I need to know at an early level so I guess it means is both:
Postpone session_start() until it's actually needed
Keep the session_start() at an early stage, but make it conditional based on existance of cookie PHPSESS
Or is there a better fix, unknown to I?
Many large sites postpone the session initialization until it's actually needed, e.g. on cart pages and the user profile screen of each user.
In theory this isn't that complicated, if you were using a config file which would be required within all pages you could simply swap out a different config file for the pages that don't require any user recognition.
You're using a CMS-framework so perhaps you're somewhat limited within it. If you can differentiate the page creation process, using session_start(); in one case and not in the other, then this shouldn't be that big of a deal. Keeping the logged in users logged on once returned to the other area of the system (the index file etc) would not work though. Of course you could be using local_storage to aid you with that but relying on JavaScript only isn't very reliable.
The easiest way would probably be to spit the system into two areas, one which doesn't use any sessions (index, other information files, etc) so the process behind those page creations would be different, i.e. not using sessions.
Perhaps you could have a session class like mentioned but it would most likely conflict with other previously outputs causing the sessions to fail, but if you could flush the other output then this could possibly work, but it's kind of a hack in my opinion and it wouldn't really solve the previously mentioned problem.
Have you considered changing the lifetime of the sessions? The default setting is 24 minutes but would reducing it to 15 change anything? Is 24 minutes really that big of a deal for you? Maybe the settings in your environment make them be even longer. Are there other aspects of the system that might be the actual performance issue? Are you hosting the system yourself or do those empty sessions really not matter?
If you're expecting a lot of guest traffic without the need for sessions, then don't use it unless you absolutely need it. What I typically do is create a class for session, and add the session_start to the constructor of the class. Then, when I need sessions, I can simply call the session class within an underlying global.class.
Related
Is it possible to check if a certain session ID exists without starting a new one?
The reasons I'm asking this are:
If every user not logged in visiting the site requires session_start(), soon the session folder will be bloated with unnecessary files (even with garbage collector cleaning up expired sessions).
Of course this can be mitigated by destroying the sessions of such users. However, in this case, it seems there would be an overhead of creating and destroying files (unless PHP is smart enough to cancel these operations). Is this a bad practice?
If the user is just a guest and doesn't require a session, there is no need to create one for him.
Ideal Solutions:
if( session_exist($_COOKIE['PHPSESSID']) )
{
session_start();
}
Or:
session_start(RESUME_ONLY);
Follow-up
There is a PHP package that explains much better the aforementioned issue. Briefly, some interesting excerpts are:
Resuming A Session
[...]
You could start a new session yourself to repopulate $_SESSION, but that will incur a performance overhead if you don't actually need the session data. Similarly, there may be no need to start a session when there was no session previously (and thus no data to repopulate into $_SESSION). What we need is a way to start a session if one was started previously, but avoid starting a session if none was started previously.
[...]
If the cookie is not present, it will not start a session, and return to the calling code. This avoids starting a session when there is no $_SESSION data to be populated.
Source: Aura.Auth
Notes:
This question was initially posted as Checking for PHP session without starting one?.
However, IMO, none of the answers addressed properly the issue.
I think you are trying to solve the wrong problem here. To answer your question, no, you must use session_start before preforming session operations. You could also destroy the session if it isn't needed in the same request with session_destroy.
You can work around the session_start problem with some clever session storage options, but I think that is just the wrong answer to the problem you have. The size of sessions stored on the FS is really negligible when your servers installation footprint is at least 8GB. Furthermore, the default session storage location is /tmp which is commonly setup as a ramfs to avoid any disk overhead. If you are running into the limitations of FS session storage, you probably need to use a different SessionHandler like memcached, not worrying about if you need to start a session. On a related note, stop prematurely optimizing your code. Session storage is not going to be an issue until you need more than one server. In reality there are going to be many more database queries that would benefit from an additional index than obscure optimizations like this one.
In my PHP application, I heavily use sessions to save information during redirection:
Saving information on category, so the correct tab and/or form is displayed after a redirection
Saving information when you are logged in to access some functionalities
Saving information on errors and warnings so they are displayed once all back-end operations are done and you are redirected to the main dashboard
In implementing that I called session_start in about 40 scripts, but outside of occasionally calling unset() on a $_SESSION variable I don't close the session in any way.
Now, while I was investigating performance issues on my server, it came to my attention that an underuse of session_write_close() might be the issue (even if the question was on an apache linux and my web app is hosted on a wamp server) and that in the end, even if it is not the cause, it might be sensible to try to close the session as soon and as often as I can.
I'm wondering how do I identify the points where I can safely destroy/restart the session? And what would be the best way to do that?
Keep in mind I want the number of opened session not being an issue, so I want to be sure to keep it at a minimum.
Typically we do not close session unless it is very important since session would be closed as soon as browser is closed.
Due to lack of knowledge of your application we are not in position to comment on exact need to close session in script. Considering the events you described it might be better idea to use cookies in certain situation like "Saving information when you are logged in to access some functionalities". Regarding error and warnings; you may like to remove some session variables after you have displayed messages on dashboard page.
For "Saving information on category, so the correct tab and/or form is displayed after a redirection" you can consider using parameters in URL to show desired tabs instead of using session variable.
In case you plan to use session_write_close() then in that case you would need to do session_start if you need access to session in the same script a second time. Use of session_write_close() is only to resolve locking of session in case two scripts try to access same session at same time. So you may like to describe if it is the case with your application or not.
So let's say user did something on my website, for example uploaded some images or whatever, and he left without logging out and never came back or let's say he did come back after few months.
So my question would be, is there some kind of way for example to delete his uploaded files after session have expired, let's say after 30 mins (keep in mind that user never reloaded page), so that would need to run entirely on server side without user interfering at all.
EDIT Thank you all for your wonderful answers, it gave me quite a few great ideas, i wish i could accept all of your answers :)
Good question! My first idea was to use a database based solution. If you don't already, you'd keep track of all active sessions in a table sessions which contains, among other things you may need, the session_id and the last_visited_time. This entry would be updated every time a user visits your site:
UPDATE sessions WHERE session_id = "<current session id>" SET last_visited_time = NOW()
The second part of the mechanism would be a cronjob that scans the the sessions table for sessions whose last_visisted_time hasn't been updated lately (in whatever time interval you'd like) and deletes the files for that session.
One way would be to call
$thePath = session_save_path();
and iterate over all saved session file, unserialze each and check them for the specified timeout property.
Unfortunately, you need to scan the whole directory to find all session files, which are older than a defined period of time. You'd use start() to figure out the age of a session file.
On a well-maintained server, each virtual host should have a separate directory for its session data. A not-so-well-maintained might store all sessions in a unified shared directory. Therefore, ensure that you don't read or delete other virtual hosts' session data.
Better Approach using a database
Therefore I propose to save session data to your application's backend database. Using SQL, it would be trivial to find all outdated session files.
The documentation for session_set_save_handler() provides a sample, which explains this whole process quite nicely based on objects.
I like all the answers above, but a different solution would be to name the uploaded files in a way that you know they are "temporary", for example prepending their name with a timestamp. This way, a periodic process would clean any such files, unless your program decides that they should be kept after all, renaming them accordingly.
Ok, i have one totaly noob question about php sessions:
I have 3 (and more) php pages, i need to protect them with login system and sessions. Now, i am including this to the top of every page:
session_name('somename');
session_start();
if(!$_SESSION['user_loggedIn']){
header("location: login.php");
}
if (isset($_SESSION["timeout"])) {
$inactive = 900;
$sessionTTL = time() - $_SESSION["timeout"];
if ($sessionTTL > $inactive) {
session_destroy();
header("location: login.php");
}
}
Question: is it correct to add something like include session.php; to top of every php file, ofc. session.php would include only code above.
You shouldn't need to handle the session timeout yourself, your webserver is almost certainly handling that for you already. All you should need to do is check to see if the session exists and make sure you have login info in that session.
Also, as far as "what's the right thing to do" -- if you require it at the top of every php file, remember to use "require_once" because there's no point in doing the same thing over and over if you include other files. Also, you may only need to do this on pages where you know you only want secured users, which isn't always every page of the site.
PHP is a programming language that is similar to JavaScript but allows for better functionality of the code to develop dynamic websites and apps. PHP stands for Hypertext Pre-Processor. In this tutorial, I will walk you through what a session is, how to declare session variables, and introduce you to a few functions that will allow you to get your session up and running in the way you need it to.
What Is a Session?
First, you may be asking yoursslef, “what is a session?” In this programming language, a session is “used to store and pass information from one page to another temporarily (until the user closes the website).” If you are familiar with cookies, sessions are a very similar topic. While cookies are only stored on the local computer and browser that you use, sessions get stored on your machine as well as on the server you’re using. Both of these collect information about the way you interact with the webpage to improve the experience for a user. To summarize the two of them, “data that is kept in cookies is solely kept on the client’s side, whereas the information kept in sessions is kept on both the client and server’s sides.” (The link to the article I found this can be found here).
The most common functions that you will use as you begin to learn PHP are the session_start() function, the die() function, and the session_destroy() function. These three functions allow you as the user to start specific tasks and then stop them whenever you want. The session start function will allow you to, of course, start a new session. The die() function will allow you to clear any session variables that you may have used during your session, and the session_destroy() function will end your session. Now, understanding what a session is, let’s discuss what a session variable is and how you can declare them.
What Are Session Variables?
Session variables make it possible to make sessions in PHP useful and functional. Which variables you use will be different depending on the project you’re working on, but in my project and database I used variables that helped me see the status of users on my database. I’ll share two examples (see screenshot below, lines 54-55). The two variables I declared here were “logged_in” and “username”. All session variables are declared with a unique syntax. The proper way to declare a session variable is as follows:
$_SESSION[“nameofvariable”] = “variable declaration”;
It is important that you declare your session variables in this syntax or you will not be able to have your sessions run properly. As a system administrator, these variables help me to see who is logged into the databases and making edits to tasks. In addition, the logged_in variable enables functionality of the database and webpage. If the user is not logged in, then the code knows to redirect the user to the login page. See the example below:
Screenshot 1:
I then used these variables to help me keep track of the state that my program and database were in to allow it to function properly.
Let’s Get To It: How to Set Up Your Sessions
Now that we understand more about what a session is and how session variables can help us accomplish our goal of a functioning program, let’s discuss the process as to how we can actually implement this. First off, go ahead and open up your IDE. I personally picked Visual Studio Code as it allows me to comfortably program with color codes, but you can pick whichever one you choose. In this example I will show you how I set up both of my sessions using a particular action that implemented my to-do list to my database. Although the code I will share will be specific to my project, the principles will remain the same for all PHP code.
In the screenshot at the end of this section I have some code I wrote at the top of an action file that ultimately ended up allowing a registered user on my webpage to sign into their to-do list. Because this was an element that required the database to be fully implemented, I knew that I had to use the PHP language. In this screenshot and in your code, you should start your code with the simple PHP starter code of:
<?php
That’s right! That is all you have to do. This allows your IDE to recognize what you will be coding in. Once it has this information you get to set up your session which, believe it or not is another easy step. In order to declare that you’re going to be starting your session all you need to do is declare the following code:
session_start();
In order to properly run your sessions, it is vital to know and understand that this HAS to be the first thing declared in your code document otherwise it will not function properly. Once this code has been declared then the computer knows to iterate through the code in your document until another function is called telling it to stop. Once your function is declared you have the chance to declare your session variables and any other information you need the computer to know. Here in screenshot 2 I have the visual example of me declaring my php language, starting my session, and declaring the variables that are unique to me that establish my connection from my to-do list to my database. This is my 2nd screenshot:
Screenshot 2:
From this example you can see from lines 1-16 of my action file. Everything that I did here is what was explained in this section.
Useful Tip:
Another function that allows you to properly manage your session is the die() function. I implemented this one in my file. It is a way for the script to be stopped while keeping your session open. This was useful to me because it was a way of letting my script know to stop and moving to the next portion of my instructions, which were found in another file. If you are coding a particular project that requires multiple actions, then this is a great function to keep in mind!
Destroying (Ending) a Session
The word “destroy” sounds pretty hardcore, but in PHP sessions destroy is just a word that means “end”. The syntax of this function within the session is the following:
session_destroy()
The destroy function will take any and all data that you used during your session and destroy it. However, it is important to note that it will NOT reset or delete any of the global variables that you may have declared during your coding. In order to start a session again you need to code your project to have the first function, start_session(), called again.
End Result
You may or may not be coding a database, but the steps that I listed above should be a place to allow you to learn the basic principles of what a session is, how to start one, declare variables, and end your session at the appropriate time. In my particular database project I was able to use sessions to allow users to login to a page, log out of their account, register a new user, to update actions included in the database, and more. Whatever your project may be, sessions have a great ability to adapt to the needs that you have as a coder. In the extremely rare event this tutorial didn’t answer every question that you have, I have also included a list of some additional links and videos that may help you answer any unanswered questions about sessions in the PHP language. Happy coding!
Additional Resources:
https://www.javatpoint.com/php-session
This website is a great resource for studying more about what a PHP session is and all basic information about what they do. This page also includes information on specific types of sessions, how to code them, how to implement them, and when they should be used.
https://www.tutorialspoint.com/What-is-the-difference-between-session-and-cookies
This is a great resource for understanding the differences between sessions and cookies, and for also seeing how they are similar. This website is comprehensive in how it compares the two features, even going into detail on their capacities, functions, data storage, and format.
https://code.tutsplus.com/tutorials/how-to-use-sessions-and-session-variables-in-php--cms-31839
This website does a deep dive more into what a session is and defines Session Variables for the PHP language. It goes into detail on how to start sessions and also talks about some common errors that may occur.
https://www.javatpoint.com/php-session
This link has outstanding information and further descriptions as to how to destroy, or end, a session. It also goes into further detail on what it will do to your project and code in addition to describing what it will not do.
https://www.youtube.com/watch?v=h6KID8n0zCU
This is a great video that describes sessions. I personally like to refer to it as “Sessions for Dummies”.
If PHP session is created before login, there will be one session file created for each request to login page.
The problem is if user makes multiple requests to server through a script then those many session files will be created.
If user wants to attack server,he can send abnormally huge number of requests creating so many session files eating up all the temporary space and making the service unavailable.
I am not sure if this kind of attack is really possible/feasible.
Please share your comments on this and implications if PHP sessions is created before/after successful login.
I think you are misunderstanding session_start()
What happens with session_start is, yes, it will create a file for the individual user. But the next time you call session_start(), it is going to use that same file for that same user because the user has a cookie on their system that tells it what ID to use. In order to have the $_SESSION array available, you must call session_start() on every page.
It is very possible that someone could whip up a scenario like you just described.
In reality, yes, a hacker could always have a robot that clears its cookies after every attempt, make 10,000 requests, and possibly create a disk writing problem, but I really wouldn't worry about it too much, because the files are tiny, much smaller than the script you are writing. You'd have to write a lot more files (on the size of millions or billions) to actually create a problem.
If you really want to see what the effects would be on your server. Write a script that creates files in a directory with the equivalent of 2 paragraphs of text. and put it in a loop for 10,000 files.
If you are then worried about the affects it would have, I suggest implementing a tracker that can see an large amount of hits coming to the site from a single IP address and then either temporarily ban the IP address, or do what Google does and just provide them with a static captcha page that doesn't take many resources to serve.
So, going back to the actual 'question':
I set a session for every single user that ever visits my site, because I use sessions for not only User Authentication, but for tracking other variables on my site. So, I believe that you should set it even if they aren't logged in.
If you're worried about a session fixation attack, think about using session_regenerate_id() function.
once you run the session_start() creates the file.
what you can do as an attack is to create a robot to send separate session id in the cookie, but just have to give that one exists.
It doesn't matter, really. Your server, as cheap as it could be, will have enough space to store millions of (almost empty) session files.
Worst it can do is slow down the files access in the folder where session files are stored, but your server's disks should be monitored to begin with, and a quickly filling /tmp partition should raise an alert at some point.