Skip to content

Commit

Permalink
Memory leak fix..
Browse files Browse the repository at this point in the history
  • Loading branch information
Felix Clase committed Feb 5, 2024
1 parent 6503d06 commit 1ee6a3f
Show file tree
Hide file tree
Showing 6 changed files with 21 additions and 29 deletions.
18 changes: 8 additions & 10 deletions src/main/Hangfire.Storage.SQLite/HangfireSQLiteConnection.cs
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,12 @@ public HangfireSQLiteConnection(
_queueProviders = queueProviders ?? throw new ArgumentNullException(nameof(queueProviders));
}

public override void Dispose()
{
DbContext.Dispose();
base.Dispose();
}

public override IDisposable AcquireDistributedLock(string resource, TimeSpan timeout)
{
return Retry.Twice((_) =>
Expand Down Expand Up @@ -347,27 +353,19 @@ public override void Heartbeat(string serverId)
throw new ArgumentNullException(nameof(serverId));
}

// DANIEL WAS HERE:
// Something fishy is going on here, a BackgroundServerGoneException is unexpectedly thrown
// https://github.com/HangfireIO/Hangfire/blob/master/src/Hangfire.Core/Server/ServerHeartbeatProcess.cs
// Changing to

// DANIEL WAS HERE:
// var server = DbContext.HangfireServerRepository.FirstOrDefault(_ => _.Id == serverId);
var server = Retry.Twice((attempts) =>
// Forcing a query (read somewhere that sqlite-net handles FirstOrDefault differently )
DbContext.HangfireServerRepository.Where(_ => _.Id == serverId)
.ToArray()
.FirstOrDefault()
);

if (server == null)
throw new BackgroundServerGoneException();

server.LastHeartbeat = DateTime.UtcNow;

// DANIEL WAS HERE:
// var affected = DbContext.Database.Update(server);
var affected = Retry.Twice((_) => DbContext.Database.Update(server));

if (affected == 0)
throw new BackgroundServerGoneException();
}
Expand Down
11 changes: 2 additions & 9 deletions src/main/Hangfire.Storage.SQLite/SQLiteDistributedLock.cs
Original file line number Diff line number Diff line change
Expand Up @@ -176,31 +176,24 @@ private void Acquire(TimeSpan timeout)
/// <exception cref="DistributedLockTimeoutException"></exception>
private void Release()
{
// DANIEL WAS HERE:
Retry.Twice((retry) => {
// Remove resource lock (if it's still ours)
_dbContext.DistributedLockRepository.Delete(_ => _.Resource == _resource && _.ResourceKey == _resourceKey);
lock (EventWaitHandleName)
Monitor.Pulse(EventWaitHandleName);
}

);
});
}


private void Cleanup()
{
try
{
// DANIEL WAS HERE:
Retry.Twice((_) => {
// Delete expired locks (of any owner)
_dbContext.DistributedLockRepository.
Delete(x => x.Resource == _resource && x.ExpireAt < DateTime.UtcNow);
}
);
});
}
catch (Exception ex)
{
Expand Down
16 changes: 9 additions & 7 deletions src/main/Hangfire.Storage.SQLite/SQLiteMonitoringApi.cs
Original file line number Diff line number Diff line change
Expand Up @@ -12,25 +12,28 @@ namespace Hangfire.Storage.SQLite
{
public class SQLiteMonitoringApi : IMonitoringApi
{
private readonly HangfireDbContext _dbContext;
private readonly SQLiteStorage _storage;

private readonly PersistentJobQueueProviderCollection _queueProviders;

/// <summary>
///
/// </summary>
/// <param name="database"></param>
/// <param name="storage"></param>
/// <param name="queueProviders"></param>
public SQLiteMonitoringApi(HangfireDbContext database, PersistentJobQueueProviderCollection queueProviders)
public SQLiteMonitoringApi(SQLiteStorage storage, PersistentJobQueueProviderCollection queueProviders)
{
_dbContext = database;
_storage = storage;
_queueProviders = queueProviders;
}

private T UseConnection<T>(Func<HangfireDbContext, T> action)
{
var result = action(_dbContext);
return result;
using (var dbContext = _storage.CreateAndOpenConnection())
{
var result = action(dbContext);
return result;
}
}

private JobList<TDto> GetJobs<TDto>(HangfireDbContext connection, int from, int count, string stateName, Func<JobDetailedDto, Job, Dictionary<string, string>, TDto> selector)
Expand Down Expand Up @@ -414,7 +417,6 @@ public JobList<FetchedJobDto> FetchedJobs(string queue, int from, int perPage)
/// <returns></returns>
public StatisticsDto GetStatistics()
{
// DANIEL WAS HERE:
return Retry.Twice((attempts) =>
UseConnection(ctx =>
Expand Down
2 changes: 1 addition & 1 deletion src/main/Hangfire.Storage.SQLite/SQLiteStorage.cs
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,7 @@ public override IStorageConnection GetConnection()
public override IMonitoringApi GetMonitoringApi()
{
CheckDisposed();
return new SQLiteMonitoringApi(CreateAndOpenConnection(), QueueProviders);
return new SQLiteMonitoringApi(this, QueueProviders);
}

/// <summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,6 @@ public override void AddToSet(string key, string value, double score)

public override void Commit()
{
// DANIEL WAS HERE
Retry.Twice((attempts) => {
lock (_lockObject)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -283,7 +283,7 @@ public void ProcessingJobs_ReturnsProcessingJobsOnly_WhenMultipleJobsExistsInPro
private void UseMonitoringApi(Action<HangfireDbContext, SQLiteMonitoringApi> action)
{
using var storage = ConnectionUtils.CreateStorage();
var connection = new SQLiteMonitoringApi(storage.CreateAndOpenConnection(), _providers);
var connection = new SQLiteMonitoringApi(storage, _providers);
using var dbContext = storage.CreateAndOpenConnection();
action(dbContext, connection);
}
Expand Down

0 comments on commit 1ee6a3f

Please sign in to comment.