Skip to content

Commit

Permalink
FileGlob: In-code files/payload harvester with include and exclude gl…
Browse files Browse the repository at this point in the history
…ob patterns
  • Loading branch information
nirbar committed Nov 25, 2024
1 parent fa37e95 commit d7d45f4
Show file tree
Hide file tree
Showing 18 changed files with 633 additions and 18 deletions.
1 change: 1 addition & 0 deletions src/Directory.Packages.props
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
<SevenZapVersion Condition=" '$(SevenZapVersion)' == '' ">24.8.41</SevenZapVersion>
</PropertyGroup>
<ItemGroup>
<PackageVersion Include="Microsoft.Extensions.FileSystemGlobbing" Version="9.0.0" />
<PackageVersion Include="WixToolset.DUtil" version="$(Wix4Version)" />
<PackageVersion Include="WixToolset.WcaUtil" version="$(Wix4Version)" />
<PackageVersion Include="WixToolset.Extensibility" Version="$(Wix4Version)" />
Expand Down
15 changes: 15 additions & 0 deletions src/PanelSwWixExtension.sln
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,8 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "PanelSwBackendExtension", "
EndProject
Project("{B7DD6F7E-DEF8-4E67-B5B7-07EF123DB6F0}") = "CustomSearchUT", "UnitTests\CustomSearchUT\CustomSearchUT.wixproj", "{58B42CEE-5989-4C3B-BAEC-946BF4664BA8}"
EndProject
Project("{B7DD6F7E-DEF8-4E67-B5B7-07EF123DB6F0}") = "FileGlobUT", "UnitTests\FileGlobUT\FileGlobUT.wixproj", "{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|ARM64 = Debug|ARM64
Expand Down Expand Up @@ -675,6 +677,18 @@ Global
{58B42CEE-5989-4C3B-BAEC-946BF4664BA8}.Release|x64.Build.0 = Release|x64
{58B42CEE-5989-4C3B-BAEC-946BF4664BA8}.Release|x86.ActiveCfg = Release|x86
{58B42CEE-5989-4C3B-BAEC-946BF4664BA8}.Release|x86.Build.0 = Release|x86
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Debug|ARM64.ActiveCfg = Debug|ARM64
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Debug|ARM64.Build.0 = Debug|ARM64
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Debug|x64.ActiveCfg = Debug|x64
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Debug|x64.Build.0 = Debug|x64
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Debug|x86.ActiveCfg = Debug|x86
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Debug|x86.Build.0 = Debug|x86
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Release|ARM64.ActiveCfg = Release|ARM64
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Release|ARM64.Build.0 = Release|ARM64
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Release|x64.ActiveCfg = Release|x64
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Release|x64.Build.0 = Release|x64
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Release|x86.ActiveCfg = Release|x86
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40}.Release|x86.Build.0 = Release|x86
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
Expand Down Expand Up @@ -726,6 +740,7 @@ Global
{5B7782E9-9913-4E25-81F4-D98DB5E8B4BD} = {B533D9FC-4927-4A05-892D-B90E8BEDCF5D}
{7BB9BAE3-93F4-47AD-A630-E0FE147F3026} = {B533D9FC-4927-4A05-892D-B90E8BEDCF5D}
{58B42CEE-5989-4C3B-BAEC-946BF4664BA8} = {B533D9FC-4927-4A05-892D-B90E8BEDCF5D}
{EDE32548-11C1-42AD-88E9-B96B9CF4BB40} = {B533D9FC-4927-4A05-892D-B90E8BEDCF5D}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {F5B6389D-77ED-4938-A322-8DFCA4D9FEF5}
Expand Down
9 changes: 7 additions & 2 deletions src/PanelSwWixExtension/PanelSwBurnBackendBinder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@ protected override IReadOnlyCollection<IntermediateSymbolDefinition> SymbolDefin
PSW_ContainerTemplate.SymbolDefinition,
PSW_ContainerExtensionData.SymbolDefinition,
PSW_CustomSearch.SymbolDefinition,
PSW_FileGlob.SymbolDefinition,
PSW_FileGlobPattern.SymbolDefinition,
};
}
return _intermediateSymbols;
Expand All @@ -32,9 +34,12 @@ protected override IReadOnlyCollection<IntermediateSymbolDefinition> SymbolDefin

public override bool TryProcessSymbol(IntermediateSection section, IntermediateSymbol symbol)
{
if (symbol is PSW_ContainerTemplate || symbol is PSW_ContainerExtensionData || symbol is PSW_CustomSearch)
foreach (IntermediateSymbolDefinition definition in SymbolDefinitions)
{
return true;
if (definition.Name == symbol.Definition.Name)
{
return true;
}
}
return base.TryProcessSymbol(section, symbol);
}
Expand Down
4 changes: 3 additions & 1 deletion src/PanelSwWixExtension/PanelSwWiBackendBinder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -486,6 +486,8 @@ public override IReadOnlyCollection<TableDefinition> TableDefinitions
new TableDefinition(nameof(PSW_ExecOnComponent_Environment), PSW_ExecOnComponent_Environment.SymbolDefinition, PSW_ExecOnComponent_Environment.ColumnDefinitions, symbolIdIsPrimaryKey: false),
new TableDefinition(nameof(PSW_ExecOnComponent_ExitCode), PSW_ExecOnComponent_ExitCode.SymbolDefinition, PSW_ExecOnComponent_ExitCode.ColumnDefinitions, symbolIdIsPrimaryKey: false),
new TableDefinition(nameof(PSW_ExecuteCommand), PSW_ExecuteCommand.SymbolDefinition, PSW_ExecuteCommand.ColumnDefinitions, symbolIdIsPrimaryKey: true, unreal: true),
new TableDefinition(nameof(PSW_FileGlob), PSW_FileGlob.SymbolDefinition, PSW_FileGlob.ColumnDefinitions, symbolIdIsPrimaryKey: true, unreal: true),
new TableDefinition(nameof(PSW_FileGlobPattern), PSW_FileGlobPattern.SymbolDefinition, PSW_FileGlobPattern.ColumnDefinitions, symbolIdIsPrimaryKey: true, unreal: true),
new TableDefinition(nameof(PSW_FileRegex), PSW_FileRegex.SymbolDefinition, PSW_FileRegex.ColumnDefinitions, symbolIdIsPrimaryKey: true),
new TableDefinition(nameof(PSW_ForceVersion), PSW_ForceVersion.SymbolDefinition, PSW_ForceVersion.ColumnDefinitions, symbolIdIsPrimaryKey: false),
new TableDefinition(nameof(PSW_InstallUtil), PSW_InstallUtil.SymbolDefinition, PSW_InstallUtil.ColumnDefinitions, symbolIdIsPrimaryKey: false),
Expand Down Expand Up @@ -591,7 +593,7 @@ private void CheckExecuteCommandSequences()
}
}
}

private void DuplicateFolder(IntermediateSection section)
{
List<PSW_DuplicateFolder> duplicateFolders = new List<PSW_DuplicateFolder>();
Expand Down
134 changes: 134 additions & 0 deletions src/PanelSwWixExtension/PanelSwWiOptimizer.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
using Microsoft.Extensions.FileSystemGlobbing;
using Microsoft.Extensions.FileSystemGlobbing.Abstractions;
using PanelSw.Wix.Extensions.Symbols;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text.RegularExpressions;
using WixToolset.Data;
using WixToolset.Data.Symbols;
using WixToolset.Extensibility;
using WixToolset.Extensibility.Data;
using WixToolset.Extensibility.Services;

namespace PanelSw.Wix.Extensions
{
public class PanelSwWiOptimizer : BaseOptimizerExtension
{
private IParseHelper _parseHelper;
private IMessaging _messaging;
private IOptimizeContext _context;

public override void PreOptimize(IOptimizeContext context)
{
_context = context;
_parseHelper = _context.ServiceProvider.GetService<IParseHelper>();
_messaging = _context.ServiceProvider.GetService<IMessaging>();
base.PreOptimize(context);

ResolveFileGlob();
}

private void ResolveFileGlob()
{
Regex bindPathRx = new Regex(@"!\(bindpath\.(?<name>[\w_]+)\).*", RegexOptions.Compiled);
foreach (Intermediate intermediate in _context.Intermediates)
{
foreach (IntermediateSection section in intermediate.Sections)
{
List<PSW_FileGlob> fileGlobs = new List<PSW_FileGlob>();
List<PSW_FileGlobPattern> fileGlobPatterns = new List<PSW_FileGlobPattern>();

foreach (IntermediateSymbol symbol in section.Symbols)
{
if (symbol is PSW_FileGlob glb)
{
fileGlobs.Add(glb);
}
if (symbol is PSW_FileGlobPattern patt)
{
fileGlobPatterns.Add(patt);
}
}

// Collect files
foreach (PSW_FileGlob glb in fileGlobs)
{
bool isBundle = !string.IsNullOrEmpty(glb.PayloadGroup_);
Matcher matcher = new Matcher();
IEnumerable<PSW_FileGlobPattern> patterns = fileGlobPatterns.Where(p => p.FileGlob_.Equals(glb.Id.Id));
matcher.AddIncludePatterns(patterns.Where(p => !string.IsNullOrEmpty(p.Include)).Select(p => p.Include));
matcher.AddExcludePatterns(patterns.Where(p => !string.IsNullOrEmpty(p.Exclude)).Select(p => p.Exclude));

List<string> baseFolders = new List<string>();
Match rxMatch = bindPathRx.Match(glb.SourceDir);
if (rxMatch.Success)
{
string bindName = rxMatch.Groups["name"].Value;
baseFolders = new List<string>(_context.BindPaths?.Where(b => bindName.Equals(b.Name))?.Select(b => b.Path));
}
else
{
baseFolders.Add(glb.SourceDir);
}

if ((baseFolders == null) || (baseFolders.Count == 0) || !baseFolders.Any(d => Directory.Exists(d)))
{
_messaging.Write(ErrorMessages.ExpectedDirectory(glb.SourceDir));
continue;
}

Dictionary<string, string> sectionCachedInlinedDirectoryIds = new Dictionary<string, string>();
foreach (string folder in baseFolders)
{
if (!Directory.Exists(folder))
{
continue;
}

PatternMatchingResult patternMatching = matcher.Execute(new DirectoryInfoWrapper(new DirectoryInfo(folder)));
foreach (FilePatternMatch filePattern in patternMatching.Files)
{
string fullPath = Path.Combine(folder, filePattern.Path);
Uri uri = new Uri(fullPath);
fullPath = uri.AbsolutePath;

string recursiveDir = Path.GetDirectoryName(filePattern.Path);

if (!string.IsNullOrEmpty(glb.PayloadGroup_))
{
Identifier id = _parseHelper.CreateIdentifier("glb", glb.PayloadGroup_, Path.GetFileName(fullPath));
string fileName = Path.Combine(recursiveDir, Path.GetFileName(fullPath));

section.AddSymbol(new WixBundlePayloadSymbol(glb.SourceLineNumbers, id) { SourceFile = new IntermediateFieldPathValue() { Path = fullPath }, Name = fileName });
section.AddSymbol(new WixGroupSymbol(glb.SourceLineNumbers, id) { ChildId = id.Id, ChildType = ComplexReferenceChildType.Payload, ParentId = glb.PayloadGroup_, ParentType = ComplexReferenceParentType.PayloadGroup });
}
else
{
string directoryId = glb.Directory_;
if (!string.IsNullOrEmpty(recursiveDir))
{
directoryId = _parseHelper.CreateDirectoryReferenceFromInlineSyntax(section, glb.SourceLineNumbers, null, directoryId, recursiveDir, sectionCachedInlinedDirectoryIds);
}
Identifier id = _parseHelper.CreateIdentifier("glb", directoryId, Path.GetFileName(fullPath));

section.AddSymbol(new ComponentSymbol(glb.SourceLineNumbers, id) { DirectoryRef = directoryId, KeyPath = id.Id, KeyPathType = ComponentKeyPathType.File });
section.AddSymbol(new FileSymbol(glb.SourceLineNumbers, id) { Source = new IntermediateFieldPathValue() { Path = fullPath }, Name = Path.GetFileName(fullPath), ComponentRef = id.Id, DirectoryRef = directoryId });
if (!string.IsNullOrEmpty(glb.ComponentGroup_))
{
_parseHelper.CreateComplexReference(section, glb.SourceLineNumbers, ComplexReferenceParentType.ComponentGroup, glb.ComponentGroup_, null, ComplexReferenceChildType.Component, id.Id, false);
}
if (!string.IsNullOrEmpty(glb.Feature_))
{
_parseHelper.CreateComplexReference(section, glb.SourceLineNumbers, ComplexReferenceParentType.Feature, glb.Feature_, null, ComplexReferenceChildType.Component, id.Id, true);
}
}
}
}
}
}
}
}
}
}
Loading

0 comments on commit d7d45f4

Please sign in to comment.