Reputation: 69
I know some programing basics but this project is far beyond my knowledge. Any help would be really appreciated, thank you in advance.
There are two files with text (see below) and I need to examine first file(regex) and replace text in another file using predefined array of patterns. Here is the example of the code and text files, this way i would be easier to understand what I need.
$file = "C:\powershell\changescript\Add.bat"
content of the file Add.bat:
@Echo Off
cd %systemroot%\system32
Reg.exe add "HKCU\Software\HP\HPTwain" /v "DesktopShortcut" /t REG_SZ /d "Yes" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "ModelName" /t REG_SZ /d "tochange" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "HostName" /t REG_SZ /d "tochange" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "IP Address" /t REG_SZ /d "tochange" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "SerialNo" /t REG_SZ /d "tochange" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "Services" /t REG_SZ /d "PclPrint eSCL LEDM" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "NetworkType" /t REG_SZ /d "Ethernet" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "MAC" /t REG_SZ /d "tochange" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "Manufacturer" /t REG_SZ /d "Hewlett-Packard" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "GUID" /t REG_SZ /d "tochange" /f
xcopy "C:\applications\TwainConfig\*" "%USERPROFILE%\AppData\Local\" /s /i /Y
Cls
Exit
$filemin = "C:\powershell\changescript\pc.txt"
content of the file pc.txt:
ModelName : HP Color LaserJet Pro M478fxxx
HostName : EPxxxxxx
IP Address : 192.x.x.x
SerialNo : CNBxx3P8WY
Services : PclPrint RestScan eSCL LEDM Fax
MAC : c4651645xxb95
GUID : urn:uuid:8866a4ce-2da1-5b24-6af5-13e5dc7f63b5
This isn't working but describe what I need (at-least I think it describe..)
$filemin = "C:\powershell\changescript\pc.txt"
$findThisAndReplace = @(
$paternchange1 = '"ModelName" /t REG_SZ /d "tochange" /f"',
$paternchange2 = '"HostName" /t REG_SZ /d "tochange" /f"',
$paternchange3 = '"IP Address" /t REG_SZ /d "tochange" /f"',
$paternchange4 = '"SerialNo" /t REG_SZ /d "tochange" /f"',
$paternchange5 = '"MAC" /t REG_SZ /d "tochange" /f"',
$paternchange6 = '"GUID" /t REG_SZ /d "tochange" /f"'
)
$file = "C:\powershell\changescript\AddScan.bat"
$replaceWith = @(
$paternget1 = '"ModelName : *',
$paternget2 = '"HostName : *',
$paternget3 = '"IP Address : *',
$paternget4 = '"SerialNo : *',
$paternget5 = '"MAC : *',
$paternget6 = '"GUID : *'
)
function getsetcontent ($patern, $filemin, $file){
$i=0;
while $1 !> 7
do
(get-content $file) | ForEach-Object {$i++;$_ -Replace $patternchange$i, "$paternget$i"} | Set-Content -Encoding UTF8 $filemin}
Result after merge should be :
@Echo Off
cd %systemroot%\system32
Reg.exe add "HKCU\Software\HP\HPTwain" /v "DesktopShortcut" /t REG_SZ /d "Yes" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "ModelName" /t REG_SZ /d "HP Color LaserJet Pro M478fxxx" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "HostName" /t REG_SZ /d "EPxxxxxx" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "IP Address" /t REG_SZ /d "192.x.x.x" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "SerialNo" /t REG_SZ /d "CNBxx3P8WY" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "Services" /t REG_SZ /d "PclPrint eSCL LEDM" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "NetworkType" /t REG_SZ /d "Ethernet" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "MAC" /t REG_SZ /d "c4651645xxb95" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "Manufacturer" /t REG_SZ /d "Hewlett-Packard" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "GUID" /t REG_SZ /d "urn:uuid:8866a4ce-2da1-5b24-6af5-13e5dc7f63b5" /f
xcopy "C:\applications\TwainConfig\*" "%USERPROFILE%\AppData\Local\" /s /i /Y
Cls
Exit
Upvotes: 1
Views: 93
Reputation: 3439
You can solve your problem with the following piece of code:
((Get-Content pc.txt) -replace '^([^:]+):', '$1=' | Out-String | ConvertFrom-StringData).GetEnumerator() | ForEach-Object -Process { New-Variable -Name $_.key -Value $_.Value -Force }
$ExecutionContext.InvokeCommand.ExpandString(((Get-Content Add.bat) -replace '("([^"]+)"[^"]+)"tochange"', '$1"${$2}"' | Out-String)) | Set-Content AddNew.bat -PassThru
Result:
@Echo Off
cd %systemroot%\system32
Reg.exe add "HKCU\Software\HP\HPTwain" /v "DesktopShortcut" /t REG_SZ /d "Yes" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "ModelName" /t REG_SZ /d "HP Color LaserJet Pro M478fxxx" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "HostName" /t REG_SZ /d "EPxxxxxx" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "IP Address" /t REG_SZ /d "192.x.x.x" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "SerialNo" /t REG_SZ /d "CNBxx3P8WY" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "Services" /t REG_SZ /d "PclPrint RestScan eSCL LEDM Fax" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "NetworkType" /t REG_SZ /d "Ethernet" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "MAC" /t REG_SZ /d "c4651645xxb95" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "Manufacturer" /t REG_SZ /d "Hewlett-Packard" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "GUID" /t REG_SZ /d "urn:uuid:8866a4ce-2da1-5b24-6af5-13e5dc7f63b5" /f
xcopy "C:\applications\TwainConfig\*" "%USERPROFILE%\AppData\Local\" /s /i /Y
Cls
Exit
regex101 for the pc.txt
file.
regex101 for the Add.bat
file.
Upvotes: 1
Reputation: 61253
One way of doing this is to read the pc.txt
with the registryvalue names and the replacement strings and convert that to an easy to use Hashtable.
Then loop over your .bat file line by line and make the changes:
# organize the values from 'pc.txt' into a Hashtable
# read the file as single multiline string and replace the first colon (:)
# of every line into an equals sign (=).
# then use ConvertFrom-StringData to obtain a Hashtable
$pcHash = (Get-Content -Path 'D:\Test\pc.txt' -Raw) -replace '(?m)^(.*?):','$1=' | ConvertFrom-StringData
# read the 'Add.bat' as string array
$bat = (Get-Content -Path 'D:\Test\Add.bat') | ForEach-Object {
if ($_ -match '^Reg.*/v\s+"([^"]+)".*"(tochange)"') {
if ($pcHash.ContainsKey($matches[1])) {
# output this line updated
$_ -replace $matches[2], $pcHash[$matches[1]]
}
}
else {
# output the line unchanged
$_
}
}
# output to (new) file. -PassThru will also show the result on screen
$bat | Set-Content -Path 'D:\Test\New.bat' -PassThru
Result:
@Echo Off
cd %systemroot%\system32
Reg.exe add "HKCU\Software\HP\HPTwain" /v "DesktopShortcut" /t REG_SZ /d "Yes" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "ModelName" /t REG_SZ /d "HP Color LaserJet Pro M478fxxx" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "HostName" /t REG_SZ /d "EPxxxxxx" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "IP Address" /t REG_SZ /d "192.x.x.x" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "SerialNo" /t REG_SZ /d "CNBxx3P8WY" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "Services" /t REG_SZ /d "PclPrint eSCL LEDM" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "NetworkType" /t REG_SZ /d "Ethernet" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "MAC" /t REG_SZ /d "c4651645xxb95" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "Manufacturer" /t REG_SZ /d "Hewlett-Packard" /f
Reg.exe add "HKCU\Software\HP\HPTwain" /v "GUID" /t REG_SZ /d "urn:uuid:8866a4ce-2da1-5b24-6af5-13e5dc7f63b5" /f
xcopy "C:\applications\TwainConfig\*" "%USERPROFILE%\AppData\Local\" /s /i /Y
Cls
Exit
Regex details:
^ Assert position at the beginning of the string
Reg Match the characters “Reg” literally
. Match any single character that is not a line break character
* Between zero and unlimited times, as many times as possible, giving back as needed (greedy)
/v Match the characters “/v” literally
\s Match a single character that is a “whitespace character” (spaces, tabs, line breaks, etc.)
+ Between one and unlimited times, as many times as possible, giving back as needed (greedy)
" Match the character “"” literally
( Match the regular expression below and capture its match into backreference number 1
[^"] Match any character that is NOT a “"”
+ Between one and unlimited times, as many times as possible, giving back as needed (greedy)
)
" Match the character “"” literally
. Match any single character that is not a line break character
* Between zero and unlimited times, as many times as possible, giving back as needed (greedy)
" Match the character “"” literally
( Match the regular expression below and capture its match into backreference number 2
tochange Match the characters “tochange” literally
)
" Match the character “"” literally
Upvotes: 1