IMport/Export and Publish CRM Solutions programmatically
private static void ExportCRMSolutions(bool managed = false)
{
if (ConfigurationHelper.CrmSolutions.Count() > 0)
{
Console.WriteLine(string.Format("{0} Exporting {1} Solution(s)", MESSAGE_PREFIX, ConfigurationHelper.CrmSolutions.Count().ToString()));
foreach (string solution in ConfigurationHelper.CrmSolutions)
{
// Retrieve version number for file name
QueryExpression querySolution = new QueryExpression
{
EntityName = "solution",
ColumnSet = new ColumnSet(new string[] { "version", "versionnumber" }),
Criteria = new FilterExpression()
};
querySolution.Criteria.AddCondition("uniquename", ConditionOperator.Equal, solution);
EntityCollection matchingSolutions = ServiceProxy_Origin.RetrieveMultiple(querySolution);
string version = matchingSolutions.Entities[0].Attributes["version"].ToString();
version = version.Replace('.', '_');
// Set Exported solution file name
string filename;
if (managed)
{
filename = solution + "_" + version + "_managed.zip";
}
else
{
filename = solution + "_" + version + ".zip";
}
if (managed)
Console.WriteLine(string.Format("{0} Exporting Managed Solution '{1}' from CRM Organization {2}", MESSAGE_PREFIX, solution, ConfigurationHelper.CrmSourceOrganization));
else
Console.WriteLine(string.Format("{0} Exporting Unmanaged Solution '{1}' from CRM Organization {2}", MESSAGE_PREFIX, solution, ConfigurationHelper.CrmSourceOrganization));
// Export Solution Request
ExportSolutionRequest exportRequest = new ExportSolutionRequest
{
Managed = managed,
SolutionName = solution
};
ExportSolutionResponse exportResponse = ServiceProxy_Origin.Execute(exportRequest) as ExportSolutionResponse;
// Write to disk
File.WriteAllBytes(ConfigurationHelper.CrmSolutionsDirectory + filename, exportResponse.ExportSolutionFile);
Console.WriteLine(string.Format("{0} Solution '{1}' Saved to disk as '{2}'", MESSAGE_PREFIX, solution, filename));
}
}
}
/// <summary>
/// Import CRM solutions in target organization
/// Note : uses the most recently modified UMANAGED solution in the target folder
/// (no solution number comparison and no import of managed solutions either)
/// </summary>
/// <param name="publishAfterImport"></param>
private static void ImportCRMSolutions(bool publishAfterImport = false)
{
if (ConfigurationHelper.CrmSolutions.Count() > 0)
{
Console.WriteLine(string.Format("{0} Importing {1} Solution(s)", MESSAGE_PREFIX, ConfigurationHelper.CrmSolutions.Count().ToString()));
List<string> solutionFilesToImport = new List<string>();
foreach (string solution in ConfigurationHelper.CrmSolutions)
{
// get list of filenames matching our solution name
string[] dirs = Directory.GetFiles(ConfigurationHelper.CrmSolutionsDirectory, solution + "_*.zip");
SortedSet<FilenameDate> possibleCandidates = new SortedSet<FilenameDate>(new byDate());
foreach (string f in dirs)
{ // retrieve their modified dates and sort by these
FileInfo d = new FileInfo(f);
possibleCandidates.Add(new FilenameDate { filename = f, modifiedDate = d.LastWriteTime });
}
IEnumerator<FilenameDate> candidates = possibleCandidates.Reverse().GetEnumerator();
while (candidates.MoveNext() != false)
{ // take the newest file, excluding managed solutions
if (!candidates.Current.filename.Contains("managed.zip"))
{
solutionFilesToImport.Add(candidates.Current.filename);
break;
}
}
}
foreach (string file in solutionFilesToImport)
{
Console.WriteLine(string.Format("{0} Importing Solution at '{1}' to CRM Organization {2}", MESSAGE_PREFIX, file, ConfigurationHelper.CrmTargetOrganization));
ImportSolutionRequest importSolution = new ImportSolutionRequest
{
OverwriteUnmanagedCustomizations = true,
CustomizationFile = File.ReadAllBytes(file),
PublishWorkflows = true,
ImportJobId = Guid.NewGuid()
};
try
{
ImportSolutionResponse importResponse = ServiceProxy_Target.Execute(importSolution) as ImportSolutionResponse;
}
catch (Exception e)
{
if (!e.Message.StartsWith("The request channel timed out while waiting for a reply after "))
{
throw e; // if timed out, ignore exception, otherwise throw
}
}
String SolutionImportResult = null;
String PercentDone = null;
double percent = 0.0;
do
{
try
{
Entity job = ServiceProxy_Target.Retrieve("importjob", importSolution.ImportJobId, new
ColumnSet(new System.String[] { "data", "solutionname" }));
System.Xml.XmlDocument doc = new System.Xml.XmlDocument();
doc.LoadXml(job["data"].ToString());
PercentDone = doc.SelectSingleNode("importexportxml/@progress").Value;
SolutionImportResult = doc.SelectSingleNode("//solutionManifest/result/@result").Value;
percent = Double.Parse(PercentDone);
}
catch (Exception e)
{
Console.WriteLine(e.Message);
}
if (percent < 100)
{
Console.WriteLine(" Import is {0}% complete.", percent);
System.Threading.Thread.Sleep(10000);
}
} while (percent < 100 && SolutionImportResult.CompareTo("success") == 0);
Console.WriteLine("{0} Solution Import Result: {1}", MESSAGE_PREFIX, SolutionImportResult.ToUpper());
}
if (publishAfterImport)
PublishAllCustomizations();
}
}
/// <summary>
/// Publish all customizations in Target environment
/// </summary>
/// <returns></returns>
private static PublishAllXmlResponse PublishAllCustomizations()
{
PublishAllXmlResponse response = null;
PublishAllXmlRequest req = new PublishAllXmlRequest();
req.RequestId = Guid.NewGuid();
Console.WriteLine(string.Format("{0} Publishing all customizations for organization {1}. Please wait...", MESSAGE_PREFIX, ConfigurationHelper.CrmTargetOrganization));
try
{
response = ServiceProxy_Target.Execute(req) as PublishAllXmlResponse;
}
catch (Exception e)
{
if (!e.Message.StartsWith("The request channel timed out while waiting for a reply after "))
{
throw e; // if timed out, ignore exception
}
else
{
Console.WriteLine("Publishing all customizations has not yet completed (the service request timed out).");
}
}
Console.WriteLine(string.Format("{0} Publishing all customizations *** Success ***", MESSAGE_PREFIX));
return response;
}