Skip to content

Commit

Permalink
More thread safety.
Browse files Browse the repository at this point in the history
  • Loading branch information
enyim committed Sep 14, 2010
1 parent 768fb59 commit feb2603
Showing 1 changed file with 28 additions and 14 deletions.
42 changes: 28 additions & 14 deletions Northscale.Store/NorthScalePool.cs
Expand Up @@ -23,12 +23,10 @@ internal class NorthScalePool : IServerPool
private Uri[] poolUrls;
private BucketConfigListener configListener;

private IMemcachedNodeLocator nodeLocator;
private IOperationFactory operationFactory;
private InternalState state;

private string bucketName;
private string bucketPassword;
private IMemcachedNode[] currentNodes;

public NorthScalePool(INorthScaleClientConfiguration configuration) : this(configuration, null) { }

Expand Down Expand Up @@ -69,6 +67,8 @@ public NorthScalePool(INorthScaleClientConfiguration configuration, string bucke
catch { }
}

public VBucketNodeLocator ForwardLocator { get; private set; }

void IServerPool.Start()
{
// get the pool urls
Expand All @@ -93,7 +93,7 @@ private void InitNodes(ClusterConfig config)
if (log.IsInfoEnabled) log.Info("Received new configuration.");

// these should be disposed after we've been reinitialized
var oldNodes = this.currentNodes;
var oldNodes = this.state == null ? null : this.state.CurrentNodes;

// default bucket does not require authentication
var auth = this.bucketName == null
Expand All @@ -102,6 +102,7 @@ private void InitNodes(ClusterConfig config)

IEnumerable<IMemcachedNode> nodes;
IMemcachedNodeLocator locator;
IOperationFactory opFactory;

if (config == null || config.vBucketServerMap == null)
{
Expand All @@ -122,7 +123,7 @@ private void InitNodes(ClusterConfig config)

locator = this.configuration.CreateNodeLocator() ?? new KetamaNodeLocator();

this.operationFactory = new Enyim.Caching.Memcached.Protocol.Binary.BinaryOperationFactory();
opFactory = new Enyim.Caching.Memcached.Protocol.Binary.BinaryOperationFactory();
}
else
{
Expand Down Expand Up @@ -151,20 +152,33 @@ private void InitNodes(ClusterConfig config)

locator = vbnl;

this.operationFactory = new VBucketAwareOperationFactory(vbnl);
opFactory = new VBucketAwareOperationFactory(vbnl);
}

var mcNodes = nodes.ToArray();
locator.Initialize(mcNodes);

Interlocked.Exchange(ref this.currentNodes, mcNodes);
Interlocked.Exchange(ref this.nodeLocator, locator);
var state = new InternalState
{
CurrentNodes = mcNodes,
Locator = locator,
OpFactory = opFactory
};

Interlocked.Exchange(ref this.state, state);

if (oldNodes != null)
for (var i = 0; i < oldNodes.Length; i++)
oldNodes[i].Dispose();
}

class InternalState
{
public IMemcachedNodeLocator Locator;
public IOperationFactory OpFactory;
public IMemcachedNode[] CurrentNodes;
}

void IDisposable.Dispose()
{
if (this.configListener != null)
Expand All @@ -173,32 +187,32 @@ void IDisposable.Dispose()

this.configListener = null;

var currentNodes = this.currentNodes;
var currentNodes = this.state.CurrentNodes;

// close the pools
if (currentNodes != null)
{
for (var i = 0; i < currentNodes.Length; i++)
currentNodes[i].Dispose();

this.currentNodes = null;
}

this.state = null;
}
}

IMemcachedNode IServerPool.Locate(string key)
{
return this.nodeLocator.Locate(key);
return this.state.Locator.Locate(key);
}

IOperationFactory IServerPool.OperationFactory
{
get { return this.operationFactory; }
get { return this.state.OpFactory; }
}

IEnumerable<IMemcachedNode> IServerPool.GetWorkingNodes()
{
return this.nodeLocator.GetWorkingNodes();
return this.state.Locator.GetWorkingNodes();
}
}
}
Expand Down

0 comments on commit feb2603

Please sign in to comment.