private IImmutableList <IActionProvider> CreateActionProvider(
            ActionParameterization action,
            IKustoManagementGatewayFactory kustoGatewayFactory,
            IFileGateway localFileGateway,
            AdxSourceParameterization?database)
        {
            var builder = ImmutableArray <IActionProvider> .Empty.ToBuilder();

            builder.Add(new ConsoleActionProvider(_tracer, !action.PushToConsole));

            if (action.FilePath != null)
            {
                builder.Add(new OneFileActionProvider(localFileGateway, action.FilePath));
            }
            if (action.FolderPath != null)
            {
                builder.Add(new MultiFilesActionProvider(localFileGateway, action.FolderPath));
            }
            if (action.CsvPath != null)
            {
                builder.Add(new CsvActionProvider(localFileGateway, action.CsvPath));
            }
            if (action.PushToCurrent)
            {
                var kustoManagementGateway = kustoGatewayFactory.CreateGateway(
                    new Uri(database !.ClusterUri !),
                    database !.Database !);

                builder.Add(new KustoActionProvider(kustoManagementGateway));
            }

            return(builder.ToImmutable());
        }
        private async Task <bool> ProcessJobAsync(
            MainParameterization parameters,
            IKustoManagementGatewayFactory kustoGatewayFactory,
            IFileGateway localFileGateway,
            string jobName,
            JobParameterization job)
        {
            _tracer.WriteLine(false, $"Job '{jobName}':");
            _tracer.WriteLine(false, "");
            try
            {
                _tracer.WriteLine(true, "Current DB Provider...  ");

                var currentDbProvider = CreateDatabaseProvider(job.Current, kustoGatewayFactory, localFileGateway);

                _tracer.WriteLine(true, "Target DB Provider...  ");

                var targetDbProvider = CreateDatabaseProvider(job.Target, kustoGatewayFactory, localFileGateway);

                var currentDbTask = RetrieveDatabaseAsync(currentDbProvider, "current");
                var targetDbTask  = RetrieveDatabaseAsync(targetDbProvider, "target");

                await Task.WhenAll(currentDbTask, targetDbTask);

                var currentDb = await currentDbTask;
                var targetDb  = await targetDbTask;

                _tracer.WriteLine(false, "Compute Delta...");

                var delta           = currentDb.ComputeDelta(targetDb);
                var actions         = new CommandCollection(job.Action !.UsePluralForms, delta);
                var jobSuccess      = ReportOnDeltaCommands(parameters, actions);
                var actionProviders = CreateActionProvider(
                    job.Action !,
                    kustoGatewayFactory,
                    localFileGateway,
                    job.Current?.Adx);

                _tracer.WriteLine(false, "Processing delta commands...");
                foreach (var actionProvider in actionProviders)
                {
                    await actionProvider.ProcessDeltaCommandsAsync(
                        parameters.FailIfDataLoss,
                        actions);
                }
                _tracer.WriteLine(false, "Delta processed / Job completed");
                _tracer.WriteLine(false, "");

                return(jobSuccess);
            }
            catch (DeltaException ex)
            {
                throw new DeltaException($"Issue in running job '{jobName}'", ex);
            }
        }
        private IDatabaseProvider CreateDatabaseProvider(
            SourceParameterization?source,
            IKustoManagementGatewayFactory kustoGatewayFactory,
            IFileGateway localFileGateway)
        {
            if (source == null)
            {
                _tracer.WriteLine(true, "Empty database");

                return(new EmptyDatabaseProvider());
            }
            else
            {
                if (source.Adx != null)
                {
                    _tracer.WriteLine(
                        true,
                        $"ADX Database:  cluster '{source.Adx.ClusterUri}', "
                        + $"database '{source.Adx.Database}'");

                    var kustoManagementGateway = kustoGatewayFactory.CreateGateway(
                        new Uri(source.Adx.ClusterUri !),
                        source.Adx.Database !);

                    return(new KustoDatabaseProvider(_tracer, kustoManagementGateway));
                }
                else if (source.Scripts != null)
                {
                    _tracer.WriteLine(true, "Database scripts");

                    return(new ScriptDatabaseProvider(_tracer, localFileGateway, source.Scripts));
                }
                else
                {
                    throw new InvalidOperationException("We should never get here");
                }
            }
        }