param (
[Parameter()]
[string] $Watch,
[string] $Out,
[string] $Filter
)
[decimal]$version = 2.0
### Collector ###
#####################
# MIT License
#
# Matthew D. Jordan, (C) 2020
# www.scenic-shop.com
#
# This script will recursively collect multiple text files within a single directory and insert them into a single file.
# The trick is that you can specify which files to collect with a special tag in the first line of that document. A few
# different tag options will allow you to perform different operations at run time.
#
# This is most often used when developing complicated Inventor iLogic routines, or collecting Autocad Lisp routines into
# a single file. Though this tool maybe used for just about any source code file.
#
# Control Tags
# ===
#
# To include a file in the collection insert the tag in the first line of each file you want to collect.
# You may comment this tag out for whatever source code you're using. E.g. for VB, the tag would read ',
# for AutoLISP it would read ;.
#
# It ensure a file is placed at the top of the collected file include the tag in the first line of
# a file. This is useful for header statements and includes.
#
# To comment out text that is collected, you may insert comment characters by placing the character between the
# and tags. E.g. for Inventor ilogic routines, use this to comment out module
# declarations and include statments. These module declarations make the code readable in Visual Studio, but need to
# be removed for iLogic to work properly.
#
#
# Parameters
# ===
#
# When ready to compile, run this powershell script to combine the files into a single file. There are several command
# line parameters you may use:
#
# -Watch : the directory to scan. The path may be relative to the script location or absolute.
# E.g. -Watch "src", or -Watch "C:\dev\project\" will only scan files within those directories.
#
# -Out : Specifies the output file name that collector will generate. The path may be relative to the script location
# or absolute.
#
#
# -Filter : an optional wildcard glob that will speed up the collection process by restricting the scanned files to
# matches. E.g. -Filter "*.vb" will instruct collector to only scan files ending in .vb.
#
# User defaults for these parameters can be set within the file.
#Parameter Defaults
#======================================
#sub-directory to watch...
$subdirectoryWatchDefault = "src"
#name of the file to build...
$outputFilePreset = "build\build.vb"
#File Search Filter
$FilterDefault = "*.vb"
#======================================
# Set up parameters if there are any...
#======================================
#Set Directory to Watch...
if (-not $Watch) {
$directoryToWatch = (Join-Path $PSScriptRoot $subdirectoryWatchDefault)
} else {
if ([System.IO.Path]::IsPathRooted($Watch)) {
$directoryToWatch = $Watch
} else {
$directoryToWatch = (Join-Path $PSScriptRoot $Watch)
}
}
if (-not (test-path -Path $directoryToWatch)) {
Write-Host "The directory $directoryToWatch does not exist. Exiting with extreme prejudice."
Write-Host ""
exit
}
#Set output filename...
if (-not $Out) {
$outputFile = (Join-Path $PSScriptRoot $outputFilePreset)
} else {
if ([System.IO.Path]::IsPathRooted($Out)) {
$outputFile = $Out
} else {
$outputFile = (Join-Path $PSScriptRoot $Out)
}
}
#Set filter...
if (-not $Filter) {
$Filter = $FilterDefault
}
# Main routine...
#======================================
#get the files in the current directory (recursive)
$fileList = Get-ChildItem -Path $directoryToWatch -File -Recurse -Filter $Filter -Name
#Create our temporary holding array, add the header...
[System.Collections.ArrayList]$dataArrayPrecollection = (("'This file has been auto-generated by Collector version " + $version), ("'Collection timestamp: " + (get-date -Uformat "%Y/%m/%d - %R")), "'2020 Matthew D. Jordan - https://github.com/jordanrobot","")
$fileList | ForEach-Object -process{
$fullPath = (Join-Path $directoryToWatch $_)
If (test-path -Path $fullPath) {
If ((Get-Content -Path $fullPath -TotalCount 1) | Select-String -Pattern "<\/CollectorHeader>" -quiet) {
#Write filename
$dataArrayPrecollection += ("'" + $_)
#Write contents
$dataArrayPrecollection += (Get-Content -Path $fullPath)
#Write new line
$dataArrayPrecollection += ""
}
}
}
$fileList | Sort-Object -Descending FullName | ForEach-Object -process{
$fullPath = (Join-Path $directoryToWatch $_)
If (test-path -Path $fullPath) {
If ((Get-Content -Path $fullPath -TotalCount 1) | Select-String -Pattern "<\/Collector>" -quiet) {
$dataArrayPrecollection += (Get-Content -Path $fullPath)
$dataArrayPrecollection += ""
}
}
}
#Create the list to hold processed data
$dataArray = New-Object Collections.Generic.List[String]
#Go through the list and process each line...
$dataArrayPrecollection | Foreach-object -Process {
If ($_ -match "(.*)<\/CollectorPrepend>") {
#Hide tag found, connect out line...
($dataArray.Add($Matches.1 + $_))
} Elseif ($_ -match "<\/Collector>") {
#IlogicCollector tag found, skip this line
}
Else {
#normal line, add to the file
($dataArray.Add($_))
}
}
#populate the collected file...
try
{
$stream = [System.IO.StreamWriter]::new( $outputFile )
$dataArray | ForEach-Object{ $stream.WriteLine( $_ ) }
}
finally
{
$stream.close()
}
$size = Get-ChildItem $outputFile | % {[math]::ceiling($_.length / 1kb)}
Write-Host "File $outputFile built at $size kb"