Powershell Search for specific string, then add text right after it - powershell

I'm pretty sure this is can be done easily but i couldn't find the answer.
Suppose i have a text file with a bunch of lines in it.
Contents of the text file below
dbuser=admin
dbpassword=
So in Powershell I want to find the string "dbpassword=" and add the text "password" right after the =.
Solutions I've searched for have -replace but i don't want to replace the line, just want to add "password" to it.
Can anyone share what the Powershell code may be?

This assumes that everything after the = character becomes 'password'.
Get-Content -Path '.\bunchoflines.txt' |
ForEach-Object { $_ -match '^dbpassword=' ? 'dbpassword=password' : $_ }

Not sure why you care if it's replaced, but you could just output that line followed by the password instead. Assuming you want to update the file I'd use Set-Content to write it and a switch statement to read the file.
$inputfile = '\path\to\inputfile.txt'
Set-Content -Path $inputfile -value $(
switch -Regex -File $inputfile {
'^dbpassword=' {"$($_)password"}
default {$_}
}
)

Thanks all for your contributions, I ended up finding this solution.
$config = Get-Content path\to\file\somefile.txt
$password = abcdef
$config -replace "dbpassword=.*",("dbpassword="+$password) |
Set-Content path\to\file\somefile.txt

Related

Loop to replace c:\, d:\ ... z:\ with \\servername\c$\

I'm actually trying to build some code to identify rights on shared folders in every single server I've got in my enterprise.
For now, I've already listed every single server and exported it in a .txt file, did a loop on this .txt to export in an other .txt file all shared folders.
All this is working fine but the path is like : c:\...\...\folder$.
To be able to use this I need to do a loop to replace c:\ d:\ etc. with \\servername\c$\.
I've tried using [system.io.file]::ReadAllText and WriteAllText, it's working fine for one letter but didn't find a way to do a loop on it.
I've tried
get-content ... -replace "c:\","\\$ServerName\c$\" ` -replace "d:\" ...
but got an error about regular expression not valid, so trying with [regex]::Escape but didn't work as expected neither...
Powershell
$contenu = [System.IO.File]::ReadAllText("$path\$SharedFolders.txt").Replace("C:\","\\$SharedFolders\c$\")
[System.IO.File]::WriteAllText("$path\$SharedFolders.txt", $contenu)
Powershell
(Get-Content "$path\$SharedFolders.txt") | foreach {
$_ -replace "C:\","\\$SharedFolders\C$\" `
-replace "D:\","\\$SharedFolders\D$\" `
[...] | Set-Content "$path\$sharedfolders.txt"}
And i'd like to have something like that :
Powershell
('a'..'z').ForEach({ (Get-Content "$path\$SharedFolders.txt" -Raw).replace("$_`:\","\\$SharedFolders\$_$") })
But I'm too newbie in Powershell to make it work proprely
You need PSv6 to use 'a'..'z'
The -replace operator is RegEx based, you need to escape a literal backslash with another one in the pattern.
following #Lee_Daileys hint build a RegEx with valid Drive letters
$OFS = '|'
$RE = ('('+(Get-Psdrive -PSProvider filesystem).where({$_.Displayroot -notmatch '^\\'}).name)+'):\\'
$OFS = $Null
"`$RE = '{0}'" -f $RE
'Loop to replace c:\, d:\ … z:\ with \\servername\c$\' -replace $RE,"\\servername\`${1}$\"
Sample output on my PC
$RE = '(A|C|D):\\'
Loop to replace \\servername\c$\, \\servername\d$\ … z:\ with \\servername\c$\
Reading the file with the -raw parameter doesn't require a loop, but wil do all changes at once.
$OFS = '|'
$RE = ('('+(Get-Psdrive -PSProvider filesystem).where({$_.Displayroot -notmatch '^\\'}).name)+'):\\'
$OFS = $Null
$File = "$path\$SharedFolders.txt"
(Get-Content $File -raw) -replace $RE,"\\servername\`${1}$\" |
Set-Content $File
Well thanks for your help, I just manage to make it works like that :
$lecteur=[int][char]'A'
1..26 | % {
$LR=[char]$lecteur
$contenu =[System.IO.File]::ReadAllText("$path\$SharedFolders.txt").Replace("${LR}:\","\\$SharedFolders\$LR$\")
[System.IO.File]::WriteAllText("$path\$SharedFolders.txt", $contenu)
$lecteur++
}
Hope it'll help some people ;)

How to replace comma with new line

I am getting input like s1,s2,s3,s4.i am writing it to file.
Tried below way :
$ServerList = Get-Content "D:\ServerName.txt"
Clear-Content -Path "D:\ServerName.txt"
[IO.File]::ReadAllText($ServerList) -replace ',',"`r`n" | Out-File "D:\ServerName.txt"
But it is not writing anything.
It should replace comma with newline to bring each server in new line.
Please let me know where i am doing wrong.
This oneliner is working for me:
(Get-Content "Path\test.txt") -replace ',',"`r`n" | Out-File "Path\test.txt"

Get-Content & Sub string combined

I'm trying to figure out if there is syntax I can use to get content out of a file and only pull back a sub string of it all in one line? Something like the following, except it doesn't work, so I'm looking for the missing piece.
$ConfigureEmail = Get-Content -Path "\\myFilePath\Location\MyFile.sql" -Raw | $_.SubString($_.IndexOf("*/"))
I'm trying to pull the main script out of the file, starting after the comment block.
Edit: I realized I could add Foreach-Object after the pipe but since I will only ever have one item is there something better to use?
$Content = Get-Content -Path "\\myFilePath\Location\MyFile.sql" -Raw
$ConfigureEmail = $Content.SubString($Content.IndexOf("*/"))
->
$ConfigureEmail = ($Content = Get-Content -Path "\\myFilePath\Location\MyFile.sql" -Raw).SubString($Content.IndexOf("*/"))
or
[regex]::Match((Get-Content .\test.txt -Raw), '\*/.*', 'singleline').Value

Powershell INI editing

I want to changing some values in an INI file. Unfortunately, I have keys in 2 different sections which share an identical name but need different values. My code uses the Get-IniContent function from PsIni.
Example INI file:
[PosScreen]
BitmapFile=C:\Temp\Random.bmp
Bitmap=1
[ControlScreen]
BitmapFile=C:\Temp\Random.bmp
Bitmap=1
I need to change the above to the following:
[PosScreen]
BitmapFile=C:\Temp\FileC.bmp
Bitmap=1
[ControlScreen]
BitmapFile=C:\Temp\FileD.bmp
Bitmap=1
The PowerShell code I am using seems to work, but it changes every value to "File D". It is obviously parsing everything twice, and the name is the same for each section.
$NewFileC = "C:\Temp\FileC.bmp"
$NewFileD = "C:\Temp\FileD.bmp"
$POSIniContent = Get-IniContent "C:\scripts\Update-EnablerImage\WINSUITE.INI"
$BOIniContent = Get-IniContent "C:\scripts\Update-EnablerImage\WINSUITE.INI"
If ($POSIniContent["PosScreen"]["BitmapFile"] -ne $NewFileC) {
Get-Content "C:\scripts\Update-EnablerImage\WINSUITE.INI" |
ForEach-Object {$_ -replace "BitmapFile=.+" , "BitmapFile=$NewFileC" } |
Set-Content "C:\scripts\Update-EnablerImage\WINSUITE.INI"
}
If ($BOIniContent["ControlScreen"]["BitmapFile"] -ne $NewFileD) {
Get-Content "C:\scripts\Update-EnablerImage\WINSUITE.INI" |
ForEach-Object {$_ -replace "BitmapFile=.+" , "BitmapFile=$NewFileD" } |
Set-Content "C:\scripts\Update-EnablerImage\WINSUITE.INI"
}
My struggle is how to change each one independently. I'm a bit of a scripting newbie, so calling out for some help. Tried using Conditional Logic (ForEach $line in $INIFile, for example), but no luck with that.
You are overcomplicating things. You can use Get-IniContent and Out-IniFile as follows:
$ini = Get-IniContent c:\temp\ini.ini
$ini["posscreen"]["BitmapFile"] = "C:\Temp\FileC.bmp"
$ini | Out-IniFile -FilePath c:\temp\ini2.ini
Note that if you want to overwrite the original file, you must add -Force to the Out-IniFile call.

Powershell. Writing out lines based on string within the file

I'm looking for a way to export all lines from within a text file where part of the line matches a certain string. The string is actually the first 4 bytes of the file and I'd like to keep the command to only checking those bytes; not the entire row. I want to write the entire row. How would I go about this?
I am using Windows only and don't have the option to use many other tools that might do this.
Thanks in advance for any help.
Do you want to perform a simple "grep"? Then try this
select-string .\test.txt -pattern "\Athat" | foreach {$_.Line}
or this (very similar regex), also writes to an outfile
select-string .\test.txt -pattern "^that" | foreach {$_.Line} | out-file -filepath out.txt
This assumes that you want to search for a 4-byte string "that" at the beginning of the string , or beginning of the line, respectively.
Something like the following Powershell function should work for you:
function Get-Lines {
[cmdletbinding()]
param(
[string]$filename,
[string]$prefix
)
if( Test-Path -Path $filename -PathType Leaf -ErrorAction SilentlyContinue ) {
# filename exists, and is a file
$lines = Get-Content $filename
foreach ( $line in $lines ) {
if ( $line -like "$prefix*" ) {
$line
}
}
}
}
To use it, assuming you save it as get-lines.ps1, you would load the function into memory with:
. .\get-lines.ps1
and then to use it, you could search for all lines starting with "DATA" with something like:
get-lines -filename C:\Files\Datafile\testfile.dat -prefix "DATA"
If you need to save it to another file for viewing later, you could do something like:
get-lines -filename C:\Files\Datafile\testfile.dat -prefix "DATA" | out-file -FilePath results.txt
Or, if I were more awake, you could ignore the script above, use a simpler solution such as the following one-liner:
get-content -path C:\Files\Datafile\testfile.dat | select-string -Pattern "^DATA"
Which just uses the ^ regex character to make sure it's only looking for "DATA" at the beginning of each line.
To get all the lines from c:\somedir\somefile.txt that begin with 'abcd' :
(get-content c:\somedir\somefile.txt) -like 'abcd*'
provided c:\somedir\somefile.txt is not an unusually large (hundreds of MB) file. For that situation:
get-content c:\somedir\somefile.txt -readcount 1000 |
foreach {$_ -like 'abcd*'}