免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 2403 | 回复: 0
打印 上一主题 下一主题

[Reprint]Enhance PHP session management [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2009-12-25 13:43 |只看该作者 |倒序浏览

               
            
            
                 0.kevin.vanzonneveld.net.techblog.article.enhance.php.session.management. a candidate for caching
    [1] => I was NOT able to retrieve valid cache for 0.kevin.vanzonneveld.net.techblog.article.enhance.php.session.management., starting ob_start()
    [2] => Generated content saved in cache0.kevin.vanzonneveld.net.techblog.article.enhance.php.session.management., starting ob_end_clean()
)
-->
In
PHP, sessions can keep track of authenticated in users. They are an
essential building block in today's websites with big communities and a
lot of user activity. Without sessions, everyone would be an anonymous
visitor.
In system terms, PHP sessions are little files, stored on the server's
disk. But on high traffic sites, the disk I/O involved, and not being
able to share sessions between multiple webservers make this default
system far from ideal. This is how to enhance PHP session management in
terms of performance and shareability.
Session sharing in web clusters
If you have multiple webservers all serving the same site, sessions
should be shared among those servers, and not reside on each server's
individual disk. Because once a user gets load-balanced to a different
server, the session cannot be found, effectively logging the user out.
A common way around this is to use custom session handlers. Writing
a class that overrules default behavior and stores sessions in a MySQL
database.
Sessions in Database
All webservers connect to the same database and so, as soon as www01
registers a session (insert in a sessions table), www02 can read it.
All servers can now see all sessions: problem solved?
Yes, and no. This sure is functional and tackles the shareability
issue. But databases seem to be the biggest bottlenecks of web clusters
these days. They are the hardest to scale, and so in high traffic
environments you don't want to (ab)use them for session management if
you don't have to. We have to tackle the 'performance' issue.
Database memory
Memory is about 30 times faster than disk storage. So storing our sessions in memory somehow, could deliver great performance.
MySQL query caching
One form of using database memory is the standard MySQL query
caching. But MySQL query caching isn't very effective because it
invalidates all cache related a table, if only one record in that table
is changed.
Of course the session table is changed all the time, so the session
cache is purged all the time, rendering it quite useless for our
purposes.
Heap tables / Memory tables
We're really closing in to our goal now. Storing the sessions in a
heap/memory table (a table that lives in your database server's RAM)
speeds up things greatly. Many demanding sites have opted for this
solution.
In my eyes however, it's still not optimal. Because it still
requires a lot of additional queries that your database server(s)
shouldn't necessarily have to process.
One other possible solution is using Memcache. And you will find
it's easier to setup and has a smaller footprint than most
alternatives. For one thing, because you will not have to code custom
session handler classes in PHP. Memcache session support comes native.
        
    Memcache
Memcache is a little program originally written by Live Journal.
It's quite straight forward: It reserves some memory, opens a socket
and just stays there.
We can connect to the socket and store variables in it, and later
retrieve them later on. The storage of the variables is done in RAM. So
it's lighting fast ;)
Memcache is used for caching a lot things: function results, entire
html blocks, database query results. But now we're going to use it to
store our site's user sessions.
Architecture
From system point of view, Memcache looks a lot like MySQL. You have a:
  • Server
        Where information is stored. Should be running at all times.
  • Client module
        Interface to save & get information from the server.
        It's integrated in our programming language.

There is one important difference though. If the Memcache server is
shut down, the information in it is lost. So remember to use memcache
as a cache only. Don't store information in it, that can't be retrieved
in some other way. For sessions this is a risk I'm willing to take.
Worst case scenario is that my users will be logged out. If you cannot
live with this, you could combine database & memcache session
handlers. Database will be the safe storage, memcache will be in front
of it for performance. If it crashes, you will only lose performance,
and not the data.
Installing a Memcache server
For session sharing, use a centralized server. If you only have one
webserver, it still makes sense to use Memcache from performance point
of view. Just limit it's maximum allowed memory size to 64MB (depending
on your server & wishes), and use the localhost (127.0.0.1) to
connect to it.
If you don't have a Memcache server already, you can install it very
easily with package management. I use Ubuntu so in my case that would
translate to:
aptitude install memcached
Adjust the settings in /etc/memcached/memcached.conf. In my case the defaults were OK, I only increased the max allowed memory, and allowed more hosts to connect to it.
Now let's spawn the Memcache Daemon (yes that's what the 'd' stands for):
/etc/init.d/memcached start
Done, we're ready to use it... But how?
Installing a Memcache 'client'
You could just open a socket and go talk to Memcache, but that would
eventually cause headaches. So there is a standard PHP module we can
use that does a lot of work for us, and allows us to talk object
oriented to it. This works much like installing a MySQL module. If it's
in your distro's package management, good for your, let's:
aptitude install php5-memcache
If not, no problem. Make sure you have pecl available and:
pear install pecl/memcache
(I used 'pear' and not directly pecl to circumvent the
bug
that caused a Fatal error: Allowed memory size of 8388608 bytes exhausted).
And please choose:
Enable memcache session handler support? [yes] : yes
You must enable PHP to use the memcache.so module we now have. So please add a
extension=memcache.so
to your php.ini (usually located at /etc/php5/apache2/php.ini)
Great, we have all the prerequisites to start Memcaching!
Sessions in Memcache
PHP allows you to overrule the default session handler in two ways:
  •      
    session_set_save_handler()
    .
    By programming your own session handlers, allowing you to virtually use
    any type of storage, as long as you can read/write to it from PHP.
    This example
    uses a MySQL database. We could also use this method to connect to Memcache.

  • session.save_handler
    . By specifying one of the default handlers in the php.ini file using the
    session.save_handler
    & session.save_path directives.
    Option 1 allows greater flexibiliy. And it even allows you to create
    a combined database/memcache mechanism. Resulting in a
    fallback-on-database in case memcache goes offline and loses all of
    it's sessions (effictively logging out all users).
    Option 2 is very easy to implement, doesn't require changing your existing code, and is the one I'm going to show you today.
    session.save_handler
    Assuming that you have one webserver, and installed the Memache
    server on that same machine, the hostname will be 127.0.0.1. If you
    have it on a different server, you will know what IP to substitute it
    with.
    session.save_handler = memcache
    session.save_path = "tcp://127.0.0.1:11211"
    Done! Huh? what just happened?
    Well, because we enabled Memcache session handler support, all work is done for us. PHP will now know not to use the default files handler so save session files in /var/lib/php5 but uses memcache running at 127.0.0.1 instead.
    Don't forget to restart your webserver to activate your changes to the php.ini
    /etc/init.d/apache2 restart
    The Catch

    Update - As Manuel de Ruiter says in the comments, the following is no longer true thanks to
    some updates
    As with anything too cool, there is a catch: Locking. The
    standard PHP Session module locks the whole session until the request
    finishes. Memcache is build for speed and as a result, does not support
    this kind of locking. This could lead to problems when using frames or
    ajax. Some actions may request a session-variable before it's actually
    saved.
            
        Further reading
    What we have just done with Memcache is the low-hanging fruit. We've
    enabled RAM sessions with minimum effort and without changing even one
    line of your existing code.
    But now that you have memcache running, you might want to use it for
    storing other often-used, rarely-changed variables as well.
    (This article is reprint from Mr. Kevin van Zonneveld's blog!)
                   
                   
                   
                   
                   

    本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u3/108551/showart_2130534.html
  • 您需要登录后才可以回帖 登录 | 注册

    本版积分规则 发表回复

      

    北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
    未成年举报专区
    中国互联网协会会员  联系我们:huangweiwei@itpub.net
    感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

    清除 Cookies - ChinaUnix - Archiver - WAP - TOP