How to parse file name in powerShell - powershell

This is the name of my file myregistration_20180105041258_NOTIFICATION_1.zip and 20180105041258 the numbers are a timestamp. I've so many files of this format. These files will be posted to my share path every day. I've automated to download all the files. But I want to download daily files with help of date. Can anyone suggest me how can I do this using power shell???

If I have got this right, then your requirement is to change the numbers(in the file names) which are actually a timestamp, into a datetime format and the use this to download the files or do whatever operation you deem to.
For that, I would use the -split parameter to get the number from the filename and then convert the number into datetime format using the PoSh ParseExact function. The code will look something like this.
$string = " myregistration_20180105041258_NOTIFICATION_1.zip"
$array = #($string.Split('_'))
$datetime = [datetime]::parseexact($array[1], 'yyyyMMddhhmmss', $null)
Now your $datetime variable will contain the date of the corresponding file and you can use this to proceed further. If you have a bunch of files, you can loop through each of them using a foreach loop.

For example:
$original = "myregistration_20180105041258_NOTIFICATION_1.zip";
$trimmed = $original | Select-String -Pattern "myregistration" -InputObject {$_.TrimEnd("whatever you want to trim")}
P.S. It's possible also if you need to get the timestamp only to say:
$original -match "\d" and pull the value of it from $Matches[0].

Related

PowerShell: Is there a way to search an specific word in a file's name and open the file if it finds it?

I haven't been able to figure out how to make this task that sounds simple in PowerShell.
I am trying to make a powershell variable that represents a file only using a part of it's name, since the rest of the name changes periodically. This should represent a little better what is my intention.
#Each day the number changes except for the Name part.
Name1, Name2, Name3...
#Variable must be able to work regardless of the number it has since the Name part never changes.
$Variable: Volume\Folder\Name(X).exe
I'm sorry if i'm not explaining myself well enough.
I'll provide any aditional information that is needed.
Well, to me it seems to be two diiferent tasks at hand:
First your title suggests You are lokking for a way to check the filenames of files in a given directory i assume and run that file with the default filehandler (again i can only speculate)
# 1. task
$path="C:\myfolder\"
$mySearchKey="taxes"
$myItmes=Get-ChildItem -Path $myPath
foreach($item in $myItems){
if($item.name -like "*$mySearchkey*"){
$matchingPath=$path+$item.name
Invoke-Item $matchingPath
}
}
Secondly In your description and the code example the question seems to be evolving around the idea to create dynamic variables for filenames most likely for the files we where opening before, based on the day in relation to a start date:
#2. task
$afileName="Marry"
$startdate= Get-Date "2022-12-06"
$todays= get-date
$numberOfDays = New-TimeSpan -Start $startdate -End $todays
$numberOfDays++ # since a differnce of 0 days means your in the 1. day
$newPath="Volume\Folder\"+$afileName+$numberOfDays+".exe"
But I yet have to figure out your end-game. How are the two coming together?
Run script where you want to search.
$all_files = ls
$filename = Read-Host "Enter File Name"
foreach ($item in $filename)
{
if ($item -match $filename)
{
Get-Content $item
}
}

How do I get the format of creationtime.month to be double digits instead of single?

I have a script that takes the creation date of a file and injects it into an xml tag. Everything works but the formatting of the date shows 2019-4-3 and I need the format to be 2019-04-03.
I have tried the 'tostring(MM)' and that has not worked for me. Anyone have any ideas? Here is a snippet of the code where I think the issue is. I can post the whole script if anyone wants to see it.
$filename="C:\Users\Public\file.xml"
$filename2="C:\Users\Public\file2.xml"
$month = (Get-ChildItem $filename).CreationTime.Month
$day = (Get-ChildItem $filename).CreationTime.Day
$year = (Get-ChildItem $filename).CreationTime.Year
$hour = (Get-ChildItem $filename).CreationTime.Hour
$min = (Get-ChildItem $filename).CreationTime.Minute
$sec= (Get-ChildItem $filename).CreationTime.Second
$output=[string]$year+"-"+[string]$month+"-"+[string]$day+"T"+[string]$hour+":"+[string]$min+":"+[string]$sec+":00z"
Write-Host $output
The output of the dates are single digit and I need them double digits. Any ideas?
The following should work assuming you don't actually need each part of the datetime as a separate variable:
$filename="C:\Users\Public\file.xml"
(Get-ChildItem $filename).creationtime.toString('yyyy-MM-ddTHH:mm:ss')+':00z'
I don't know why the toString() method did not work for you previously unless you didn't quote contents inside the parentheses. The method doesn't always require an input argument, but with what you are trying it requires a string to be passed to it.
You are constructing this the hard way. Formatting dates and times as strings is fully explained here: https://ss64.com/ps/syntax-dateformats.html
A simpler way to do this, and faster since right now you are getting the file info 6 times right now, would be to use the built-in [datetime] method ToString().
(Get-Item $filename).CreationTimeUtc.ToString("yyyy-MM-ddTHH:mm:ss.00Z")
Notice that I used the CreationTimeUtc property instead of CreationTime, since the "Z" at the end of your string that you are creating indicates that this is the time in UTC (the "Z" stands for Zulu time, as explained in Wikipedia).
To complement TheMadTechnician's helpful answer:
Except for the T separating the date and time parts and a sub-second component, your format is the same as the standard u date/time format:
PS> (Get-Item /).CreationTimeUtc.ToString('u') -replace ' ', 'T'
2018-11-30T10:47:40Z
If you need an explicit zero-valued sub-second component, append -replace 'Z$', '.00Z' - note the use of ., not :, as the separator, because . is normally used.

Trying to format ticks as datetime and export to excel

I am struggling a bit with an issue I hope you can help me with.
I am using get-winevent to grab specific events from a computer and export the results to a csv.
I am setting a variable to hold all of the returned events and then using a foreach loop to step through all the events and export them to a csv file.
When I export the timecreated object, the data is formatted as date-time and I can sort oldest to newest or newest to oldest. What I am running into is that the default format of "timecreated" is "MM/DD/YYYY hh:mm ". This causes a problem in that, unless I can see seconds and milliseconds, a lot of these events appear to happen at the same time.
To resolve this, I have been using the following to format the date:
$ticks = [datetime]$event.timecreated.Ticks
$date = $ticks.Tostring("MM/dd/yyyy hh:mm:ss:fff")
This works well when I just output to the screen, the date shows exactly like I want it to. However, since the variable is a string, when I export the variable to excel I can’t sort based on time.
Does anyone know of a way to convert ticks to the display format I want, but keep it as datetime rather than a string? Or any way to grab the timecreated object and format it the way I want, without having to convert it to a string?
I'm beginning to think I may have to create a PSObject and handle it that way, but I am not sure I can do it even then.
Thanks for reading.
if i understand your whole query and excepted result.
I have tested what your are looking for and result it to we doesn't have to add "fff" to string date format on excel because it's doesn't work.
Try this :
$ticks = [datetime]$event.timecreated.Ticks
$date = $ticks.Tostring("MM/dd/yyyy hh:mm:ss")
The full example we have using for testing :
$events =Get-WinEvent -ListLog * | Where {$_.IsClassicLog -eq ‘True’}
$events | Select-Object LogMode, RecordCount, LogName, #{n="DateWrite";e={$_.LastWriteTime.ToString("dd/MM/yyyy hh:mm:ss")}} | Export-Csv -Path c:\fso\event_tester.csv -Encoding ascii -NoTypeInformation
At result have the excepted Date column :
Resources :
How to represent a DateTime in Excel
pandas output timestamps to_excel with microseconds

Powershell - Find & Replace Dates

I'm looking for a bit of assistance here. I currently have a Powershell script which adjusts the dates within a file. I'm looking to stop myself having to manually adjust these dates every time. What I need is to replace the date two days ago, with the date from yesterday.
I believe that I'd have to use (Get-Date).AddDays(-1) and (Get-Date).AddDays(-2) but I'm not exactly sure how I'd script this in!
What I currently have:
echo "Adjusting Import Dates"
(Get-Content D:\Temp\Example.txt).replace('20180917', '20180918') | Set-Content D:\Temp\Example.txt
You could try this:
$yesterday = (Get-Date).AddDays(-1).tostring("yyyyMMdd")
$twodaysago = (Get-Date).AddDays(-2).tostring("yyyyMMdd")
(Get-Content D:\Temp\Example.txt).replace($twodaysago, $yesterday) | Set-Content D:\Temp\Example.txt
You just introduce variables for the two dates and format them to the required date format.
There is probably some other way of replacing in files, but the above should work.

Powershell - rename file using Date Taken attribute

I have a stack load of images and videos on my Samsung phone. I copied these images to a USB then onto my PC.
I want to use Powershell to rename these files based on their Date Taken attribute.
Format required = yyyy-MM-dd HH.mm.ss ddd
I have been using a Powershell script (see below) that does this beautifully using the Date Modified attribute, but the copy above somehow changed the Date Modified value on me (WTH!), so I can't use that now (as its not accurate).
Get-ChildItem | Rename-Item -NewName {$_.LastWriteTime.ToString("yyyy-MM-dd HH.mm.ss ddd") + ($_.Extension)}
In summary - is there a way to change the file name based on the Date Taken file attribute? Suggestions I have seen online require use of the .NET System.Drawing.dll and convoluted code (I'm sure it works, but damn its ugly).
GG
Please checkout Set-PhotographNameAsDateTimeTaken Powershell module. It extract date and time from the picture and change name of the picture to it.
It allows to use -Recurse -Replace and -Verbose parameter. By default it will create reuslt folder at the same level as your working dir.
If you need change the format of the target names the code can be found here.
I 'glued' together a bunch of other answers to make a bulk script. Credit to those, but Chrome crashed and I lost those other webpages on Stack. This works on photo files only and will rename all files to YYYYMMDD_HHMMSS.jpg format.
Here it is:
$nocomment = [reflection.assembly]::LoadWithPartialName("System.Drawing")
get-childitem *.jpg | foreach {
$pic = New-Object System.Drawing.Bitmap($_.Name)
$bitearr = $pic.GetPropertyItem(36867).Value
$string = [System.Text.Encoding]::ASCII.GetString($bitearr)
$date = [datetime]::ParseExact($string,"yyyy:MM:dd HH:mm:ss`0",$Null)
[string] $newfilename = get-date $date -format yyyyMd_HHmmss
$newfilename += ".jpg"
$pic.Dispose()
rename-item $_ $newfilename -Force
$newfilename
}
In order to avoid this error:
New-Object : Cannot find type [System.Drawing.Bitmap]: verify that the assembly containing this type is
loaded.
...
Make sure the required assembly is loaded before executing the code above:
add-type -AssemblyName System.Drawing