コード例 #1
0
        public static bool Set(RedisConnection redisConnection, string key, string value, RedisOfficeStateStorageSettings settings)
        {
            string[] keyArgs   = new string[] { key };
            object[] valueArgs = new object[] { value };

            string stringGetScript = @"
                local keyName = KEYS[1]
                local value = ARGV[1]

                local status = redis.call('SET', keyName, value)
                setExpired(keyName)

                local retValues = {} 
                    retValues[1] = status
                return retValues
            ";

            var expireScript = ExpireHelper.GetExpireScript(settings);
            var script       = expireScript + stringGetScript;
            var results      = (RedisResult[])(RedisResult)redisConnection.ScriptEvaluate(script, keyArgs, valueArgs);

            string setStatus = (string)results[0];

            return(setStatus == "OK");
        }
コード例 #2
0
        public static bool CheckIn(RedisConnection redisConnection, string lockerId, string workSessionId, string documentId, string state, RedisOfficeStateStorageSettings settings)
        {
            var keyBunch = new KeyNameHelper(workSessionId, documentId);

            string[] keyArgs   = new string[] { keyBunch.LockerKeyName, keyBunch.StateKeyName, keyBunch.DocumentIdToWorkSessionIdKeyName, keyBunch.WorkSessionIdToDocumentIdKeyName };
            object[] valueArgs = new object[] { lockerId, state, workSessionId, documentId };

            string checkInScript = @"
                local lockerKeyName = KEYS[1]
                local stateKeyName = KEYS[2]
                local documentIdToWorkSessionIdKeyName = KEYS[3]
                local workSessionIdToDocumentIdKeyName= KEYS[4]

                local lockerId = ARGV[1]
                local state = ARGV[2]
                local workSessionId = ARGV[3]
                local documentId = ARGV[4]

                local stateUpdateStatus = 'failed'
                local docIdToStateIdUpdateStatus = 'failed'
                local stateIdToDocIdUpdateStatus  = 'failed'
                local locker_DeletedKeysCount = 0

                updateATime(stateKeyName)
                
                local wasLockedBy = redis.call('GET', lockerKeyName)
                local lockerWasNotFound = type(wasLockedBy) == 'boolean' and not wasLockedBy
                local wasLocked = not lockerWasNotFound

                local wasLockedByMe = wasLockedBy == lockerId
                local wasLockedByAnother = wasLocked and not wasLockedByMe
                
                if not wasLockedByAnother then
                    stateUpdateStatus = redis.call('SET', stateKeyName, state)
                    setExpired(stateKeyName)
                    if not (documentId == nil or documentId == '') then
                        docIdToStateIdUpdateStatus = redis.call('SET', documentIdToWorkSessionIdKeyName, workSessionId)
                        stateIdToDocIdUpdateStatus = redis.call('SET', workSessionIdToDocumentIdKeyName, documentId)
                        setExpired(documentIdToWorkSessionIdKeyName)
                        setExpired(workSessionIdToDocumentIdKeyName)
                    end
                end
                if wasLockedByMe then
                    locker_DeletedKeysCount = redis.call('DEL', KEYS[1])
                end

                local retValues = {} 
                retValues[1] = stateUpdateStatus
                retValues[2] = locker_DeletedKeysCount
                retValues[3] = wasLockedByMe
                retValues[4] = wasLocked
                --[[
                docIdToStateIdUpdateStatus
                stateIdToDocIdUpdateStatus
                --]]

                return retValues
            ";

            var expireScript      = ExpireHelper.GetExpireScript(settings);
            var atimeUpdateScript = GetAccessTimeUpdateScript(settings);
            var script            = expireScript + atimeUpdateScript + checkInScript;
            var results           = (RedisResult[])(RedisResult)redisConnection.ScriptEvaluate(script, keyArgs, valueArgs);

            string stateUpdateStatus = (string)results[0];

#if DebugTest
            int  locker_DeletedKeysCount = (int)results[1];
            bool wasLockedByMe           = (bool)results[2];
            bool wasLocked = (bool)results[3];

            DiagnosticEvents.OnCheckIn(workSessionId, documentId, lockerId, stateUpdateStatus, locker_DeletedKeysCount, wasLockedByMe, wasLocked);
#endif
            bool success = stateUpdateStatus == "OK";

            return(success);
        }
コード例 #3
0
        internal static bool AddCheckedOut(RedisConnection redisConnection, string lockerId, string workSessionId, string documentId, RedisOfficeStateStorageSettings settings)
        {
            var keyBunch = new KeyNameHelper(workSessionId, documentId);

            string[] keyArgs   = new string[] { keyBunch.LockerKeyName, keyBunch.StateKeyName, keyBunch.DocumentIdToWorkSessionIdKeyName, keyBunch.WorkSessionIdToDocumentIdKeyName };
            object[] valueArgs = new object[] { lockerId, workSessionId, documentId, settings.LockerTTL };

            string addCheckedOutScript = @"
                local lockerKeyName = KEYS[1]
                local stateKeyName = KEYS[2]
                local documentIdToWorkSessionIdKeyName = KEYS[3]
                local workSessionIdToDocumentIdKeyName = KEYS[4]

                local lockerId = ARGV[1]
                local workSessionId = ARGV[2]
                local documentId = ARGV[3]
                local lockerTTL = ARGV[4]

                local stateUpdateStatus = 'failed'
                local docIdToStateIdUpdateStatus = 'failed'
                local stateIdToDocIdUpdateStatus  = 'failed'
                local wasLockedByAnother = false

                updateATime(stateKeyName)

                local documentIdSearch = getWorkSessionIdFromDocumentId(documentIdToWorkSessionIdKeyName)
                local sessionForThisDocumentIdFound = documentIdSearch[1];
                if not sessionForThisDocumentIdFound then

                    wasLockedByAnother = tryToLock(lockerKeyName, lockerId, lockerTTL)

                    local state = ''
                    if not wasLockedByAnother then
                        stateUpdateStatus = redis.call('SET', stateKeyName, state)
                        setExpired(stateKeyName)
                        if not (documentId == nil or documentId == '') then
                            docIdToStateIdUpdateStatus = redis.call('SET', documentIdToWorkSessionIdKeyName, workSessionId)
                            stateIdToDocIdUpdateStatus = redis.call('SET', workSessionIdToDocumentIdKeyName, documentId)
                            setExpired(documentIdToWorkSessionIdKeyName)
                            setExpired(workSessionIdToDocumentIdKeyName)
                        end
                    end
                end

                local retValues = {} 
                retValues[1] = sessionForThisDocumentIdFound
                retValues[2] = wasLockedByAnother

                retValues[3] = stateUpdateStatus
                retValues[4] = docIdToStateIdUpdateStatus
                retValues[5] = stateIdToDocIdUpdateStatus

                return retValues
            ";

            var expireScript      = ExpireHelper.GetExpireScript(settings);
            var atimeUpdateScript = GetAccessTimeUpdateScript(settings);
            var script            = expireScript + atimeUpdateScript + getWorkSessionIdFromDocumentId + tryToLock + addCheckedOutScript;
            var results           = (RedisResult[])(RedisResult)redisConnection.ScriptEvaluate(script, keyArgs, valueArgs);

            var sessionForThisDocumentIdFound = (bool)results[0];
            var wasLockedByAnother            = (bool)results[1];

            string stateUpdateStatus = (string)results[2];

#if DebugTest
            var docIdToStateIdUpdateStatus = (string)results[3];
            var stateIdToDocIdUpdateStatus = (string)results[4];

            DiagnosticEvents.OnAddCheckOut(workSessionId, documentId, lockerId, stateUpdateStatus, sessionForThisDocumentIdFound, wasLockedByAnother, docIdToStateIdUpdateStatus, stateIdToDocIdUpdateStatus);
#endif
            bool success = stateUpdateStatus == "OK";

            if (sessionForThisDocumentIdFound)
            {
                throw new CannotAddWorkSessionThatAlreadyExistsException();
            }

            return(success);
        }