예제 #1
0
        public virtual Task <TimeSpan> GetUptimeAsync(TimeSpan updatePeriod, CancellationToken cancellationToken = default)
        {
            var computed = Computed.GetCurrent();

            Task.Delay(updatePeriod, cancellationToken).ContinueWith(_ => computed !.Invalidate(), cancellationToken);
            return(Task.FromResult(DateTime.UtcNow - _startTime));
        }
예제 #2
0
        public virtual Task <string> GetMomentsAgo(DateTime time)
        {
            // TODO: Make this method stop leaking some memory due to timers that don't die unless timeout
            var delta = DateTime.UtcNow - time.DefaultKind(DateTimeKind.Utc).ToUniversalTime();

            if (delta < TimeSpan.Zero)
            {
                delta = TimeSpan.Zero;
            }
            var(unit, unitName) = GetMomentsAgoUnit(delta);
            var    unitCount = (int)(delta.TotalSeconds / unit.TotalSeconds);
            string result;

            if (unitCount == 0 && unit == TimeSpan.FromSeconds(1))
            {
                result = $"just now";
            }
            else
            {
                var pluralizedUnitName = Pluralize.Format(unitName, unitCount);
                result = $"{unitCount} {pluralizedUnitName} ago";
            }

            // Invalidate the result when it's supposed to change
            var delay = TrimInvalidationDelay((unitCount + 1) * unit - delta + TimeSpan.FromMilliseconds(100));

            Computed.GetCurrent() !.Invalidate(delay, false);
            return(Task.FromResult(result));
        }
예제 #3
0
        public virtual Task <double> GetUptime(double updatePeriod, CancellationToken cancellationToken = default)
        {
            var computed = Computed.GetCurrent();

            Task.Delay(TimeSpan.FromSeconds(updatePeriod), default)
            .ContinueWith(_ => computed !.Invalidate(), CancellationToken.None);
            return(Task.FromResult((DateTime.UtcNow - _startTime).TotalSeconds));
        }
예제 #4
0
파일: TimeService.cs 프로젝트: mrHBH/About
        public virtual Task <TimeSpan> GetUptimeAsync(TimeSpan updatePeriod, CancellationToken cancellationToken = default)
        {
            var computed = Computed.GetCurrent();
            var time     = DateTime.UtcNow;

            time = time.AddYears(100);
            //time.Days += 42;
            Task.Delay(updatePeriod, default)
            .ContinueWith(_ => computed !.Invalidate(), CancellationToken.None);
            return(Task.FromResult(time - _startTime));
        }
예제 #5
0
        public virtual Task <long> GetActiveUserCountAsync(CancellationToken cancellationToken = default)
        {
            var channelHub = _publisher.ChannelHub;
            var userCount  = (long)channelHub.ChannelCount;
            var c          = Computed.GetCurrent();

            Task.Run(async() => {
                do
                {
                    await Task.Delay(1000, default).ConfigureAwait(false);
                } while (userCount == channelHub.ChannelCount);
                c !.Invalidate();
            }, default).Ignore();
예제 #6
0
            public virtual async Task <DateTime> GetTimeAsync()
            {
                WriteLine($"* {nameof(GetTimeAsync)}()");
                // That's how you "pull" the computed that is going to
                // store the result of this computation
                var computed = Computed.GetCurrent();

                // We just start this task here, but don't await for its result
                Task.Delay(TimeSpan.FromSeconds(0.1)).ContinueWith(_ => {
                    computed !.Invalidate();
                    WriteLine($"! {nameof(GetTimeAsync)}() -> invalidated");
                }).Ignore();
                return(DateTime.Now);
            }
예제 #7
0
        public virtual async Task <bool> DeleteAsync(User user, CancellationToken cancellationToken = default)
        {
            Computed.GetCurrent().Should().BeNull();
            await using var dbContext = DbContextFactory.CreateDbContext();
            dbContext.Users.Remove(user);
            try {
                await dbContext.SaveChangesAsync(cancellationToken).ConfigureAwait(false);

                Invalidate(user);
                return(true);
            }
            catch (DbUpdateConcurrencyException) {
                return(false);
            }
        }
    protected virtual Task <DirectBitmap> GetScreenshot(CancellationToken cancellationToken = default)
    {
        // Captures a full-resolution screenshot; the code here is optimized
        // to produce the next screenshot in advance & instantly return the prev. one.
        var currentProducer = Task.Run(TakeScreenshot, default);
        var prevProducer    = Interlocked.Exchange(ref _currentProducer, currentProducer) ?? currentProducer;

        Computed.GetCurrent() !.Invalidated += c => Task.Delay(1000).ContinueWith(_ => {
            // Let's dispose the bitmap in 1 second after invalidation
            var computed = (IComputed <DirectBitmap>)c;
            if (computed.HasValue)
            {
                computed.Value.Dispose();
            }
        });
        return(prevProducer);
    }
        protected virtual Task <Bitmap> GetScreenshotAsync(CancellationToken cancellationToken = default)
        {
            // This method takes a full-resolution screenshot
            var(w, h) = (_displayDimensions.Width, _displayDimensions.Height);
            var bScreen = new Bitmap(w, h);

            using var gScreen = Graphics.FromImage(bScreen);
            gScreen.CopyFromScreen(0, 0, 0, 0, bScreen.Size);
            Computed.GetCurrent() !.Invalidated += c => Task.Delay(2000).ContinueWith(_ => {
                // Let's dispose these values in 2 seconds
                var computed = (IComputed <Bitmap>)c;
                if (computed.HasValue)
                {
                    computed.Value.Dispose();
                }
            });
            return(Task.FromResult(bScreen));
        }
        public virtual Task <string> GetMomentsAgoAsync(DateTime time)
        {
            var delta = Clock.Now.ToDateTime() - time;

            if (delta < TimeSpan.Zero)
            {
                delta = TimeSpan.Zero;
            }
            var(unit, unitName) = GetMomentsAgoUnit(delta);
            var unitCount          = (int)(delta.TotalSeconds / unit.TotalSeconds);
            var pluralizedUnitName = Pluralize.Format(unitName, unitCount);
            var result             = $"{unitCount} {pluralizedUnitName} ago";

            // Invalidate the result when it's supposed to change
            var delay    = (unitCount + 1) * unit - delta;
            var computed = Computed.GetCurrent();

            Task.Delay(delay, default).ContinueWith(_ => computed !.Invalidate()).Ignore();

            return(Task.FromResult(result));
        }
        protected override Action <IInvocation> CreateHandler <T>(
            IInvocation initialInvocation, MethodDef methodDef)
        {
            var computeMethodDef = (ComputeMethodDef)methodDef;
            var function         = CreateFunction <T>(computeMethodDef);

            return(invocation => {
                var input = computeMethodDef.CreateInput(function, (AbstractInvocation)invocation);
                var arguments = input.Arguments;
                var cancellationTokenIndex = computeMethodDef.CancellationTokenArgumentIndex;
                var cancellationToken = cancellationTokenIndex >= 0
                    ? (CancellationToken)arguments[cancellationTokenIndex]
                    : default;

                // Invoking the function
                var usedBy = Computed.GetCurrent();

                // InvokeAndStripAsync allows to get rid of one extra allocation
                // of a task stripping the result of regular InvokeAsync.
                var task = function.InvokeAndStripAsync(input, usedBy, null, cancellationToken);
                if (cancellationTokenIndex >= 0)
                {
                    // We don't want memory leaks + unexpected cancellation later
                    arguments[cancellationTokenIndex] = NoCancellationTokenBoxed;
                }

                if (methodDef.ReturnsValueTask)
                {
                    // ReSharper disable once HeapView.BoxingAllocation
                    invocation.ReturnValue = new ValueTask <T>(task);
                }
                else
                {
                    invocation.ReturnValue = task;
                }
            });
        }
예제 #12
0
 public virtual Task <DateTime> GetUtcNow(TimeSpan updatePeriod)
 {
     Computed.GetCurrent() !.Invalidate(TrimInvalidationDelay(updatePeriod));
     return(Task.FromResult(Clock.Now.ToDateTime()));
 }