Example #1
0
        // key goal is to create background tracer that is independent of request.
        public static void PerformBackgroundDeployment(DeploymentInfo deployInfo, IEnvironment environment, IDeploymentSettingsManager settings, TraceLevel traceLevel, Uri uri)
        {
            var tracer       = traceLevel <= TraceLevel.Off ? NullTracer.Instance : new XmlTracer(environment.TracePath, traceLevel);
            var traceFactory = new TracerFactory(() => tracer);

            var backgroundTrace = tracer.Step(XmlTracer.BackgroundTrace, new Dictionary <string, string>
            {
                { "url", uri.AbsolutePath },
                { "method", "POST" }
            });

            Task.Run(() =>
            {
                try
                {
                    // lock related
                    string lockPath           = Path.Combine(environment.SiteRootPath, Constants.LockPath);
                    string deploymentLockPath = Path.Combine(lockPath, Constants.DeploymentLockFile);
                    string statusLockPath     = Path.Combine(lockPath, Constants.StatusLockFile);
                    string hooksLockPath      = Path.Combine(lockPath, Constants.HooksLockFile);
                    var statusLock            = new LockFile(statusLockPath, traceFactory);
                    var hooksLock             = new LockFile(hooksLockPath, traceFactory);
                    var deploymentLock        = new DeploymentLockFile(deploymentLockPath, traceFactory);

                    var analytics = new Analytics(settings, new ServerConfiguration(), traceFactory);
                    var deploymentStatusManager = new DeploymentStatusManager(environment, analytics, statusLock);
                    var repositoryFactory       = new RepositoryFactory(environment, settings, traceFactory);
                    var siteBuilderFactory      = new SiteBuilderFactory(new BuildPropertyProvider(), environment);
                    var webHooksManager         = new WebHooksManager(tracer, environment, hooksLock);
                    var deploymentManager       = new DeploymentManager(siteBuilderFactory, environment, traceFactory, analytics, settings, deploymentStatusManager, deploymentLock, NullLogger.Instance, webHooksManager);
                    var fetchHandler            = new FetchHandler(tracer, deploymentManager, settings, deploymentStatusManager, deploymentLock, environment, null, repositoryFactory, null);

                    // Perform deployment
                    var acquired = deploymentLock.TryLockOperation(() =>
                    {
                        fetchHandler.PerformDeployment(deployInfo).Wait();
                    }, TimeSpan.Zero);

                    if (!acquired)
                    {
                        using (tracer.Step("Update pending deployment marker file"))
                        {
                            // REVIEW: This makes the assumption that the repository url is the same.
                            // If it isn't the result would be buggy either way.
                            FileSystemHelpers.SetLastWriteTimeUtc(fetchHandler._markerFilePath, DateTime.UtcNow);
                        }
                    }
                }
                catch (Exception ex)
                {
                    tracer.TraceError(ex);
                }
                finally
                {
                    backgroundTrace.Dispose();
                }
            });
        }
        public void EnsureCorrectPriorityOfOverridesWhenCreatingBuilder(
            IDeploymentSettingsManager settings,
            IRepository repository,
            Type expectedBuilderType)
        {
            var environment = Mock.Of <IEnvironment>();
            var pProvider   = Mock.Of <IBuildPropertyProvider>();
            var tracer      = Mock.Of <ITracer>();
            var logger      = Mock.Of <ILogger>();

            var factory = new SiteBuilderFactory(pProvider, environment);

            var result = factory.CreateBuilder(tracer, logger, settings, repository);

            Assert.IsType(expectedBuilderType, result);
        }
Example #3
0
        private static int PerformDeploy(
            string appRoot,
            string wapTargets,
            string deployer,
            string lockPath,
            IEnvironment env,
            IDeploymentSettingsManager settingsManager,
            TraceLevel level,
            ITracer tracer,
            ITraceFactory traceFactory,
            IOperationLock deploymentLock)
        {
            System.Environment.SetEnvironmentVariable("GIT_DIR", null, System.EnvironmentVariableTarget.Process);

            // Skip SSL Certificate Validate
            OperationClient.SkipSslValidationIfNeeded();

            // Adjust repo path
            env.RepositoryPath = Path.Combine(env.SiteRootPath, settingsManager.GetRepositoryPath());

            string statusLockPath = Path.Combine(lockPath, Constants.StatusLockFile);
            string hooksLockPath = Path.Combine(lockPath, Constants.HooksLockFile);

            IOperationLock statusLock = new LockFile(statusLockPath, traceFactory);
            IOperationLock hooksLock = new LockFile(hooksLockPath, traceFactory);

            IBuildPropertyProvider buildPropertyProvider = new BuildPropertyProvider();
            ISiteBuilderFactory builderFactory = new SiteBuilderFactory(buildPropertyProvider, env);
            var logger = new ConsoleLogger();

            IRepository gitRepository;
            if (settingsManager.UseLibGit2SharpRepository())
            {
                gitRepository = new LibGit2SharpRepository(env, settingsManager, traceFactory);
            }
            else
            {
                gitRepository = new GitExeRepository(env, settingsManager, traceFactory);
            }

            IServerConfiguration serverConfiguration = new ServerConfiguration();
            IAnalytics analytics = new Analytics(settingsManager, serverConfiguration, traceFactory);

            IWebHooksManager hooksManager = new WebHooksManager(tracer, env, hooksLock);
            IDeploymentStatusManager deploymentStatusManager = new DeploymentStatusManager(env, analytics, statusLock);
            IAutoSwapHandler autoSwapHander = new AutoSwapHandler(env, settingsManager, traceFactory);
            var functionManager = new FunctionManager(env, traceFactory);
            IDeploymentManager deploymentManager = new DeploymentManager(builderFactory,
                                                          env,
                                                          traceFactory,
                                                          analytics,
                                                          settingsManager,
                                                          deploymentStatusManager,
                                                          deploymentLock,
                                                          GetLogger(env, level, logger),
                                                          hooksManager,
                                                          functionManager);

            var step = tracer.Step(XmlTracer.ExecutingExternalProcessTrace, new Dictionary<string, string>
            {
                { "type", "process" },
                { "path", "kudu.exe" },
                { "arguments", appRoot + " " + wapTargets }
            });

            using (step)
            {
                try
                {
                    deploymentManager.DeployAsync(gitRepository, changeSet: null, deployer: deployer, clean: false)
                        .Wait();

                    string branch = settingsManager.GetBranch();
                    ChangeSet changeSet = gitRepository.GetChangeSet(branch);
                    IDeploymentStatusFile statusFile = deploymentStatusManager.Open(changeSet.Id);
                    if (statusFile != null && statusFile.Status == DeployStatus.Success)
                    {
                        autoSwapHander.HandleAutoSwap(changeSet.Id, deploymentManager.GetLogger(changeSet.Id), tracer).Wait();
                    }
                }
                catch (Exception e)
                {
                    tracer.TraceError(e);

                    System.Console.Error.WriteLine(e.GetBaseException().Message);
                    System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                    return 1;
                }
            }

            if (logger.HasErrors)
            {
                System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                return 1;
            }

            return 0;
        }
Example #4
0
        static int Main(string[] args)
        {
            // Turn flag on in app.config to wait for debugger on launch
            if (ConfigurationManager.AppSettings["WaitForDebuggerOnStart"] == "true")
            {
                while (!Debugger.IsAttached)
                {
                    System.Threading.Thread.Sleep(100);
                }
            }

            if (args.Length < 2)
            {
                System.Console.WriteLine("Usage: kudu.exe appRoot wapTargets [deployer]");
                return 1;
            }

            // The post receive hook launches the exe from sh and intereprets newline differently.
            // This fixes very wacky issues with how the output shows up in the conosle on push
            System.Console.Error.NewLine = "\n";
            System.Console.Out.NewLine = "\n";

            System.Environment.SetEnvironmentVariable("GIT_DIR", null, System.EnvironmentVariableTarget.Process);

            string appRoot = args[0];
            string wapTargets = args[1];
            string deployer = args.Length == 2 ? null : args[2];

            IEnvironment env = GetEnvironment(appRoot);
            ISettings settings = new XmlSettings.Settings(GetSettingsPath(env));
            IDeploymentSettingsManager settingsManager = new DeploymentSettingsManager(settings);

            // Adjust repo path
            env.RepositoryPath = Path.Combine(env.SiteRootPath, settingsManager.GetRepositoryPath());

            // Setup the trace
            IFileSystem fileSystem = new FileSystem();
            TraceLevel level = settingsManager.GetTraceLevel();
            ITracer tracer = GetTracer(env, level, fileSystem);
            ITraceFactory traceFactory = new TracerFactory(() => tracer);

            // Calculate the lock path
            string lockPath = Path.Combine(env.SiteRootPath, Constants.LockPath);
            string deploymentLockPath = Path.Combine(lockPath, Constants.DeploymentLockFile);
            string statusLockPath = Path.Combine(lockPath, Constants.StatusLockFile);
            IOperationLock deploymentLock = new LockFile(deploymentLockPath, traceFactory, fileSystem);
            IOperationLock statusLock = new LockFile(statusLockPath, traceFactory, fileSystem);

            IBuildPropertyProvider buildPropertyProvider = new BuildPropertyProvider();
            ISiteBuilderFactory builderFactory = new SiteBuilderFactory(buildPropertyProvider, env);

            IRepository gitRepository = new GitExeRepository(env, settingsManager, traceFactory);

            var logger = new ConsoleLogger();
            IDeploymentManager deploymentManager = new DeploymentManager(builderFactory,
                                                          env, 
                                                          fileSystem, 
                                                          traceFactory, 
                                                          settingsManager,
                                                          new DeploymentStatusManager(env, fileSystem, statusLock),
                                                          deploymentLock,
                                                          GetLogger(env, level, logger));

            var step = tracer.Step("Executing external process", new Dictionary<string, string>
            {
                { "type", "process" },
                { "path", "kudu.exe" },
                { "arguments", appRoot + " " + wapTargets }
            });

            using (step)
            {
                try
                {
                    deploymentManager.Deploy(gitRepository, changeSet: null, deployer: deployer, clean: false);
                }
                catch (Exception e)
                {
                    System.Console.Error.WriteLine(e.Message);
                    System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                    return 1;
                }
            }

            if (logger.HasErrors)
            {
                System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                return 1;
            }

            return 0;
        }
Example #5
0
        private static int Main(string[] args)
        {
            // Turn flag on in app.config to wait for debugger on launch
            if (ConfigurationManager.AppSettings["WaitForDebuggerOnStart"] == "true")
            {
                while (!Debugger.IsAttached)
                {
                    System.Threading.Thread.Sleep(100);
                }
            }

            if (System.Environment.GetEnvironmentVariable(SettingsKeys.DisableDeploymentOnPush) == "1")
            {
                return(0);
            }

            if (args.Length < 2)
            {
                System.Console.WriteLine("Usage: kudu.exe appRoot wapTargets [deployer]");
                return(1);
            }

            // The post receive hook launches the exe from sh and intereprets newline differently.
            // This fixes very wacky issues with how the output shows up in the console on push
            System.Console.Error.NewLine = "\n";
            System.Console.Out.NewLine   = "\n";

            System.Environment.SetEnvironmentVariable("GIT_DIR", null, System.EnvironmentVariableTarget.Process);

            // Skip SSL Certificate Validate
            OperationClient.SkipSslValidationIfNeeded();

            string appRoot    = args[0];
            string wapTargets = args[1];
            string deployer   = args.Length == 2 ? null : args[2];

            IEnvironment env      = GetEnvironment(appRoot);
            ISettings    settings = new XmlSettings.Settings(GetSettingsPath(env));
            IDeploymentSettingsManager settingsManager = new DeploymentSettingsManager(settings);

            // Adjust repo path
            env.RepositoryPath = Path.Combine(env.SiteRootPath, settingsManager.GetRepositoryPath());

            // Setup the trace
            TraceLevel    level        = settingsManager.GetTraceLevel();
            ITracer       tracer       = GetTracer(env, level);
            ITraceFactory traceFactory = new TracerFactory(() => tracer);

            // Calculate the lock path
            string lockPath           = Path.Combine(env.SiteRootPath, Constants.LockPath);
            string deploymentLockPath = Path.Combine(lockPath, Constants.DeploymentLockFile);
            string statusLockPath     = Path.Combine(lockPath, Constants.StatusLockFile);
            string hooksLockPath      = Path.Combine(lockPath, Constants.HooksLockFile);

            IOperationLock deploymentLock = new LockFile(deploymentLockPath, traceFactory);
            IOperationLock statusLock     = new LockFile(statusLockPath, traceFactory);
            IOperationLock hooksLock      = new LockFile(hooksLockPath, traceFactory);

            IBuildPropertyProvider buildPropertyProvider = new BuildPropertyProvider();
            ISiteBuilderFactory    builderFactory        = new SiteBuilderFactory(buildPropertyProvider, env);

            IRepository gitRepository;

            if (settingsManager.UseLibGit2SharpRepository())
            {
                gitRepository = new LibGit2SharpRepository(env, settingsManager, traceFactory);
            }
            else
            {
                gitRepository = new GitExeRepository(env, settingsManager, traceFactory);
            }

            IServerConfiguration serverConfiguration = new ServerConfiguration();
            IAnalytics           analytics           = new Analytics(settingsManager, serverConfiguration, traceFactory);

            IWebHooksManager         hooksManager            = new WebHooksManager(tracer, env, hooksLock);
            IDeploymentStatusManager deploymentStatusManager = new DeploymentStatusManager(env, analytics, statusLock);
            IAutoSwapHandler         autoSwapHander          = new AutoSwapHandler(deploymentStatusManager, env, settingsManager, traceFactory);
            var functionManager = new FunctionManager(env, traceFactory);
            var logger          = new ConsoleLogger();
            IDeploymentManager deploymentManager = new DeploymentManager(builderFactory,
                                                                         env,
                                                                         traceFactory,
                                                                         analytics,
                                                                         settingsManager,
                                                                         deploymentStatusManager,
                                                                         deploymentLock,
                                                                         GetLogger(env, level, logger),
                                                                         hooksManager,
                                                                         autoSwapHander,
                                                                         functionManager);

            var step = tracer.Step(XmlTracer.ExecutingExternalProcessTrace, new Dictionary <string, string>
            {
                { "type", "process" },
                { "path", "kudu.exe" },
                { "arguments", appRoot + " " + wapTargets }
            });

            using (step)
            {
                try
                {
                    deploymentManager.DeployAsync(gitRepository, changeSet: null, deployer: deployer, clean: false)
                    .Wait();
                }
                catch (Exception e)
                {
                    tracer.TraceError(e);

                    System.Console.Error.WriteLine(e.GetBaseException().Message);
                    System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                    return(1);
                }
            }

            if (logger.HasErrors)
            {
                System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                return(1);
            }

            return(0);
        }
Example #6
0
        private static int PerformDeploy(
            string appRoot,
            string wapTargets,
            string deployer,
            string lockPath,
            IEnvironment env,
            IDeploymentSettingsManager settingsManager,
            TraceLevel level,
            ITracer tracer,
            ITraceFactory traceFactory,
            IOperationLock deploymentLock)
        {
            System.Environment.SetEnvironmentVariable("GIT_DIR", null, System.EnvironmentVariableTarget.Process);

            // Skip SSL Certificate Validate
            if (System.Environment.GetEnvironmentVariable(SettingsKeys.SkipSslValidation) == "1")
            {
                ServicePointManager.ServerCertificateValidationCallback = delegate { return(true); };
            }

            // Adjust repo path
            env.RepositoryPath = Path.Combine(env.SiteRootPath, settingsManager.GetRepositoryPath());

            string statusLockPath = Path.Combine(lockPath, Constants.StatusLockFile);
            string hooksLockPath  = Path.Combine(lockPath, Constants.HooksLockFile);

            IOperationLock statusLock = new LockFile(statusLockPath, traceFactory);
            IOperationLock hooksLock  = new LockFile(hooksLockPath, traceFactory);

            IBuildPropertyProvider buildPropertyProvider = new BuildPropertyProvider();
            ISiteBuilderFactory    builderFactory        = new SiteBuilderFactory(buildPropertyProvider, env);
            var logger = new ConsoleLogger();

            IRepository gitRepository;

            if (settingsManager.UseLibGit2SharpRepository())
            {
                gitRepository = new LibGit2SharpRepository(env, settingsManager, traceFactory);
            }
            else
            {
                gitRepository = new GitExeRepository(env, settingsManager, traceFactory);
            }

            IServerConfiguration serverConfiguration = new ServerConfiguration();
            IAnalytics           analytics           = new Analytics(settingsManager, serverConfiguration, traceFactory);

            IWebHooksManager         hooksManager            = new WebHooksManager(tracer, env, hooksLock);
            IDeploymentStatusManager deploymentStatusManager = new DeploymentStatusManager(env, analytics, statusLock);
            IDeploymentManager       deploymentManager       = new DeploymentManager(builderFactory,
                                                                                     env,
                                                                                     traceFactory,
                                                                                     analytics,
                                                                                     settingsManager,
                                                                                     deploymentStatusManager,
                                                                                     deploymentLock,
                                                                                     GetLogger(env, level, logger),
                                                                                     hooksManager);

            var step = tracer.Step(XmlTracer.ExecutingExternalProcessTrace, new Dictionary <string, string>
            {
                { "type", "process" },
                { "path", "kudu.exe" },
                { "arguments", appRoot + " " + wapTargets }
            });

            using (step)
            {
                try
                {
                    // although the api is called DeployAsync, most expensive works are done synchronously.
                    // need to launch separate task to go async explicitly (consistent with FetchDeploymentManager)
                    var deploymentTask = Task.Run(async() => await deploymentManager.DeployAsync(gitRepository, changeSet: null, deployer: deployer, clean: false));

#pragma warning disable 4014
                    // Track pending task
                    PostDeploymentHelper.TrackPendingOperation(deploymentTask, TimeSpan.Zero);
#pragma warning restore 4014

                    deploymentTask.Wait();

                    if (PostDeploymentHelper.IsAutoSwapEnabled())
                    {
                        string                branch     = settingsManager.GetBranch();
                        ChangeSet             changeSet  = gitRepository.GetChangeSet(branch);
                        IDeploymentStatusFile statusFile = deploymentStatusManager.Open(changeSet.Id);
                        if (statusFile != null && statusFile.Status == DeployStatus.Success)
                        {
                            PostDeploymentHelper.PerformAutoSwap(env.RequestId, new PostDeploymentTraceListener(tracer, deploymentManager.GetLogger(changeSet.Id))).Wait();
                        }
                    }
                }
                catch (Exception e)
                {
                    tracer.TraceError(e);

                    System.Console.Error.WriteLine(e.GetBaseException().Message);
                    System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                    return(1);
                }
            }

            if (logger.HasErrors)
            {
                System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                return(1);
            }

            return(0);
        }
Example #7
0
        // key goal is to create background tracer that is independent of request.
        public static void PerformBackgroundDeployment(DeploymentInfo deployInfo, IEnvironment environment, IDeploymentSettingsManager settings, TraceLevel traceLevel, Uri uri, IDisposable tempDeployment, IAutoSwapHandler autoSwapHandler, ChangeSet tempChangeSet)
        {
            var tracer = traceLevel <= TraceLevel.Off ? NullTracer.Instance : new XmlTracer(environment.TracePath, traceLevel);
            var traceFactory = new TracerFactory(() => tracer);

            var backgroundTrace = tracer.Step(XmlTracer.BackgroundTrace, new Dictionary<string, string>
            {
                {"url", uri.AbsolutePath},
                {"method", "POST"}
            });

            Task.Run(() =>
            {
                try
                {
                    // lock related
                    string lockPath = Path.Combine(environment.SiteRootPath, Constants.LockPath);
                    string deploymentLockPath = Path.Combine(lockPath, Constants.DeploymentLockFile);
                    string statusLockPath = Path.Combine(lockPath, Constants.StatusLockFile);
                    string hooksLockPath = Path.Combine(lockPath, Constants.HooksLockFile);
                    var statusLock = new LockFile(statusLockPath, traceFactory);
                    var hooksLock = new LockFile(hooksLockPath, traceFactory);
                    var deploymentLock = new DeploymentLockFile(deploymentLockPath, traceFactory);

                    var analytics = new Analytics(settings, new ServerConfiguration(), traceFactory);
                    var deploymentStatusManager = new DeploymentStatusManager(environment, analytics, statusLock);
                    var repositoryFactory = new RepositoryFactory(environment, settings, traceFactory);
                    var siteBuilderFactory = new SiteBuilderFactory(new BuildPropertyProvider(), environment);
                    var webHooksManager = new WebHooksManager(tracer, environment, hooksLock);
                    var functionManager = new FunctionManager(environment, traceFactory);
                    var deploymentManager = new DeploymentManager(siteBuilderFactory, environment, traceFactory, analytics, settings, deploymentStatusManager, deploymentLock, NullLogger.Instance, webHooksManager, autoSwapHandler, functionManager);
                    var fetchHandler = new FetchHandler(tracer, deploymentManager, settings, deploymentStatusManager, deploymentLock, environment, null, repositoryFactory, null);

                    // Perform deployment
                    var acquired = deploymentLock.TryLockOperation(() =>
                    {
                        fetchHandler.PerformDeployment(deployInfo, tempDeployment, tempChangeSet).Wait();
                    }, TimeSpan.Zero);

                    if (!acquired)
                    {
                        if (tempDeployment != null)
                        {
                            tempDeployment.Dispose();
                        }

                        using (tracer.Step("Update pending deployment marker file"))
                        {
                            // REVIEW: This makes the assumption that the repository url is the same.
                            // If it isn't the result would be buggy either way.
                            FileSystemHelpers.SetLastWriteTimeUtc(fetchHandler._markerFilePath, DateTime.UtcNow);
                        }
                    }
                }
                catch (Exception ex)
                {
                    tracer.TraceError(ex);
                }
                finally
                {
                    backgroundTrace.Dispose();
                }
            });
        }
Example #8
0
        // key goal is to create background tracer that is independent of request.
        public static async Task PerformBackgroundDeployment(
            DeploymentInfo deployInfo,
            IEnvironment environment,
            IDeploymentSettingsManager settings,
            TraceLevel traceLevel,
            Uri uri,
            bool waitForTempDeploymentCreation)
        {
            var tracer       = traceLevel <= TraceLevel.Off ? NullTracer.Instance : new CascadeTracer(new XmlTracer(environment.TracePath, traceLevel), new ETWTracer(environment.RequestId, "POST"));
            var traceFactory = new TracerFactory(() => tracer);

            var backgroundTrace = tracer.Step(XmlTracer.BackgroundTrace, new Dictionary <string, string>
            {
                { "url", uri.AbsolutePath },
                { "method", "POST" }
            });

            // For monitoring creation of temp deployment
            var tcs = new TaskCompletionSource <object>();

            // This task will be let out of scope intentionally
            var deploymentTask = Task.Run(() =>
            {
                try
                {
                    // lock related
                    string lockPath           = Path.Combine(environment.SiteRootPath, Constants.LockPath);
                    string deploymentLockPath = Path.Combine(lockPath, Constants.DeploymentLockFile);
                    string statusLockPath     = Path.Combine(lockPath, Constants.StatusLockFile);
                    string hooksLockPath      = Path.Combine(lockPath, Constants.HooksLockFile);
                    var statusLock            = new LockFile(statusLockPath, traceFactory);
                    var hooksLock             = new LockFile(hooksLockPath, traceFactory);
                    var deploymentLock        = new DeploymentLockFile(deploymentLockPath, traceFactory);

                    var analytics = new Analytics(settings, new ServerConfiguration(), traceFactory);
                    var deploymentStatusManager = new DeploymentStatusManager(environment, analytics, statusLock);
                    var repositoryFactory       = new RepositoryFactory(environment, settings, traceFactory);
                    var siteBuilderFactory      = new SiteBuilderFactory(new BuildPropertyProvider(), environment);
                    var webHooksManager         = new WebHooksManager(tracer, environment, hooksLock);
                    var deploymentManager       = new DeploymentManager(siteBuilderFactory, environment, traceFactory, analytics, settings, deploymentStatusManager, deploymentLock, NullLogger.Instance, webHooksManager);
                    var fetchHandler            = new FetchHandler(tracer, deploymentManager, settings, deploymentStatusManager, deploymentLock, environment, null, repositoryFactory);

                    IDisposable tempDeployment = null;

                    try
                    {
                        // Perform deployment
                        deploymentLock.LockOperation(() =>
                        {
                            ChangeSet tempChangeSet = null;
                            if (waitForTempDeploymentCreation)
                            {
                                // create temporary deployment before the actual deployment item started
                                // this allows portal ui to readily display on-going deployment (not having to wait for fetch to complete).
                                // in addition, it captures any failure that may occur before the actual deployment item started
                                tempDeployment = deploymentManager.CreateTemporaryDeployment(
                                    Resources.ReceivingChanges,
                                    out tempChangeSet,
                                    deployInfo.TargetChangeset,
                                    deployInfo.Deployer);

                                tcs.TrySetResult(null);
                            }

                            fetchHandler.PerformDeployment(deployInfo, tempDeployment, tempChangeSet).Wait();
                        }, "Performing continuous deployment", TimeSpan.Zero);
                    }
                    catch (LockOperationException)
                    {
                        if (tempDeployment != null)
                        {
                            tempDeployment.Dispose();
                        }

                        using (tracer.Step("Update pending deployment marker file"))
                        {
                            // REVIEW: This makes the assumption that the repository url is the same.
                            // If it isn't the result would be buggy either way.
                            FileSystemHelpers.SetLastWriteTimeUtc(fetchHandler._markerFilePath, DateTime.UtcNow);
                        }
                    }
                }
                catch (Exception ex)
                {
                    tracer.TraceError(ex);
                }
                finally
                {
                    backgroundTrace.Dispose();
                }
            });

            // When the frontend/ARM calls /deploy with isAsync=true, it starts polling
            // the deployment status immediately, so it's important that the temp deployment
            // is created before we return.
            if (waitForTempDeploymentCreation)
            {
                // If deploymentTask blows up before it creates the temp deployment,
                // go ahead and return.
                await Task.WhenAny(tcs.Task, deploymentTask);
            }
        }
Example #9
0
        static int Main(string[] args)
        {
            if (args.Length < 2)
            {
                System.Console.WriteLine("Usage: kudu.exe appRoot wapTargets [deployer]");
                return(1);
            }

            // The post receive hook launches the exe from sh and intereprets newline differently.
            // This fixes very wacky issues with how the output shows up in the conosle on push
            System.Console.Error.NewLine = "\n";
            System.Console.Out.NewLine   = "\n";

            System.Environment.SetEnvironmentVariable("GIT_DIR", null, System.EnvironmentVariableTarget.Process);

            var    appRoot        = args[0];
            var    wapTargets     = args[1];
            string deployer       = args.Length == 2 ? null : args[2];
            string nugetCachePath = null;

            IEnvironment env = GetEnvironment(appRoot, nugetCachePath);

            // Setup the trace
            string tracePath    = Path.Combine(env.ApplicationRootPath, Constants.TracePath, Constants.TraceFile);
            var    tracer       = new Tracer(tracePath);
            var    traceFactory = new TracerFactory(() => tracer);

            // Calculate the lock path
            string lockPath           = Path.Combine(env.ApplicationRootPath, Constants.LockPath);
            string deploymentLockPath = Path.Combine(lockPath, Constants.DeploymentLockFile);
            var    deploymentLock     = new LockFile(traceFactory, deploymentLockPath);

            var fs = new FileSystem();
            var buildPropertyProvider = new BuildPropertyProvider(wapTargets);
            var builderFactory        = new SiteBuilderFactory(buildPropertyProvider, env);
            var serverRepository      = new GitDeploymentRepository(env.DeploymentRepositoryPath, traceFactory);

            var logger            = new ConsoleLogger();
            var deploymentManager = new DeploymentManager(serverRepository,
                                                          builderFactory,
                                                          env,
                                                          fs,
                                                          traceFactory,
                                                          deploymentLock,
                                                          logger);

            var step = tracer.Step("Executing external process", new Dictionary <string, string>
            {
                { "type", "process" },
                { "path", "kudu.exe" },
                { "arguments", appRoot + " " + wapTargets }
            });

            using (step)
            {
                try
                {
                    deploymentManager.Deploy(deployer);
                }
                catch
                {
                    System.Console.Error.WriteLine(Resources.Log_DeploymentError);

                    throw;
                }
            }

            if (logger.HasErrors)
            {
                System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                return(1);
            }

            return(0);
        }
Example #10
0
        private static int PerformDeploy(
            string appRoot,
            string wapTargets,
            string deployer,
            string lockPath,
            IEnvironment env,
            IDeploymentSettingsManager settingsManager,
            TraceLevel level,
            ITracer tracer,
            ITraceFactory traceFactory,
            IOperationLock deploymentLock)
        {
            System.Environment.SetEnvironmentVariable("GIT_DIR", null, System.EnvironmentVariableTarget.Process);

            // Skip SSL Certificate Validate
            OperationClient.SkipSslValidationIfNeeded();

            // Adjust repo path
            env.RepositoryPath = Path.Combine(env.SiteRootPath, settingsManager.GetRepositoryPath());

            string statusLockPath = Path.Combine(lockPath, Constants.StatusLockFile);
            string hooksLockPath  = Path.Combine(lockPath, Constants.HooksLockFile);

            IOperationLock statusLock = new LockFile(statusLockPath, traceFactory);
            IOperationLock hooksLock  = new LockFile(hooksLockPath, traceFactory);

            IBuildPropertyProvider buildPropertyProvider = new BuildPropertyProvider();
            ISiteBuilderFactory    builderFactory        = new SiteBuilderFactory(buildPropertyProvider, env);
            var logger = new ConsoleLogger();

            IRepository gitRepository;

            if (settingsManager.UseLibGit2SharpRepository())
            {
                gitRepository = new LibGit2SharpRepository(env, settingsManager, traceFactory);
            }
            else
            {
                gitRepository = new GitExeRepository(env, settingsManager, traceFactory);
            }

            IServerConfiguration serverConfiguration = new ServerConfiguration();
            IAnalytics           analytics           = new Analytics(settingsManager, serverConfiguration, traceFactory);

            IWebHooksManager         hooksManager            = new WebHooksManager(tracer, env, hooksLock);
            IDeploymentStatusManager deploymentStatusManager = new DeploymentStatusManager(env, analytics, statusLock);
            IAutoSwapHandler         autoSwapHander          = new AutoSwapHandler(env, settingsManager, traceFactory);
            var functionManager = new FunctionManager(env, traceFactory);
            IDeploymentManager deploymentManager = new DeploymentManager(builderFactory,
                                                                         env,
                                                                         traceFactory,
                                                                         analytics,
                                                                         settingsManager,
                                                                         deploymentStatusManager,
                                                                         deploymentLock,
                                                                         GetLogger(env, level, logger),
                                                                         hooksManager,
                                                                         functionManager);

            var step = tracer.Step(XmlTracer.ExecutingExternalProcessTrace, new Dictionary <string, string>
            {
                { "type", "process" },
                { "path", "kudu.exe" },
                { "arguments", appRoot + " " + wapTargets }
            });

            using (step)
            {
                try
                {
                    deploymentManager.DeployAsync(gitRepository, changeSet: null, deployer: deployer, clean: false)
                    .Wait();

                    string                branch     = settingsManager.GetBranch();
                    ChangeSet             changeSet  = gitRepository.GetChangeSet(branch);
                    IDeploymentStatusFile statusFile = deploymentStatusManager.Open(changeSet.Id);
                    if (statusFile != null && statusFile.Status == DeployStatus.Success)
                    {
                        autoSwapHander.HandleAutoSwap(changeSet.Id, deploymentManager.GetLogger(changeSet.Id), tracer).Wait();
                    }
                }
                catch (Exception e)
                {
                    tracer.TraceError(e);

                    System.Console.Error.WriteLine(e.GetBaseException().Message);
                    System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                    return(1);
                }
            }

            if (logger.HasErrors)
            {
                System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                return(1);
            }

            return(0);
        }
Example #11
0
        static int Main(string[] args)
        {
            // Turn flag on in app.config to wait for debugger on launch
            if (ConfigurationManager.AppSettings["WaitForDebuggerOnStart"] == "true")
            {
                while (!Debugger.IsAttached)
                {
                    System.Threading.Thread.Sleep(100);
                }
            }

            if (args.Length < 2)
            {
                System.Console.WriteLine("Usage: kudu.exe appRoot wapTargets [deployer]");
                return(1);
            }

            // The post receive hook launches the exe from sh and intereprets newline differently.
            // This fixes very wacky issues with how the output shows up in the conosle on push
            System.Console.Error.NewLine = "\n";
            System.Console.Out.NewLine   = "\n";

            System.Environment.SetEnvironmentVariable("GIT_DIR", null, System.EnvironmentVariableTarget.Process);

            var    appRoot        = args[0];
            var    wapTargets     = args[1];
            string deployer       = args.Length == 2 ? null : args[2];
            string nugetCachePath = null;

            IEnvironment env             = GetEnvironment(appRoot, nugetCachePath);
            var          settings        = new XmlSettings.Settings(GetSettingsPath(env));
            var          settingsManager = new DeploymentSettingsManager(settings);

            // Setup the trace
            TraceLevel level        = settingsManager.GetTraceLevel();
            var        tracer       = GetTracer(env, level);
            var        traceFactory = new TracerFactory(() => tracer);

            // Calculate the lock path
            string lockPath           = Path.Combine(env.SiteRootPath, Constants.LockPath);
            string deploymentLockPath = Path.Combine(lockPath, Constants.DeploymentLockFile);
            var    deploymentLock     = new LockFile(traceFactory, deploymentLockPath);

            var fs = new FileSystem();
            var buildPropertyProvider = new BuildPropertyProvider();
            var serverRepository      = new GitDeploymentRepository(env.RepositoryPath, env.SiteRootPath, traceFactory);
            var builderFactory        = new SiteBuilderFactory(settingsManager, buildPropertyProvider, env);

            var logger            = new ConsoleLogger();
            var deploymentManager = new DeploymentManager(serverRepository,
                                                          builderFactory,
                                                          env,
                                                          fs,
                                                          traceFactory,
                                                          settingsManager,
                                                          deploymentLock,
                                                          GetLogger(env, level, logger));

            var step = tracer.Step("Executing external process", new Dictionary <string, string>
            {
                { "type", "process" },
                { "path", "kudu.exe" },
                { "arguments", appRoot + " " + wapTargets }
            });

            using (step)
            {
                try
                {
                    deploymentManager.Deploy(deployer);
                }
                catch
                {
                    System.Console.Error.WriteLine(Resources.Log_DeploymentError);

                    throw;
                }
            }

            if (logger.HasErrors)
            {
                System.Console.Error.WriteLine(Resources.Log_DeploymentError);
                return(1);
            }

            return(0);
        }