<commit_before>﻿using System;
using System.Collections.Concurrent;
using System.Threading;
using System.Threading.Tasks;
using System.Web.Hosting;
using Umbraco.Core.Events;
using Umbraco.Core.Logging;

namespace Umbraco.Web.Scheduling
{
    // exists for logging purposes
    internal class BackgroundTaskRunner
    { }

    /// <summary>
    /// Manages a queue of tasks of type <typeparamref name="T"/> and runs them in the background.
    /// </summary>
    /// <typeparam name="T">The type of the managed tasks.</typeparam>
    /// <remarks>The task runner is web-aware and will ensure that it shuts down correctly when the AppDomain
    /// shuts down (ie is unloaded).</remarks>
    internal class BackgroundTaskRunner<T> : BackgroundTaskRunner, IBackgroundTaskRunner<T>
        where T : class, IBackgroundTask
    {
        private readonly string _logPrefix;
        private readonly BackgroundTaskRunnerOptions _options;
        private readonly ILogger _logger;
        private readonly BlockingCollection<T> _tasks = new BlockingCollection<T>();
        private readonly object _locker = new object();
        private readonly ManualResetEventSlim _completedEvent = new ManualResetEventSlim(false);
        private BackgroundTaskRunnerAwaiter<T> _awaiter;

        private volatile bool _isRunning; // is running
        private volatile bool _isCompleted; // does not accept tasks anymore, may still be running
        private Task _runningTask;

        private CancellationTokenSource _tokenSource;

        internal event TypedEventHandler<BackgroundTaskRunner<T>, TaskEventArgs<T>> TaskError;
        internal event TypedEventHandler<BackgroundTaskRunner<T>, TaskEventArgs<T>> TaskStarting;
        internal event TypedEventHandler<BackgroundTaskRunner<T>, TaskEventArgs<T>> TaskCompleted;
        internal event TypedEventHandler<BackgroundTaskRunner<T>, TaskEventArgs<T>> TaskCancelled;
        
        // triggers when the runner stops (but could start again if a task is added to it)
        internal event TypedEventHandler<BackgroundTaskRunner<T>, EventArgs> Stopped;

        // triggers when the runner completes (no task can be added to it anymore)
        internal event TypedEventHandler<BackgroundTaskRunner<T>, EventArgs> Completed;

        /// <summary>
        /// Initializes a new instance of the <see cref="BackgroundTaskRunner{T}"/> class.
        /// </summary>
        public BackgroundTaskRunner(ILogger logger)
            : this(typeof (T).FullName, new BackgroundTaskRunnerOptions(), logger)
        { }

        /// <summary>
        /// Initializes a new instance of the <see cref="BackgroundTaskRunner{T}"/> class.
        /// </summary>
        /// <param name="name">The name of the runner.</param>
        public BackgroundTaskRunner(string name)
            : this(name, new BackgroundTaskRunnerOptions())
        { }

        /// <summary>
        /// Initializes a new instance of the <see cref="BackgroundTaskRunner{T}"/> class with a set of options.
        /// </summary>
        /// <param name="options">The set of options.</param>
        /// <param name="logger"></param>
        public BackgroundTaskRunner(BackgroundTaskRunnerOptions options, ILogger logger)
            : this(typeof (T).FullName, options, logger)
        { }

        /// <summary>
        /// Initializes a new instance of the <see cref="BackgroundTaskRunner{T}"/> class with a set of options.
        /// </summary>
        /// <param name="name">The name of the runner.</param>
        /// <param name="options">The set of options.</param>
        public BackgroundTaskRunner(string name, BackgroundTaskRunnerOptions options, ILogger logger)
        {
            if (options == null) throw new ArgumentNullException("options");
            if (logger == null) throw new ArgumentNullException("logger");
            _options = options;
            _logPrefix = "[" + name + "] ";
            _logger = logger;

            HostingEnvironment.RegisterObject(this);

            if (options.AutoStart)
                StartUp();
        }

        /// <summary>
        /// Gets the number of tasks in the queue.
        /// </summary>
        public int TaskCount
        {
            get { return _tasks.Count; }
        }<commit_msg>fixes merge issues<commit_after>﻿using System;
using System.Collections.Concurrent;
using System.Threading;
using System.Threading.Tasks;
using System.Web.Hosting;
using Umbraco.Core.Events;
using Umbraco.Core.Logging;

namespace Umbraco.Web.Scheduling
{
    // exists for logging purposes
    internal class BackgroundTaskRunner
    { }

    /// <summary>
    /// Manages a queue of tasks of type <typeparamref name="T"/> and runs them in the background.
    /// </summary>
    /// <typeparam name="T">The type of the managed tasks.</typeparam>
    /// <remarks>The task runner is web-aware and will ensure that it shuts down correctly when the AppDomain
    /// shuts down (ie is unloaded).</remarks>
    internal class BackgroundTaskRunner<T> : BackgroundTaskRunner, IBackgroundTaskRunner<T>
        where T : class, IBackgroundTask
    {
        private readonly string _logPrefix;
        private readonly BackgroundTaskRunnerOptions _options;
        private readonly ILogger _logger;
        private readonly BlockingCollection<T> _tasks = new BlockingCollection<T>();
        private readonly object _locker = new object();
        private readonly ManualResetEventSlim _completedEvent = new ManualResetEventSlim(false);
        private BackgroundTaskRunnerAwaiter<T> _awaiter;

        private volatile bool _isRunning; // is running
        private volatile bool _isCompleted; // does not accept tasks anymore, may still be running
        private Task _runningTask;

        private CancellationTokenSource _tokenSource;

        internal event TypedEventHandler<BackgroundTaskRunner<T>, TaskEventArgs<T>> TaskError;
        internal event TypedEventHandler<BackgroundTaskRunner<T>, TaskEventArgs<T>> TaskStarting;
        internal event TypedEventHandler<BackgroundTaskRunner<T>, TaskEventArgs<T>> TaskCompleted;
        internal event TypedEventHandler<BackgroundTaskRunner<T>, TaskEventArgs<T>> TaskCancelled;
        
        // triggers when the runner stops (but could start again if a task is added to it)
        internal event TypedEventHandler<BackgroundTaskRunner<T>, EventArgs> Stopped;

        // triggers when the runner completes (no task can be added to it anymore)
        internal event TypedEventHandler<BackgroundTaskRunner<T>, EventArgs> Completed;

        /// <summary>
        /// Initializes a new instance of the <see cref="BackgroundTaskRunner{T}"/> class.
        /// </summary>
        public BackgroundTaskRunner(ILogger logger)
            : this(typeof (T).FullName, new BackgroundTaskRunnerOptions(), logger)
        { }

        /// <summary>
        /// Initializes a new instance of the <see cref="BackgroundTaskRunner{T}"/> class.
        /// </summary>
        /// <param name="name">The name of the runner.</param>
        /// <param name="logger"></param>
        public BackgroundTaskRunner(string name, ILogger logger)
            : this(name, new BackgroundTaskRunnerOptions(), logger)
        { }

        /// <summary>
        /// Initializes a new instance of the <see cref="BackgroundTaskRunner{T}"/> class with a set of options.
        /// </summary>
        /// <param name="options">The set of options.</param>
        /// <param name="logger"></param>
        public BackgroundTaskRunner(BackgroundTaskRunnerOptions options, ILogger logger)
            : this(typeof (T).FullName, options, logger)
        { }

        /// <summary>
        /// Initializes a new instance of the <see cref="BackgroundTaskRunner{T}"/> class with a set of options.
        /// </summary>
        /// <param name="name">The name of the runner.</param>
        /// <param name="options">The set of options.</param>
        /// <param name="logger"></param>
        public BackgroundTaskRunner(string name, BackgroundTaskRunnerOptions options, ILogger logger)
        {
            if (options == null) throw new ArgumentNullException("options");
            if (logger == null) throw new ArgumentNullException("logger");
            _options = options;
            _logPrefix = "[" + name + "] ";
            _logger = logger;

            HostingEnvironment.RegisterObject(this);

            if (options.AutoStart)
                StartUp();
        }

        /// <summary>
        /// Gets the number of tasks in the queue.
        /// </summary>
        public int TaskCount
        {
            get { return _tasks.Count; }
        }
{'fraction_non_alphanumeric': 0.10123656535305674, 'fraction_numerical': 0.0, 'mean_word_length': 2.63919259882254, 'pattern_counts': {'":': 0, '<': 111, '<?xml version=': 0, '>': 111, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4223904', 'n_tokens_mistral': 2144, 'n_tokens_neox': 2133, 'n_words': 689}