< Summary

Information
Class: GistBackend.Utils.GistDebouncer
Assembly: GistBackend
File(s): /home/runner/work/the-gist-of-it-sec/the-gist-of-it-sec/backend/GistBackend/Utils/GistDebouncer.cs
Line coverage
100%
Covered lines: 22
Uncovered lines: 0
Coverable lines: 22
Total lines: 51
Line coverage: 100%
Branch coverage
100%
Covered branches: 12
Total branches: 12
Branch coverage: 100%
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity Line coverage
.ctor(...)100%11100%
.cctor()100%11100%
IsReady(...)100%44100%
DebounceGist(...)100%11100%
CalculateReadyTime(...)100%88100%

File(s)

/home/runner/work/the-gist-of-it-sec/the-gist-of-it-sec/backend/GistBackend/Utils/GistDebouncer.cs

#LineLine coverage
 1using GistBackend.Handlers;
 2
 3namespace GistBackend.Utils;
 4
 5public interface IGistDebouncer
 6{
 7    bool IsReady(int gistId, DateTime updated);
 8}
 9
 1110public class GistDebouncer(IDateTimeHandler dateTimeHandler) : IGistDebouncer
 11{
 1112    private readonly Dictionary<int, DateTime> _readyTimesByGistId = new();
 113    private static readonly Random Random = new();
 14
 15    public bool IsReady(int gistId, DateTime updated)
 16    {
 2117        if (_readyTimesByGistId.TryGetValue(gistId, out var readyTime))
 18        {
 1519            if (readyTime > dateTimeHandler.GetUtcNow()) return false;
 520            DebounceGist(gistId, updated);
 521            return true;
 22        }
 1123        DebounceGist(gistId, updated);
 1124        return false;
 25    }
 26
 27    private void DebounceGist(int gistId, DateTime updated)
 28    {
 1629        _readyTimesByGistId[gistId] = CalculateReadyTime(updated);
 1630    }
 31
 32    private DateTime CalculateReadyTime(DateTime updated)
 33    {
 1634        var now = dateTimeHandler.GetUtcNow();
 1635        var age = now - updated;
 36
 37        TimeSpan meanDebounceDuration;
 1838        if (age < TimeSpan.FromHours(1)) meanDebounceDuration = TimeSpan.FromMinutes(30);
 1939        else if (age < TimeSpan.FromHours(6)) meanDebounceDuration = TimeSpan.FromHours(1);
 1240        else if (age < TimeSpan.FromDays(1)) meanDebounceDuration = TimeSpan.FromHours(3);
 941        else if (age < TimeSpan.FromDays(7)) meanDebounceDuration = TimeSpan.FromHours(6);
 342        else meanDebounceDuration = TimeSpan.FromDays(1);
 43
 44        // Generate random jitter between -meanDebounceDuration/2 and +meanDebounceDuration/2
 1645        var halfDuration = meanDebounceDuration / 2;
 1646        var randomFactor = Random.NextDouble() * 2 - 1; // [-1, 1]
 1647        var jitter = halfDuration * randomFactor;
 48
 1649        return now + meanDebounceDuration + jitter;
 50    }
 51}