Skip to content
This repository has been archived by the owner on Jul 7, 2019. It is now read-only.

EnyimMemcached with touch support #157

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Enyim.Caching.Tests/Enyim.Caching.Tests.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@
<Compile Include="KetamaTest.cs" />
<Compile Include="MemcachedClientCasTests.cs" />
<Compile Include="MemcachedClientConcatTests.cs" />
<Compile Include="MemcachedClientTouchTests.cs" />
<Compile Include="MemcachedClientGetTests.cs" />
<Compile Include="MemcachedClientMutateTests.cs" />
<Compile Include="MemcachedClientRemoveTests.cs" />
Expand Down
12 changes: 12 additions & 0 deletions Enyim.Caching.Tests/MemcachedClientTestsBase.cs
Original file line number Diff line number Diff line change
Expand Up @@ -137,6 +137,18 @@ protected void ConcatAssertFail(IConcatOperationResult result)
Assert.That(result.Cas, Is.EqualTo(0), "Cas value was not 0");
Assert.That(result.StatusCode, Is.Null.Or.GreaterThan(0), "StatusCode not greater than 0");
}

protected void TouchAssertPass(ITouchOperationResult result)
{
Assert.That(result.Success, Is.True, "Success was false");
Assert.That(result.StatusCode, Is.EqualTo(0), "StatusCode was not 0");
}

protected void TouchAssertFail(ITouchOperationResult result)
{
Assert.That(result.Success, Is.False, "Success was true");
Assert.That(result.StatusCode, Is.Null.Or.GreaterThan(0), "StatusCode not greater than 0");
}
}
}

Expand Down
52 changes: 52 additions & 0 deletions Enyim.Caching.Tests/MemcachedClientTouchTests.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
using System;
using NUnit.Framework;


namespace Enyim.Caching.Tests
{
[TestFixture]
public class MemcachedClientTouchTests : MemcachedClientTestsBase
{
[Test]
public void When_Touching_Existing_Item_Result_Is_Successful()
{
var key = GetUniqueKey("get");
var value = GetRandomString();
var storeResult = Store(key: key, value: value);
StoreAssertPass(storeResult);

var touchResult = _Client.ExecuteTouch(key, new TimeSpan(0, 1, 0));
TouchAssertPass(touchResult);
}

[Test]
public void When_Touching_Nonexistent_Item_Result_Is_NotSuccessful()
{
var key = GetUniqueKey("get");
var touchResult = _Client.ExecuteTouch(key, new TimeSpan(0, 1, 0));
TouchAssertFail(touchResult);
}
}
}

#region [ License information ]
/* ************************************************************
*
* @author Couchbase <[email protected]>
* @copyright 2012 Couchbase, Inc.
* @copyright 2012 Attila Kiskó, enyim.com
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* ************************************************************/
#endregion
6 changes: 6 additions & 0 deletions Enyim.Caching/Enyim.Caching.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -213,6 +213,7 @@
</Compile>
<Compile Include="Memcached\Protocol\Binary\StoreOperation.cs">
</Compile>
<Compile Include="Memcached\Protocol\Binary\TouchOperation.cs" />
<Compile Include="Memcached\Protocol\ItemOperation.cs">
</Compile>
<Compile Include="Memcached\Protocol\MultiItemOperation.cs">
Expand Down Expand Up @@ -244,9 +245,11 @@
</Compile>
<Compile Include="Memcached\Protocol\Text\TextSocketHelper.cs">
</Compile>
<Compile Include="Memcached\Protocol\Text\TouchOperation.cs" />
<Compile Include="Memcached\Results\BinaryOperationResult.cs" />
<Compile Include="Memcached\Results\ConcatOperationResult.cs" />
<Compile Include="Memcached\Results\Extensions\OperationResultExtensions.cs" />
<Compile Include="Memcached\Results\Factories\DefaultTouchOperationResultFactory.cs" />
<Compile Include="Memcached\Results\Factories\IGetOperationResultFactory`1.cs" />
<Compile Include="Memcached\Results\Factories\DefaultConcatOperationResultFactory.cs" />
<Compile Include="Memcached\Results\Factories\DefaultGetOperationResultFactory.cs" />
Expand All @@ -258,12 +261,14 @@
<Compile Include="Memcached\Results\Factories\IGetOperationResultFactory.cs" />
<Compile Include="Memcached\Results\Factories\IMutateOperationResultFactory.cs" />
<Compile Include="Memcached\Results\Factories\IRemoveOperationResultFactory.cs" />
<Compile Include="Memcached\Results\Factories\ITouchOperationResultFactory.cs" />
<Compile Include="Memcached\Results\GetOperationResult`1.cs" />
<Compile Include="Memcached\Results\Helpers\ResultHelper.cs" />
<Compile Include="Memcached\Results\IGetOperationResult`1.cs" />
<Compile Include="Memcached\Results\IPooledSocketResult.cs" />
<Compile Include="Memcached\Results\IRemoveOperationResult.cs" />
<Compile Include="Memcached\Results\Factories\IStoreOperationResultFactory.cs" />
<Compile Include="Memcached\Results\ITouchOperationResult.cs" />
<Compile Include="Memcached\Results\PooledSocketResult.cs" />
<Compile Include="Memcached\Results\RemoveOperationResult.cs" />
<Compile Include="Memcached\Results\GetOperationResult.cs" />
Expand All @@ -280,6 +285,7 @@
<Compile Include="Memcached\Results\StatusCodes\StatusCodeMessages.cs" />
<Compile Include="Memcached\Results\StoreOperationResult.cs" />
<Compile Include="Memcached\Results\TextOperationResult.cs" />
<Compile Include="Memcached\Results\TouchOperationResult.cs" />
<Compile Include="Memcached\ServerStats.cs">
</Compile>
<Compile Include="Memcached\SlidingBuffer.cs" />
Expand Down
2 changes: 2 additions & 0 deletions Enyim.Caching/IMemcachedClient.cs
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,8 @@ public interface IMemcachedClient : IDisposable

void FlushAll();

bool Touch(string key, TimeSpan validFor);

ServerStats Stats();
ServerStats Stats(string type);

Expand Down
2 changes: 2 additions & 0 deletions Enyim.Caching/Memcached/IOperationFactory.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@ public interface IOperationFactory

IStatsOperation Stats(string type);
IFlushOperation Flush();

ITouchOperation Touch(string key, uint expires);
}
}

Expand Down
4 changes: 4 additions & 0 deletions Enyim.Caching/Memcached/OperationInterfaces.cs
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,10 @@ public interface IFlushOperation : IOperation
{
}

public interface ITouchOperation : ISingleItemOperation
{
}

public struct CasResult<T>
{
public T Result { get; set; }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,12 @@ IFlushOperation IOperationFactory.Flush()
{
return new FlushOperation();
}
}

ITouchOperation IOperationFactory.Touch(string key, uint expires)
{
return new TouchOperation(key, expires);
}
}
}

#region [ License information ]
Expand Down
3 changes: 3 additions & 0 deletions Enyim.Caching/Memcached/Protocol/Binary/OpCode.cs
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,9 @@ public enum OpCode : byte
FlushQ = 0x18,
AppendQ = 0x19,
PrependQ = 0x1A,
Touch = 0x1C,
GetAndTouch = 0x1D,
GetAndTouchQ = 0x1E,

// SASL authentication op-codes
SaslList = 0x20,
Expand Down
75 changes: 75 additions & 0 deletions Enyim.Caching/Memcached/Protocol/Binary/TouchOperation.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
using System;
using System.Text;
using Enyim.Caching.Memcached.Results;
using Enyim.Caching.Memcached.Results.Extensions;
using Enyim.Caching.Memcached.Results.Helpers;

namespace Enyim.Caching.Memcached.Protocol.Binary
{
public class TouchOperation : BinarySingleItemOperation, ITouchOperation
{
private static readonly Enyim.Caching.ILog log = Enyim.Caching.LogManager.GetLogger(typeof(TouchOperation));

private uint expires;

public TouchOperation(string key, uint expires) : base(key)
{
this.expires = expires;
}

protected override BinaryRequest Build()
{
var extra = new byte[4];
BinaryConverter.EncodeUInt32(expires, extra, 0);

var request = new BinaryRequest(OpCode.Touch)
{
Key = this.Key,
Extra = new ArraySegment<byte>(extra)
};

return request;
}

protected override IOperationResult ProcessResponse(BinaryResponse response)
{
var result = new BinaryOperationResult();
#if EVEN_MORE_LOGGING
if (log.IsDebugEnabled)
if (response.StatusCode == 0)
log.DebugFormat("Touch succeeded for key '{0}'.", this.Key);
else
log.DebugFormat("Touch failed for key '{0}'. Reason: {1}", this.Key, Encoding.ASCII.GetString(response.Data.Array, response.Data.Offset, response.Data.Count));
#endif
if (response.StatusCode == 0)
{
return result.Pass();
}
else
{
var message = ResultHelper.ProcessResponseData(response.Data);
return result.Fail(message);
}
}
}
}

#region [ License information ]
/* ************************************************************
*
* Copyright (c) 2010 Attila Kisk�, enyim.com
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* ************************************************************/
#endregion
5 changes: 5 additions & 0 deletions Enyim.Caching/Memcached/Protocol/Text/TextOperationFactory.cs
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,11 @@ IFlushOperation IOperationFactory.Flush()
{
return new FlushOperation();
}

ITouchOperation IOperationFactory.Touch(string key, uint expires)
{
return new TouchOperation(key, expires);
}
}
}

Expand Down
57 changes: 57 additions & 0 deletions Enyim.Caching/Memcached/Protocol/Text/TouchOperation.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
using System;
using System.Collections.Generic;
using Enyim.Caching.Memcached.Results;

namespace Enyim.Caching.Memcached.Protocol.Text
{
public class TouchOperation : SingleItemOperation, ITouchOperation
{
private uint expires;

internal TouchOperation(string key, uint expires)
: base(key)
{
this.expires = expires;
}

protected internal override IList<ArraySegment<byte>> GetBuffer()
{
var command = "touch " + this.Key + " " + this.expires + TextSocketHelper.CommandTerminator;

return TextSocketHelper.GetCommandBuffer(command);
}

protected internal override IOperationResult ReadResponse(PooledSocket socket)
{
return new TextOperationResult
{
Success = String.Compare(TextSocketHelper.ReadResponse(socket), "TOUCHED", StringComparison.Ordinal) == 0
};
}

protected internal override bool ReadResponseAsync(PooledSocket socket, System.Action<bool> next)
{
throw new System.NotSupportedException();
}
}
}

#region [ License information ]
/* ************************************************************
*
* Copyright (c) 2010 Attila Kisk�, enyim.com
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* ************************************************************/
#endregion
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Enyim.Caching.Memcached.Results.Factories
{
public class DefaultTouchOperationResultFactory : ITouchOperationResultFactory
{
public ITouchOperationResult Create()
{
return new TouchOperationResult()
{
Success = false,
Message = string.Empty
};
}
}
}

#region [ License information ]
/* ************************************************************
*
* @author Couchbase <[email protected]>
* @copyright 2012 Couchbase, Inc.
* @copyright 2012 Attila Kiskó, enyim.com
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* ************************************************************/
#endregion
Loading