Category: Microsoft

Navidrome, Clients and the Compilation MP3 Tag

As I outlined in a previous post, I switched from Jellyfin to Navidrome for my music. While on the whole I’m happy with the change, I discovered that Navidrome handles Various Artists albums such that if the Compilation tag isn’t set, it indexes the album from one into as many as there are artists. And, as outlined in the aforementioned post, this is not a bug, but by design. The intent is to account for different artists with the same album name, and that makes sense.

So I set out to attempt to automate the modification of the Compilation tag – a quest that turned out to be more complicated than I anticipated. The Compilation tag is apparently not a ‘standard’ tag. If you load up an mp3 in taglibsharp and have it vomit out all the tags, the Compilation tag won’t be among them. Here, try it yourself in PowerShell. You’ll have to update the path to your taglibsharp.dll and your test mp3 file.

Here’s an example output:

As you can see, no Compilation tag there. Compilation is technically an iTunes Flag Text Frame, and is set with a Boolean value (1 for Yup, 0 for Nope). It’s defined as TCMP. As of this writing id3.org is down, but here’s the archived page on this tag.

Given all this, I threw together the below. As per usual it’s unrefined, has almost zero error handling, and will be something I improve upon over time. This thing assumes your compilation albums are in directories formatted as “Various – Name of Album.”

Bonus: If you, like me, discovered you have a whole mess of compilation albums in directories with the format “VA – Album Title” instead of “Various – Album Title,” This one liner will help correct that.

Navidrome, Clients and Albums With Varying Artist Tags

I’m using Navidrome as my music server now, having switched from shoehorning Jellyfin into that role, and I quite like it. One thing I discovered, however, is that it – and quite a few clients that support it – rely on the Album Artist tag to help index files. Initially I found this problematic because many of my files didn’t have Album Artist populated. I solved this by writing a PowerShell script to copy the Perfomers tag data (Performers = Artist) to the Album Artist tag. I’ll share that in another post.

But then I discovered a different problem. If an album is a compilation or has variance in the artists from file to file (for example: This Guy feat. That Other Guy), it’d index files into separate albums of the same title. Navidrome’s developers confirmed that this is a feature, not a bug, and it makes sense. The solution for compilation albums is to set the Compilation tag to 1, which I haven’t automated yet but will shortly. The solution for non-comp albums is to make sure the Album Artists tag is consistent.

To accomplish this, I threw together the below script. It’s not optimized, it doesn’t have error handling or confirmation, and it’s apt to be destructive if you’re not careful. Still, it’s something you can build on, just as I inevitably will. As with all my music file related scripts, it requires taglib-sharp.dll. Obtain this file from TagLibSharp. You don’t have to futz with nuget or anything – just download the zipped package, yank the dll out of it, and put it in a subdir you’ll reference in the script.

This script will prompt for the full path to the files you wish to update, and then the name you wish to update the Album Artist tag to.

Powershell – Monitoring a log file

I had a situation at work where I needed to monitor a log file for a particular entry. I needed to be notified when that entry appeared. This log file gets created anew, with the current date, every day. Here’s what I came up with:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
while($true)
{
# get the date
$now = get-date
# create the log name from said date eg :20231223Err.txt
$fileName = '{0}{1}{2}Err.txt' -f $now.Year, $now.Month, $now.Day
# network path to said log
$fullPath = "\\path\e$\LogFiles\app\$($fileName)"

#I don't need this to run in perpetuity - it's a temp situation - so I'm just
#invoking this in a Powershell window and letting it rip.
Write-Host "[$(Get-Date)] Starting job for file $fullPath"
$latest = Start-Job -Arg $fullPath -ScriptBlock {
param($file)

# wait until the file exists, just in case
while(-not (Test-Path $file)){ sleep -sec 10 }
# matching the phrase Queue Count. could make all these variables
Get-Content $file -wait | where {$_ -match 'Queue Count'} |
foreach {
Send-MailMessage -SmtpServer SMTPSERVER -From me@email.com -To me@email.com -Subject 'Queue Count' -Body $_
write-host $_
}
}

# wait until date change
while($now.Date -eq (Get-Date).Date){ sleep -Sec 10 }

# kill the job and start anew
Write-Host "[$(Get-Date)] Stopping job for file $fullPath"
$latest | Stop-Job
}

The Magic of Logparser

I had a slew of IIS FTP logs to dig through for a work project. I needed unique visitor details, and I needed it from a month of logs. Some of these daily logs were in excess of 40mb. I threw together a PowerShell script to do just so, kicked it off, and waited. And waited. I reconfigured the script to be more efficient in its processing, kicked it off again, and waited. And waited. And researched, because this was taking far too long. And – late to the game, I know – I found Microsoft’s Logparser. Logparser is a free tool, and it’s filled with magic. With one simple query it managed to pull the raw data I needed from the log files in *seconds*.

1
2
3
4
5
#log files in c:\temp\iis, results to same path

logparser "SELECT DISTINCT c-ip, cs-username INTO C:\temp\iis\results.txt FROM 'C:\temp\iis\*.log'" -i:W3C -o:W3C

#

In less than a minute I had a text file of unique visits gleaned from 550 MB worth of plaintext log files. From there I could use PowerShell to filter out any IP dupes (some connections do not have user details, thus producing some leftover duplication) and resolve hostnames from IP addresses to create a final masterlist. I’m not sure how Logparser does what it does so quickly.

Windows 10, NVidia, and Paint Shop Pro

I’m a luddite – I love Paint Shop Pro 9. Yeah, I use Illustrator and Photoshop and Inkscape and Gimp and all that goodness but, in a pinch, PSP9’s been my go-to quick and dirty image manipulator forever.

Then I got a fancy new laptop with a fancy new video card… and PSP9 wouldn’t work. It wouldn’t produce a window on launch, even though I could see it there in the task manager, running. And when I uninstalled and tried to reinstall, it hung for infinity on “registering modules.”

Continue reading

VisualCron – Powershell Network Path Truncation

I set up a VisualCron job to kick off a Powershell script to reach out to certain directories – built dynamically from an array – to check for content. The script ran perfectly when invoked manually, but through VisualCron it would error out with a truncated path:

The above path should have been \\atldireng03\e$\download\. I just could not get the path to resolve. The script that builds the path looks similar to this:

Ultimately the issue was one of rights. The account VisualCron was utilizing to invoke the script did not have rights to the administrative share path being built by the script. Change the account to an administrator on the remote server and the script ran like a charm. Now, that it would error out with this weird truncated path problem rather than something referring to a lack of sufficient rights is frustrating. I suppose it’s because it could not ‘see’ the path (hence “it does not exist”), but were you to manually attempt to map to a path you hadn’t rights to pretty much all OSes would return you some kind of informative error about insufficient rights. Not here. And for the record, I haven’t tried running the script manually through a Powershell prompt without rights to the paths to see what happens. It’s entirely probable this uninformative error is on Powershell’s side and not VisualCron.