bdampmpc
Posts: 4
Joined: Fri Mar 08, 2024 9:39 pm

AzureDO: Setting Sync Folder In Pipeline

I have my installer project in its own repo as I will be bringing in the artifacts/assemblies from multiple other pipelines. The pipeline will handle building the file/folder structure that I want the installer to install.

When I'm working on the installer project locally, I have an example folder of these assemblies in C:\InstalleFiles\ProjectName.
When I build it in the pipeline that folder isn't going to exist and I want it to be based on the System.ArtifactsDirectory that AzureDO downloads the pipeline artifacts into by default.

One of the files, the main EXE, needs to be used to set the version as well as used as the assembly for a Windows Service.

There's a few different threads on this in the forum but most of them are over a decade old and reference using cmdline parameters instead of the Powershell automation shown in the AzureDO tutorials.

I tried using a PowerShell script to modify the AIP file to update the caphyon.advinst.msicomp.SynchronizedFolderComponent component's SourcePath. That broke the versioning:
"The source file "D:\InstallerFiles\ProjectName\ProjectName.exe" used for value of property "ProductVersion" is missing
from disk. Create it on disk or change the property's options."

Maybe I just need to keep hacking away at the AIP file but thought I'd ask here if there was a 'better' way to do this?
bdampmpc
Posts: 4
Joined: Fri Mar 08, 2024 9:39 pm

Re: AzureDO: Setting Sync Folder In Pipeline

FWIW: I was able to get it to 'work' by writing a Powershell script to grab the sourcepath element from the SynchronizedFolderComponent and use that to replace all the paths in the MsiFilesComponent element.

That got it to build but that's not truly what I'm after, it doesn't appear to be truly syncing by adding/removing files that it finds in the folder.
Catalin
Posts: 6721
Joined: Wed Jun 13, 2018 7:49 am

Re: AzureDO: Setting Sync Folder In Pipeline

Hello Bryan and welcome to our forums,

Not quite sure I fully grasp your scenario here.

If I understand this correctly, are you trying to enable Synchronization between a folder from your project and a "folder" from Azure DevOps?

If so, here's a PowerShell snippet that can help you with that:

Code: Select all

# loading the AIP file

$aipPath = join-path $(System.ArtifactsDirectory) "AzureDevOps.aip"

write-host $aipPath

$ai = new-object -comobject AdvancedInstaller

$proj = $ai.LoadProject($aipPath)

$appDir = $proj.PredefinedFolders.ApplicationFolder

$appDir.Synchronization.SourceFolder = "$(System.ArtifactsDirectory)"

$proj.build()
Upon running the above, I checked the built MSI and it did the synchronization just fine:
Screenshot_122.png
Screenshot_122.png (87.56 KiB) Viewed 16225 times
Screenshot_123.png
Screenshot_123.png (33.8 KiB) Viewed 16225 times

The above is the "File" table for the downloaded MSI.

Hope this helps!

Best regards,
Catalin
Catalin Gheorghe - Advanced Installer Team
Follow us: Twitter - Facebook - YouTube
bdampmpc
Posts: 4
Joined: Fri Mar 08, 2024 9:39 pm

Re: AzureDO: Setting Sync Folder In Pipeline

Thanks for the reply Catalin, that's exactly what I was looking for.

I kept looking in the IFolder or IFile components, totally missed PredefinedFolders.ApplicationFolder.

For anyone who sees this later, you'll probably want to change the output folder as well which can be done with:
$project.BuildComponent.SelectedBuild.OutputFolder = $newOutputFolder

Putting it all together then, here's a small script to modify the input (sync folder) and the output:

Code: Select all

$fileNameSearch = "Installer.Project.aip"
$newSourceFolder = "$(System.ArtifactsDirectory)"
$newOutputFolder = "$(Build.BinariesDirectory)"

#Check to make sure we have files.
If ((Get-ChildItem -Path  $newSourceFolder -Force | Measure-Object).Count -eq 0) {
    Throw "Error: the source folder $($newSourceFolder) does not contain files."
}

#Find installer project file
$installerProjectFilePath = Get-ChildItem -Filter $fileNameSearch -File -Recurse | Select-Object -First 1
if ($installerProjectFilePath -eq $null) {
    throw "Error: $($fileNameSearch) not found."
}
Write-Host "Found installer project: $($installerProjectFilePath.FullName)"

# Load the project
$advInstaller = new-object -com "advancedinstaller";
$project = $advInstaller.LoadProject($installerProjectFilePath.FullName);

#Update the Output folder
$project.BuildComponent.SelectedBuild.OutputFolder = $newOutputFolder

#Update the Syncronization folder
$appDir = $project.PredefinedFolders.ApplicationFolder
$appDir.Synchronization.SourceFolder = $newSourceFolder

# Build the project
$project.Build();
Last edited by bdampmpc on Tue Mar 19, 2024 5:22 pm, edited 1 time in total.
Catalin
Posts: 6721
Joined: Wed Jun 13, 2018 7:49 am

Re: AzureDO: Setting Sync Folder In Pipeline

You are always welcome, Bryan!

Glad I was able to assist.

And thank you for sharing your script with us. I'm sure other customers facing a similar scenario will find this useful.

Best regards,
Catalin
Catalin Gheorghe - Advanced Installer Team
Follow us: Twitter - Facebook - YouTube
bdampmpc
Posts: 4
Joined: Fri Mar 08, 2024 9:39 pm

Re: AzureDO: Setting Sync Folder In Pipeline

EDITED: Ah, nevermind, I figured it out.

ProTip: If you have multiple stages in an AzureDO pipeline it will clean between them and your build artifacts are gone. I've added a quick sanity check to the script above to make sure the source directory is not emtpy.
Catalin
Posts: 6721
Joined: Wed Jun 13, 2018 7:49 am

Re: AzureDO: Setting Sync Folder In Pipeline

Thank you for your followup on this, Bryan.

Glad you managed to find the culprit.

Yes, the resources are indeed removed between "stages", this is something I encountered too some time ago. :)

If there's anything else I could help you with, please let me know and I will gladly do so.

Best regards,
Catalin
Catalin Gheorghe - Advanced Installer Team
Follow us: Twitter - Facebook - YouTube

Return to “Building Installers”