forked from nhibernate/nhibernate-core
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathCacheBatcher.cs
110 lines (98 loc) · 2.71 KB
/
CacheBatcher.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using NHibernate.Engine;
using NHibernate.Persister.Collection;
using NHibernate.Persister.Entity;
namespace NHibernate.Cache
{
/// <summary>
/// A batcher for batching operations of <see cref="ICacheConcurrencyStrategy"/>.
/// </summary>
public sealed partial class CacheBatcher
{
private readonly Dictionary<ICacheConcurrencyStrategy, CachePutBatch> _putBatches =
new Dictionary<ICacheConcurrencyStrategy, CachePutBatch>();
private readonly ISessionImplementor _session;
private static readonly INHibernateLogger Log = NHibernateLogger.For(typeof(CacheBatcher));
internal CacheBatcher(ISessionImplementor session)
{
_session = session;
}
/// <summary>
/// Adds a put operation to the batch.
/// </summary>
/// <param name="persister">The entity persister.</param>
/// <param name="data">The data to put in the cache.</param>
internal void AddToBatch(IEntityPersister persister, CachePutData data)
{
if (Log.IsDebugEnabled())
{
Log.Debug("Adding a put operation to batch for entity {0} and key {1}", persister.EntityName, data.Key);
}
AddToBatch(persister.Cache, data);
}
/// <summary>
/// Adds a put operation to the batch.
/// </summary>
/// <param name="persister">The collection persister.</param>
/// <param name="data">The data to put in the cache.</param>
internal void AddToBatch(ICollectionPersister persister, CachePutData data)
{
if (Log.IsDebugEnabled())
{
Log.Debug("Adding a put operation to batch for collection role {0} and key {1}", persister.Role, data.Key);
}
AddToBatch(persister.Cache, data);
}
private void AddToBatch(ICacheConcurrencyStrategy cache, CachePutData data)
{
if (!_putBatches.TryGetValue(cache, out var cachePutBatch))
{
cachePutBatch = new CachePutBatch(_session, cache);
_putBatches.Add(cache, cachePutBatch);
}
cachePutBatch.Add(data);
}
/// <summary>
/// Executes the pending batches.
/// </summary>
internal void ExecuteBatch()
{
if (_putBatches.Count == 0)
{
return;
}
try
{
Stopwatch duration = null;
if (Log.IsDebugEnabled())
{
duration = Stopwatch.StartNew();
}
foreach (var batch in _putBatches.Values)
{
batch.Execute();
}
if (Log.IsDebugEnabled() && duration != null)
{
Log.Debug(
"ExecuteBatch for {0} batches totaling {1} keys took {2} ms",
_putBatches.Count, _putBatches.Values.Sum(b => b.BatchSize),
duration.ElapsedMilliseconds);
}
}
finally
{
Cleanup();
}
}
/// <summary>
/// Cleans up the current batch.
/// </summary>
internal void Cleanup()
{
_putBatches.Clear();
}
}
}