Click here to Skip to main content
12,253,114 members (46,699 online)
Click here to Skip to main content

Stats

50.3K views
444 downloads
89 bookmarked
Posted

Deployer

, 30 Mar 2012 Apache
Automate deployment of Windows Services, ClickOnce, and other .NET applications.
Deployer
Deployer
!copyToDllCache
Interop.VSFlex7L.dll
stdole.dll
ClassDiagram1.cd
clickOnceKey.pfx
deployer-full.xsx
Deployer.csproj.user
DeployTypes
DomainClasses
_tfs
text-base
ConfigReplacesEntry.cs.tfs-base
ConfigReplacesRoot.cs.tfs-base
DllCacheEntry.cs.tfs-base
_tfs
text-base
BaseDeployType.cs.tfs-base
ClickOnce.cs.tfs-base
DatabaseScript.cs.tfs-base
Service.cs.tfs-base
XCopy.cs.tfs-base
Logic
_tfs
text-base
Controller.cs.tfs-base
FileSystemUtil.cs.tfs-base
XmlUtil.cs.tfs-base
mage.exe
Properties
_tfs
text-base
AssemblyInfo.cs.tfs-base
Resources.Designer.cs.tfs-base
Resources.resx.tfs-base
Settings.Designer.cs.tfs-base
Settings.settings.tfs-base
Zip
.svn
entries
format
prop-base
_tfs
text-base
props
_tfs
text-base
text-base
ZipArchive.cs.svn-base
ZipDirectory.cs.svn-base
ZipEntry.cs.svn-base
ZipEntryCollection.cs.svn-base
ZipException.cs.svn-base
ZipLib.cs.svn-base
ZipStream.cs.svn-base
_tfs
text-base
ZipArchive.cs.svn-base.tfs-base
ZipDirectory.cs.svn-base.tfs-base
ZipEntry.cs.svn-base.tfs-base
ZipEntryCollection.cs.svn-base.tfs-base
ZipException.cs.svn-base.tfs-base
ZipLib.cs.svn-base.tfs-base
ZipStream.cs.svn-base.tfs-base
tmp
prop-base
_tfs
text-base
props
_tfs
text-base
text-base
_tfs
text-base
_tfs
text-base
_tfs
text-base
entries.tfs-base
format.tfs-base
_tfs
text-base
ZipArchive.cs.tfs-base
ZipDirectory.cs.tfs-base
ZipEntry.cs.tfs-base
ZipEntryCollection.cs.tfs-base
ZipException.cs.tfs-base
ZipLib.cs.tfs-base
ZipStream.cs.tfs-base
zlib.dll
TestApp
Properties
_tfs
text-base
AssemblyInfo.cs.tfs-base
Resources.Designer.cs.tfs-base
Resources.resx.tfs-base
Settings.Designer.cs.tfs-base
Settings.settings.tfs-base
TestClickOnceApp
ClickOnceApp_TemporaryKey.pfx
Properties
_tfs
text-base
AssemblyInfo.cs.tfs-base
Resources.Designer.cs.tfs-base
Resources.resx.tfs-base
Settings.Designer.cs.tfs-base
Settings.settings.tfs-base
TestClickOnceApp.csproj.user
TestDatabaseScript
Properties
_tfs
text-base
AssemblyInfo.cs.tfs-base
TestWindowsService
Properties
_tfs
text-base
AssemblyInfo.cs.tfs-base
someFiles
_tfs
text-base
will not be included in backup.txt.tfs-base
using System;
using System.Collections.Generic;
using System.Text;
using System.IO;
using System.Xml;
using Deployer.Logic;
using Deployer.DeployTypes.DomainClasses;

namespace Deployer.DeployTypes
{
    class XCopy : BaseDeployType
    {
        public XCopy() : base()
        {
            _backupInfo = new List<string>();
            _configReplaces = new List<ConfigReplacesRoot>();
            _dllCache = new List<DllCacheEntry>();
        }

        public XCopy(XmlNode configNode) : this()
        {
            XmlNode targetPathNode = configNode.SelectSingleNode("targetPath");
            TargetPath = targetPathNode.InnerXml.TrimEnd('\\');
            ClearFolderBeforeCopy = XmlUtil.ParseBoolAttribute(targetPathNode.Attributes["clear"], false);
            BackupFolderBeforeCopy = XmlUtil.ParseBoolAttribute(targetPathNode.Attributes["backup"], false);

            foreach (XmlNode backupInfo in configNode.SelectSingleNode("backupInfo").ChildNodes)
            {
                BackupInfo.Add(backupInfo.Attributes["path"].InnerXml.Replace("~", TargetPath).TrimEnd('\\'));
            }

            foreach (XmlNode configReplacesNode in configNode.SelectNodes("configReplaces"))
            {
                string searchExpression = XmlUtil.ParseStringAttribute(configReplacesNode.Attributes["searchExpression"], "*.config");
                ConfigReplacesRoot crr = new ConfigReplacesRoot(searchExpression);

                foreach (XmlNode node in configReplacesNode.ChildNodes)
                {
                    ConfigReplacesEntry entry = new ConfigReplacesEntry(
                        node.ChildNodes[0].InnerText, node.ChildNodes[1].InnerText);
                    crr.Entries.Add(entry);
                }

                this.ConfigReplaces.Add(crr);
            }

            foreach (XmlNode node in configNode.SelectNodes("dllCache/dll"))
            {
                DllCacheEntry entry = new DllCacheEntry(
                    node.Attributes["name"].InnerXml, node.Attributes["copyTo"].InnerXml);

                this.DllCache.Add(entry);
            }
        }

        private string _targetPath;
        public string TargetPath
        {
            get { return _targetPath; }
            set { _targetPath = value; }
        }

        public DirectoryInfo TargetDirectory
        {
            get { return new DirectoryInfo(TargetPath); }
        }

        private bool _clearFolderBeforeCopy;
        public bool ClearFolderBeforeCopy
        {
            get { return _clearFolderBeforeCopy; }
            set { _clearFolderBeforeCopy = value; }
        }

        private bool _backupFolderBeforeCopy;
        public bool BackupFolderBeforeCopy
        {
            get { return _backupFolderBeforeCopy; }
            set { _backupFolderBeforeCopy = value; }
        }

        private List<string> _backupInfo;
        public List<string> BackupInfo
        {
            get { return _backupInfo; }
            set { _backupInfo = value; }
        }

        private List<ConfigReplacesRoot> _configReplaces;
        internal List<ConfigReplacesRoot> ConfigReplaces
        {
            get { return _configReplaces; }
            set { _configReplaces = value; }
        }

        private List<DllCacheEntry> _dllCache;
        internal List<DllCacheEntry> DllCache
        {
            get { return _dllCache; }
            set { _dllCache = value; }
        }

        public override void Execute(DirectoryInfo sourceDirectory)
        {
            Execute(sourceDirectory, true, true);
        }

        protected void Execute(DirectoryInfo sourceDirectory, bool replaceTargetConfig, bool copyDllCache)
        {
			onDeployNotice("Source directory: '{0}'", sourceDirectory.FullName);
			onDeployNotice("Target directory: '{0}'", TargetDirectory.FullName);

            if (!TargetDirectory.Exists)
                TargetDirectory.Create();
            else if (ClearFolderBeforeCopy)
                FileSystemUtil.ClearFolder(TargetDirectory);

            if (BackupFolderBeforeCopy)
            {
                FileSystemUtil.CopyFolderWithExclude(TargetPath,
                    string.Format("{0}\\{1}", Properties.Settings.Default.BackupPath, sourceDirectory.Name),
                    BackupInfo);
            }

            FileSystemUtil.CopyFolder(sourceDirectory.FullName, TargetPath);

            if (replaceTargetConfig)
                ReplaceConfigValues();

            if (copyDllCache)
                CopyDllsFromCache();
        }

        protected virtual void CopyDllsFromCache()
        {
            foreach (DllCacheEntry dce in DllCache)
                dce.CopyTo = dce.CopyTo.Replace("{targetDirectory}", TargetPath);

            foreach (DllCacheEntry dce in DllCache)
            {
                string source = string.Format("{0}\\{1}", Properties.Settings.Default.DllCache, dce.Dll);
                if (!File.Exists(source))
                {
                    throw new Exception(string.Format(
                        "Specified dll [{0}] does not exist in cache. Can't continue with deployment", dce.Dll));
                }

                string destination = string.Format("{0}\\{1}", dce.CopyTo, dce.Dll);
                FileSystemUtil.CopyFile(source, destination);
            }
        }

        // Configuration methods

        public void ReplaceConfigValues()
        {
            ReplaceConfigValues(TargetDirectory);
        }

        public void ReplaceConfigValues(DirectoryInfo directory)
        {
            foreach (ConfigReplacesRoot crr in ConfigReplaces)
                ReplaceConfigValues(directory, crr);
        }

        public void ReplaceConfigValues(DirectoryInfo directory, ConfigReplacesRoot configReplaces)
        {
            foreach (string f in Directory.GetFiles(directory.FullName, configReplaces.SearchExpression, SearchOption.AllDirectories))
            {
                StringBuilder file = null;
                using (StreamReader sr = new StreamReader(f))
                {
                    file = new StringBuilder(sr.ReadToEnd());
                }

                foreach (ConfigReplacesEntry cre in configReplaces.Entries)
                {
                    file.Replace(cre.Find, cre.Replace);
                }

                using (StreamWriter sw = new StreamWriter(f, false))
                {
                    sw.Write(file.ToString());
                }
            }
        }
    }
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Apache License, Version 2.0

Share

About the Author

lepipele
Chief Technology Officer
United States United States
If you liked this article, consider reading other articles by me. For republishing article on other websites, please contact me by leaving a comment.

Bitcoin wallet:
1ARXmh58S6aRiZPCbneDCzrB1HUU6PLmDQ

Blogs I enjoy:
http://blog.codinghorror.com/

You may also be interested in...

| Advertise | Privacy | Terms of Use | Mobile
Web02 | 2.8.160426.1 | Last Updated 30 Mar 2012
Article Copyright 2008 by lepipele
Everything else Copyright © CodeProject, 1999-2016
Layout: fixed | fluid