Using Redis to implement session functions

Source: Internet
Author: User

0. What is Redis

Redis is an open source API that is written in ANSI C, supports the network, can be persisted in memory, key-value databases, and provides multiple languages.

---wikipedia

1. Comparison with other user state save scenarios

General development of user status using session or cookie, two ways various pros and cons.

Session: Easy to lose in InProc mode and cause concurrency problems. If you use SQL Server or SQL Server mode and consume performance

Cookies are easy to expose some user information, and decryption also consumes performance.

Redis uses such a solution to solve a few problems,

1.Redis access speed is fast.

2. User data cannot be easily lost.

3. The user can easily support the cluster in many cases.

4. Ability to view online users.

5. Be able to realize the user log in one place. (through code implementation, follow-up introduction)

6. Support Persistence. (Of course it may be useless)

2. Realization of Ideas

1. We know that the session is actually stored in a cookie SessionID, the user each access will be sessionid to the server, the server through the ID of the user to find the corresponding state data.

My handling here is also to define a SessionID in the cookie, the program needs to get the user state when the SessionID as key to find in Redis.

2. At the same time the session allows users to not access the session during a certain period to recycle.

This feature is supported by the use of the keys in Redis to support expiration, but it is required to invoke this method on the program's own interception request in the renewal phase (Demo has an example)

The following starts the code description

3.Redis Calling Interface

The Servicestack related DLLs are referenced first.

In the Web. config add configuration, this configuration is used to set the Redis invocation address for each service separated by ",". Host written in first place

1 <appsettings>2 3     <!--per Redis, split. The first must be a host-->4     <add key= "Sessionredis" value= " 127.0.0.1:6384,127.0.0.1:6384 "/>5 6 </appSettings>

Initialize configuration

 static Managers () {string sessionredis= configurationmanager.appsettings["Sessionredis"];            String timeOut = configurationmanager.appsettings["Sessionredistimeout"]; if (string. IsNullOrEmpty (Sessionredis)) {throw new Exception ("Web. config is missing a configuration Sessionredis, split between each redis." First            Must be a host "); } if (string.            IsNullOrEmpty (timeout) ==false) {timeout = Convert.ToInt32 (timeout); } var host = Sessionredis.split (char.            Parse (","));            var writehost = new string[] {host[0]}; var readhosts = host. Skip (1).            ToArray ();                Clientmanagers = new Pooledredisclientmanager (Writehost, readhosts, new Redisclientmanagerconfig {                Maxwritepoolsize = writereadcount,//"write" link pool link number maxreadpoolsize = writereadcount,//"read" Link Pool link number        AutoStart = true}); }

To control the convenience of writing a delegate

<summary>/        /write to        //</summary>//<typeparam name= "F" ></typeparam>        // /<param name= "Dowrite" ></param>///        <returns></returns> public        F tryrediswrite< F> (func<iredisclient, f> dowrite)        {            Pooledredisclientmanager prcm = new Managers (). Getclientmanagers ();            Iredisclient client = null;            Try            {                using (client = PRCM. Getclient ())                {                    return dowrite (client);                }            }            catch (redisexception)            {                throw new Exception ("Redis write exception. Host:" + client.) Host + ", Port:" + client. Port);            }            Finally            {                if (client! = null)                {                    client. Dispose ();}}}        

A call to the example other specific look at the source code

        <summary>////        store objects in key/value form to cache///</summary>//        <typeparam name= "T" > Object categories </typeparam>        //<param name= "Value" > collection to write </param> public        void Kset (dictionary< String, t> value)        {            func<iredisclient, bool> fun = (iredisclient client) = =            {                client. Setall<t> (value);                return true;            };            Tryrediswrite (fun);        }

4. Implement session

Write a SessionID to the cookie as stated above

    <summary>///    User status Management///    </summary> public    class Session {//        <summary>        ///Initialize//</summary>//<param name= "_context" ></param> public Session ( HttpContextBase _context)        {            var context = _context;            var cookie = context. Request.Cookies.Get (sessionname);            if (cookie = = NULL | | string. IsNullOrEmpty (cookies. Value)            {                SessionId = NewGuid ();                Context. RESPONSE.COOKIES.ADD (New HttpCookie (SessionName, SessionId));                Context. REQUEST.COOKIES.ADD (New HttpCookie (SessionName, SessionId));            }            else            {                SessionId = cookie. Value;}}    }

Ways to access the user

        <summary>///        Get current User information///</summary>//        <typeparam name= "T" ></typeparam> /        //<returns></returns> public Object get<t> () where t:class,new ()        {            return new Redisclient<t> (). Kget (SessionId);        }        <summary>//        whether the user is online//</summary>//        <returns></returns>        Public BOOL IsLogin ()        {            return new redisclient<object> (). Kisexist (SessionId);        }        <summary>///Login///        </summary>/        <typeparam name= "T" ></typeparam> /        //<param name= "obj" ></param> public        void login<t> (T obj) where t:class,new ()        { C24/>new redisclient<t> (). Kset (SessionId, obj, new TimeSpan (0, managers.timeout, 0));        }

6. Renewal

The default user does not have access to log off users for more than 30 minutes, so the user's logoff time is delayed by 30 minutes per visit

This requires a call to the Redis renewal method

        <summary>//extension///        </summary>/        <param name= "key" ></param>///        < param name= "expirestime" ></param> public        void Ksetentryin (string key, TimeSpan expirestime)        {            Func<iredisclient, bool> fun = (iredisclient client) = =            {                client. Expireentryin (key, expirestime);                return false;            };            Tryrediswrite (fun);        }

After encapsulation

Here I use the actionfilter in MVC3 to intercept all requests from the user.

namespace test{public    class Sessionfilterattribute:actionfilterattribute    {        //<summary>// /renewal per request///</summary>//        <param name= "Filtercontext" ></param> public        override void OnActionExecuting (ActionExecutingContext filtercontext)        {            new Session (Filtercontext.httpcontext). Postpone ();}}}    


To register in Global.asax

public static void Registerglobalfilters (Globalfiltercollection filters)        {            filters. ADD (New Sessionfilterattribute ());        }        protected void Application_Start ()        {            registerglobalfilters (globalfilters.filters);        }

5. Invocation mode

To facilitate the invocation of new features in borrowing 4.0, add a controller to an extended property

public static class Extsessions{public static Session Sessionext (this controller controller)    {        return new Session (Controller. HttpContext);}    }

Calling methods

    public class Homecontroller:controller    {publicly        actionresult Index ()        {this            . Sessionext (). IsLogin ();            return View ();        }    }

6. Code download

Click to download

7. Follow-up

SessionManager includes getting the number of user lists, logging off a user, obtaining user information based on user ID, Online user object list, online user SessionID list, etc.

Follow-up will implement a user login function

Using Redis to implement session functions

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.