Skip to main content
Inspiring
October 31, 2011
Question

Limiting User to One Login

  • October 31, 2011
  • 2 replies
  • 979 views

Greetings,

The goal is: Stop multiple logins with same user info

CF Version: 8,0,1,195765

MySQL Version: 5.5.14

DW Version: CS5

<cfapplication

    name="yfirsUserLogin"

    clientmanagement="Yes"

    sessionmanagement="Yes"

    sessiontimeout="#CreateTimeSpan(0,0,20,0)#"

    applicationtimeout="#CreateTimeSpan(0,0,20,0)#">

    <cfparam name="session.allowin" default="false">

    <cfparam name="session.record_id" default="0">

<cfif session.allowin neq "true">

    <cfif ListLast(CGI.SCRIPT_NAME, "/") EQ "login.cfm">

        <cfelseif ListLast(CGI.SCRIPT_NAME, "/") EQ "login_process.cfm">

          <cfelse>

            <cflocation url="http://localhost/firebureau/yfirs/login_alert.cfm" addtoken="no">

         <cfabort />

      </cfif>

</cfif>

--- Query ---

<cfquery name="rs_verify" datasource="yfirssql01">

SELECT record_id, agency_id, user_id . . . .

FROM agency_users

WHERE

user_login_name = <cfqueryparam cfsqltype="cf_sql_varchar" value="#login#"> AND

user_login_password = <cfqueryparam cfsqltype="cf_sql_varchar" value="#password#">

</cfquery>

--- Login checker ---

<cfif user_info.recordCount>
     <cfset liveSessions = createObject(
"java","coldfusion.runtime.SessionTracker")>
     <cfset sessions = tracker.
getSessionCollection(application.applicationName)>
     <cfloop item=
"loopSession" collection="#sessions#">
     <cfscript>

        thisSession = sessions[loopSession];

        thisUser = thisSession.userID;

        if(thisUser EQ user_info.user_id){

            thisSession.setMaxInactiveInterval(1);

            break;       

        }   

    </cfscript>
     </cfloop>


   <!--- log them in --->

     --- additional code here ---

    <cfset session.userID = user_info.userID>

</cfif>

    This topic has been closed for replies.

    2 replies

    Leonard_BAuthor
    Inspiring
    October 31, 2011

    Hi Owain,

    First thing is that for whatever uknown reason, my post got posted before I could add the rest of the information in reference to the actual question and I apologize for that.

    -- Answers ---

    Q1: Have not learned / had positive experiences with cfc(s) and the application.cfm has been working fine.

    Q2: With what I have been using for login allows for a user to login from multiple computers.

    Q3: Access to the section of the web site is a paid access. -  base subscription = 3 user logins

    Q4: How do I block users from purchasing base subscription and allowing ie: 20 users to login without paying additional subscriptions?

    Thanks in advance.

    Leonard B

    Owainnorth
    Inspiring
    October 31, 2011

    Okay, that's all good except for one - Application.cfm. I really would look seriously at .cfc - it's far more powerful and, learning aside, there is no reason it should give you issues, only benefits. I honestly don't even know how this can be done with App.cfm, as I don't believe it has the concept of SessionEnd. Using an app.cfc, you'd do something like this:

    <cfcomponent>

     

              <cfset this.name = "MyApplication" />

              <cfset this.SessionManagement = true />

     

              <!--- Fires on the first request to the application

              <cffunction name="onApplicationStart">

         <!--- Create a struct to keep track of which clients have how many logins --->

         <cfset application.CurrentLogins = structNew() />

              </cffunction>

              <!--- Fires on every page request --->

              <cffunction name="onRequestStart">

                          <!--- If the person's not logged in, send them to the login page, but protect against loops

        <cfif NOT structKeyExists(SESSION, "LoggedIn") and cgi.script_name NEQ "login.cfm" >

           <cflocation url="login.cfm" addtoken="false" />

        </cfif>

      </cffunction>

     

              <!--- Fires at the end of a session, in the background, so works as an auto-timeout --->

              <cffunction name="onSessionEnd">

                        <cfargument name="SessionScope" type="any">

     

         <!--- Decrement the number of logins you have on file for this Customer

         <cfif structKeyExists(application.CurrentLogins, arguments.SessionScope.CustomerId >

             <!--- Lock the struct to make it thread-safe --->

              <cflock scope="application.CurrentLogins">

                <cfset application.CurrentLogins[arguments.SessionScope.CustomerId] = application.CurrentLogins[arguments.SessionScope.CustomerId] - 1 />

              </cflock>

        </cfif>

      </cffunction>

    </cfcomponent>

    Then on your login page, do something like this once you've validated their credentials:

     

                        <!--- First make sure there's a dictionary entry in the Application scope tracker struct

                        <cfif NOT structKeyExists(application.CurrentLogins, UserCustomerId >

                                  <cfset application.CurrentLogins[UserCustomerId] = 0 />

                        </cfif>

     

      <cfif application.CurrentLogins[UserCustomerId] GTE <get max logins from database or something >

         <cflocation url="/sorry_max_connections.cfm" />

      </cfif>

                        <!--- Lock the struct to make it thread-safe --->

                        <cflock scope="application.CurrentLogins">

                                  <cfset application.CurrentLogins[UserCustomerId] = application.CurrentLogins[UserCustomerId] + 1 />

                        </cflock>

      <cfset session.LoggedIn = true />

    That would achieve what you're after, you'd have a system which kept track of everyone logged in, and automatically decrements the value at the end of someone's session. Application.cfc is not something to be feared

    Owainnorth
    Inspiring
    October 31, 2011

    Four questions:

    1 - Why aren't you using Application.cfc?

    2 - If a user's already logged in, presumably they would never get a login page? So how would they log in more than once?

    3 - Why is it a problem if they do?

    4 - What's the actual question?