From 5b8407c85b196a84037b89e12f63739607a60b2f Mon Sep 17 00:00:00 2001 From: jvlflame Date: Sun, 30 Aug 2020 00:16:18 -0700 Subject: [PATCH] Updates --- src/Javinizer/Private/Convert-JVString.ps1 | 72 ++++ src/Javinizer/Public/Get-DmmData.ps1 | 1 + src/Javinizer/Public/Get-JVAggregatedData.ps1 | 43 ++- src/Javinizer/Public/Get-JVData.ps1 | 75 ++-- src/Javinizer/Public/Get-JVItem.ps1 | 4 +- src/Javinizer/Public/Get-JVNfo.ps1 | 124 +++++++ src/Javinizer/Public/Set-JVMovie.ps1 | 331 ++++++++++++++++++ src/Javinizer/javinizerSettings.json | 48 +-- 8 files changed, 636 insertions(+), 62 deletions(-) create mode 100644 src/Javinizer/Private/Convert-JVString.ps1 create mode 100644 src/Javinizer/Public/Get-JVNfo.ps1 create mode 100644 src/Javinizer/Public/Set-JVMovie.ps1 diff --git a/src/Javinizer/Private/Convert-JVString.ps1 b/src/Javinizer/Private/Convert-JVString.ps1 new file mode 100644 index 00000000..9e853fbc --- /dev/null +++ b/src/Javinizer/Private/Convert-JVString.ps1 @@ -0,0 +1,72 @@ +function Convert-JVString { + [CmdletBinding()] + param ( + [Parameter(Mandatory = $true)] + [PSObject]$Data, + [Parameter(Mandatory = $true)] + [String]$FormatString, + [Parameter()] + [Int]$PartNumber, + [Parameter()] + [Int]$MaxTitleLength + ) + + process { + # These symbols need to be removed to create a valid Windows filesystem name + $invalidSymbols = @( + '\', + '/', + ':', + '*', + '?', + '"', + '<', + '>', + '|', + "'" + ) + + if ($maxTitleLength) { + if ($Data.Title.Length -ge $MaxTitleLength) { + $shortTitle = $Data.Title.Substring(0, $MaxTitleLength) + $splitTitle = $shortTitle -split ' ' + if ($splitTitle.Count -gt 1) { + # Remove the last word of the title just in case it is cut off + $title = ($splitTitle[0..($splitTitle.Length - 2)] -join ' ') + if ($title[-1] -match '\W') { + $Data.Title = ($title.Substring(0, $title.Length - 2)) + '...' + } else { + $Data.Title = $title + '...' + } + } else { + $Data.Title = $shortTitle + '...' + } + } + } + + $convertedName = $FormatString ` + -replace '', "$($Data.Id)" ` + -replace '', "$($Data.Title)" ` + -replace '<RELEASEDATE>', "$($Data.ReleaseDate)" ` + -replace '<YEAR>', "$(($Data.ReleaseDate -split '-')[0])" ` + -replace '<STUDIO>', "($($Data.Maker)" ` + -replace '<RUNTIME>', "$($Data.Runtime)" ` + -replace '<SET>', "$($Data.Series)" ` + -replace '<LABEL>', "$($Data.Label)" ` + -replace '<ORIGINALTITLE>', "$($Data.AlternateTitle)" + + foreach ($symbol in $invalidSymbols) { + if ([regex]::Escape($symbol) -eq '/') { + $convertedName = $convertedName -replace [regex]::Escape($symbol), '-' + } else { + $convertedName = $convertedName -replace [regex]::Escape($symbol), '' + } + } + + if ($PartNumber) { + $convertedName += "-pt$PartNumber" + } + + Write-Output $convertedName + } +} diff --git a/src/Javinizer/Public/Get-DmmData.ps1 b/src/Javinizer/Public/Get-DmmData.ps1 index 8d16baa2..0312e526 100644 --- a/src/Javinizer/Public/Get-DmmData.ps1 +++ b/src/Javinizer/Public/Get-DmmData.ps1 @@ -14,6 +14,7 @@ function Get-DmmData { $webRequest = Invoke-WebRequest -Uri $dmmUrl -Method Get -Verbose:$false } catch { Write-JLog -Level Error -Message "Error [GET] on URL [$dmmUrl]: $PSItem" + return } $movieDataObject = [PSCustomObject]@{ diff --git a/src/Javinizer/Public/Get-JVAggregatedData.ps1 b/src/Javinizer/Public/Get-JVAggregatedData.ps1 index fd92db7a..e64255d9 100644 --- a/src/Javinizer/Public/Get-JVAggregatedData.ps1 +++ b/src/Javinizer/Public/Get-JVAggregatedData.ps1 @@ -1,10 +1,9 @@ function Get-JVAggregatedData { - [CmdletBinding(DefaultParameterSetName = 'Pipeline')] + [CmdletBinding(DefaultParameterSetName = 'Setting')] param ( - [Parameter(Mandatory = $true, ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Pipeline')] - [Parameter(Mandatory = $true, ParameterSetName = 'Setting')] + [Parameter(Mandatory = $true, ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] [PSObject]$Data, - [Parameter(Mandatory = $true, ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Pipeline')] + [Parameter(Mandatory = $true, ParameterSetName = 'Setting')] [PSObject]$Settings, [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] [Alias('sort.metadata.priority.actress')] @@ -50,7 +49,31 @@ function Get-JVAggregatedData { [Array]$TitlePriority, [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] [Alias('sort.metadata.priority.trailerurl')] - [Array]$TrailerUrlPriority + [Array]$TrailerUrlPriority, + [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] + [Alias('sort.metadata.displayname')] + [String]$DisplayNameFormat, + [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] + [Alias('sort.metadata.firstnameorder')] + [Boolean]$FirstNameOrder, + [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] + [Alias('sort.metadata.thumbcsv')] + [Boolean]$ThumbCsv, + [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] + [Alias('sort.metadata.thumbcsv.convertalias')] + [Boolean]$ThumbCsvAlias, + [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] + [Alias('sort.metadata.genre.normalize')] + [Boolean]$NormalizeGenre, + [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] + [Alias('sort.metadata.genre.ignore')] + [Array]$IgnoreGenre, + [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] + [Alias('sort.metadata.requiredfield')] + [Array]$RequiredField, + [Parameter(ValueFromPipelineByPropertyName = $true, ParameterSetName = 'Setting')] + [Alias('sort.metadata.maxtitlelength')] + [Int]$MaxTitleLength ) process { @@ -70,10 +93,12 @@ function Get-JVAggregatedData { $ScreenshotUrlPriority = $Settings.'sort.metadata.priority.screenshoturl' $TitlePriority = $Settings.'sort.metadata.priority.title' $TrailerUrlPriority = $Settings.'sort.metadata.priority.trailerurl' + $DisplayNameFormat = $Settings.'sort.metadata.nfo.displayname' } $aggregatedDataObject = [PSCustomObject]@{ Id = $null + DisplayName = $null Title = $null AlternateTitle = $null Description = $null @@ -119,14 +144,16 @@ function Get-JVAggregatedData { } else { $aggregatedDataObject.$field = $sourceData.$field } - Write-Debug "[$field] [$priority] Set to [$($sourceData.$field | ConvertTo-Json -Compress)]" + Write-JLog -Level Debug -Message "[$($Data[0].Id)] [$($MyInvocation.MyCommand.Name)] [$field - $priority] Set to [$($sourceData.$field | ConvertTo-Json -Compress)]" } } } + $aggregatedDataObject.DisplayName = Convert-JVString -Data $aggregatedDataObject -FormatString $DisplayNameFormat + + $dataObject = [PSCustomObject]@{ - Data = $aggregatedDataObject - Settings = $Settings + Data = $aggregatedDataObject } Write-Output $dataObject diff --git a/src/Javinizer/Public/Get-JVData.ps1 b/src/Javinizer/Public/Get-JVData.ps1 index eba0a978..775478fb 100644 --- a/src/Javinizer/Public/Get-JVData.ps1 +++ b/src/Javinizer/Public/Get-JVData.ps1 @@ -1,7 +1,7 @@ function Get-JVData { [CmdletBinding()] param ( - [Parameter(Mandatory = $true, Position = 0)] + [Parameter(Position = 0, ValueFromPipelineByPropertyName = $true)] [String]$Id, [Parameter(ValueFromPipelineByPropertyName = $true)] [Alias('scraper.movie.r18')] @@ -40,104 +40,123 @@ function Get-JVData { process { $javinizerDataObject = @() + if ($Settings) { + $R18 = $Settings.'scraper.movie.r18' + $R18Zh = $Settings.'scraper.movie.r18zh' + $Jav321 = $Settings.'scraper.movie.jav321' + $Javlibrary = $Settings.'scraper.movie.javlibrary' + $JavlibraryJa = $Settings.'scraper.movie.javlibraryja' + $JavlibraryZh = $Settings.'scraper.movie.javlibraryzh' + $Dmm = $Settings.'scraper.movie.dmm' + $Javbus = $Settings.'scraper.movie.javbus' + $JavbusJa = $Settings.'scraper.movie.javbusja' + $JavbusZh = $Settings.'scraper.movie.javbuszh' + } + try { if ($R18) { - Write-JLog -Level Info -Message "Searching [R18] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching R18" Start-ThreadJob -Name "$Id-R18" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-R18Url -Id $using:Id -Language en | Get-R18Data } | Out-Null } - + if ($R18Zh) { - Write-JLog -Level Info -Message "Searching [R18Zh] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching R18Zh" Start-ThreadJob -Name "$Id-R18Zh" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-R18Url -Id $using:Id -Language zh | Get-R18Data } | Out-Null } - + if ($Javlibrary) { - Write-JLog -Level Info -Message "Searching [Javlibrary] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching Javlibrary" Start-ThreadJob -Name "$Id-Javlibrary" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-JavlibraryUrl -Id $using:Id -Language en | Get-JavlibraryData } | Out-Null } - + if ($JavlibraryJa) { - Write-JLog -Level Info -Message "Searching [JavlibraryJa] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching JavlibraryJa" Start-ThreadJob -Name "$Id-JavlibraryJa" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-JavlibraryUrl -Id $using:Id -Language ja | Get-JavlibraryData } | Out-Null } - + if ($JavlibraryZh) { - Write-JLog -Level Info -Message "Searching [JavlibraryZh] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching JavlibraryZh" Start-ThreadJob -Name "$Id-JavlibraryZh" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-JavlibraryUrl -Id $using:Id -Language zh | Get-JavlibraryData } | Out-Null } - + if ($Dmm) { - Write-JLog -Level Info -Message "Searching [Dmm] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching Dmm" Start-ThreadJob -Name "$Id-Dmm" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-DmmUrl -Id $using:Id | Get-DmmData } | Out-Null } - + if ($Javbus) { - Write-JLog -Level Info -Message "Searching [Javbus] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching Javbus" Start-ThreadJob -Name "$Id-Javbus" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-JavbusUrl -Id $using:Id -Language en | Get-JavbusData } | Out-Null } - + if ($JavbusJa) { - Write-JLog -Level Info -Message "Searching [JavbusJa] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching JavbusJa" Start-ThreadJob -Name "$Id-JavbusJa" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-JavbusUrl -Id $using:Id -Language ja | Get-JavbusData } | Out-Null } - + if ($JavbusZh) { - Write-JLog -Level Info -Message "Searching [JavbusZh] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching JavbusZh" Start-ThreadJob -Name "$Id-JavbusZh" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-JavbusUrl -Id $using:Id -Language zh | Get-JavbusData } | Out-Null } - + if ($Jav321) { - Write-JLog -Level Info -Message "Searching [Jav321] for Id: [$Id]" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Searching Jav321" Start-ThreadJob -Name "$Id-Jav321" -ScriptBlock { Import-Module X:\git\Projects\JAV-Organizer\src\Javinizer\Javinizer.psm1 Get-Jav321Url -Id $using:Id | Get-Jav321Data } | Out-Null } - - # Wait for all jobs to complete to write to the combined data object - $javinizerDataObject = Get-Job | Receive-Job -AutoRemoveJob -Wait -Force + # Wait-Job is used separately rather than in a pipeline due to the PowerShell.Exit job that is being created during the first-run of this function + Write-Debug "[$Id] [$($MyInvocation.MyCommand.Name)] Waiting for jobs to complete" + $jobId = @((Get-Job | Where-Object { $_.Name -like "$Id*" } | Select-Object Id).Id) + Wait-Job -Id $jobId | Out-Null + + Write-Debug "[$Id] [$($MyInvocation.MyCommand.Name)] Jobs completed" + $javinizerDataObject = Get-Job -Id $jobId | Receive-Job + + $hasData = ($javinizerDataObject | Select-Object Source).Source + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Data successfully retrieved from sources [$hasData]" $dataObject = [PSCustomObject]@{ - Data = $javinizerDataObject - Settings = $Settings + Data = $javinizerDataObject } - + Write-Output $dataObject } catch { - Write-JLog -Level Error -Message "Error occured during scraper jobs: $PSItem" + Write-JLog -Level Error -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Error occured during scraper jobs: $PSItem" } finally { # Remove all completed or running jobs before exiting this script # If jobs remain after closure, it may cause issues in concurrent runs - Write-JLog -Level Debug -Message "Stopping/removing all completed/running jobs" + Write-JLog -Level Debug -Message "[$Id] [$($MyInvocation.MyCommand.Name)] Stopping/removing all completed/running jobs" Get-Job | Remove-Job -Force } } diff --git a/src/Javinizer/Public/Get-JVItem.ps1 b/src/Javinizer/Public/Get-JVItem.ps1 index 2dbebe2d..d54d038e 100644 --- a/src/Javinizer/Public/Get-JVItem.ps1 +++ b/src/Javinizer/Public/Get-JVItem.ps1 @@ -53,8 +53,8 @@ function Get-JVItem { } } else { foreach ($file in $files) { - $fileObject += $file | Convert-JVTitle -Strict:$Strict -RegexEnabled:$RegexEnabled - } + $fileObject += $file | Convert-JVTitle -Strict:$Strict -RegexEnabled:$RegexEnabled + } } Write-Output $fileObject diff --git a/src/Javinizer/Public/Get-JVNfo.ps1 b/src/Javinizer/Public/Get-JVNfo.ps1 new file mode 100644 index 00000000..72124699 --- /dev/null +++ b/src/Javinizer/Public/Get-JVNfo.ps1 @@ -0,0 +1,124 @@ +function Get-JVNfo { + [CmdletBinding()] + param( + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$Id, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$DisplayName, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$Title, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$AlternateTitle, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$Description, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$ReleaseDate, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Int]$Runtime, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$Director, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$Maker, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$Label, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$Series, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [PSObject]$Actress, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Array]$Genre, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$CoverUrl, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Array]$ScreenshotUrl, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [String]$TrailerUrl, + [Parameter()] + [Boolean]$NameOrder, + [Parameter()] + [Boolean]$AddTag + ) + + process { + function Convert-NfoChar { + [CmdletBinding()] + param ( + [Parameter(Mandatory = $true, Position = 0, ValueFromPipeline = $true)] + [AllowEmptyString()] + [String]$String + ) + + process { + $newString = ((($String -replace '&', '&') -replace '<', '(') -replace '>', ')') -replace '/', '-' + Write-Output $newString + } + } + + $DisplayName = Convert-NfoChar -String $DisplayName -ErrorAction SilentlyContinue + $AlternateTitle = Convert-NfoChar -String $AlternateTitle -ErrorAction SilentlyContinue + $Title = Convert-NfoChar -String $Title -ErrorAction SilentlyContinue + $Description = Convert-NfoChar -String $Description -ErrorAction SilentlyContinue + $Director = Convert-NfoChar -String $Director -ErrorAction SilentlyContinue + $Maker = Convert-NfoChar -String $Maker -ErrorAction SilentlyContinue + $Label = Convert-NfoChar -String $Label -ErrorAction SilentlyContinue + $Series = Convert-NfoChar -String $Series -ErrorAction SilentlyContinue + + $nfoString = @" +<?xml version="1.0" encoding="UTF-8" standalone="yes"?> +<movie> + <title>$DisplayName + $AlternateTitle + $Id + $ReleaseDate + $Director + $Maker + $Description + $Runtime + $TrailerUrl + XXX + $Series + +"@ + + if ($AddTag) { + $tagNfoString = @" + $Series + +"@ + $nfoString = $nfoString + $tagNfoString + } + + foreach ($item in $Genre) { + $item = Convert-NfoChar -String $item + $genreNfoString = @" + $item + +"@ + $nfoString = $nfoString + $genreNfoString + } + + foreach ($item in $Actress) { + if ($NameOrder) { + $ActressName = ("$($item.FirstName) $($item.LastName)").Trim() + } else { + $ActressName = ("$($item.LastName) $($item.FirstName)").Trim() + } + $actressNfoString = @" + + $ActressName + $($item.ThumbUrl) + Actress + + +"@ + } + + $nfoString = $nfoString + $actressNfoString + $endNfoString = @" + +"@ + $nfoString = $nfoString + $endNfoString + + Write-Output $nfoString + } +} diff --git a/src/Javinizer/Public/Set-JVMovie.ps1 b/src/Javinizer/Public/Set-JVMovie.ps1 new file mode 100644 index 00000000..3a4a57af --- /dev/null +++ b/src/Javinizer/Public/Set-JVMovie.ps1 @@ -0,0 +1,331 @@ +function Set-JVMovie { + [CmdletBinding(SupportsShouldProcess = $true)] + param ( + [Parameter(Mandatory = $true, Position = 0)] + [System.IO.FileInfo]$Path, + [Parameter(Mandatory = $true, Position = 1)] + [System.IO.DirectoryInfo]$DestinationPath, + [Parameter(Mandatory = $true)] + [PSObject]$Settings, + [Parameter(Mandatory = $true, ValueFromPipelineByPropertyName = $true)] + [PSObject]$Data, + [Parameter()] + [Int]$PartNumber, + [Parameter()] + [Switch]$Force, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.movetofolder')] + [Boolean]$MoveToFolder, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.renamefile')] + [Boolean]$RenameFile, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.maxpathlength')] + [Boolean]$MaxPathLength, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.maxtitlelength')] + [Boolean]$MaxTitleLength, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.create.nfo')] + [Boolean]$CreateNfo, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.create.nfoperfile')] + [Boolean]$CreateNfoPerFile, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.download.actressimg')] + [Boolean]$DownloadActressImg, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.download.thumbimg')] + [Boolean]$DownloadThumbImg, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.download.posterimg')] + [Boolean]$DownloadPosterImg, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.download.screenshotimg')] + [Boolean]$DownloadScreenshotImg, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.download.trailervid')] + [Boolean]$DownloadTrailerVid, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.format.file')] + [String]$FileFormat, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.format.folder')] + [String]$FolderFormat, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.format.posterimg')] + [String]$PosterFormat, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.format.thumbimg')] + [String]$ThumbnailFormat, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.format.trailervid')] + [String]$TrailerFormat, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.format.nfo')] + [String]$NfoFormat, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.format.screenshotimg')] + [String]$ScreenshotImgFormat, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.format.screenshotfolder')] + [String]$ScreenshotFolderFormat, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.format.actressimgfolder')] + [String]$ActressFolderFormat, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.metadata.nfo.displayname')] + [String]$DisplayName, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.metadata.nfo.seriesastag')] + [Boolean]$AddTag, + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('sort.metadata.nfo.firstnameorder')] + [Boolean]$NameOrder + ) + + begin { + if (-not $PSBoundParameters.ContainsKey('Confirm')) { + $ConfirmPreference = $PSCmdlet.SessionState.PSVariable.GetValue('ConfirmPreference') + } + if (-not $PSBoundParameters.ContainsKey('WhatIf')) { + $WhatIfPreference = $PSCmdlet.SessionState.PSVariable.GetValue('WhatIfPreference') + } + } + + process { + <# Pre-impact code #> + if ($Settings) { + $MoveToFolder = $Settings.'sort.movetofolder' + $RenameFile = $Settings.'sort.renamefile' + $MaxPathLength = $Settings.'sort.maxpathlength' + $MaxTitleLength = $Settings.'sort.maxtitlelength' + $CreateNfo = $Settings.'sort.create.nfo' + $CreateNfoPerFile = $Settings.'sort.create.nfoperfile' + $DownloadActressImg = $Settings.'sort.download.actressimg' + $DownloadThumbImg = $Settings.'sort.download.screenshotimg' + $DownloadPosterImg = $Settings.'sort.download.posterimg' + $DownloadScreenshotImg = $Settings.'sort.download.screenshotimg' + $DownloadTrailerVid = $Settings.'sort.download.trailervid' + $FileFormat = $Settings.'sort.format.file' + $FolderFormat = $Settings.'sort.format.folder' + $PosterFormat = $Settings.'sort.format.posterimg' + $ThumbnailFormat = $Settings.'sort.format.thumbimg' + $TrailerFormat = $Settings.'sort.format.trailervid' + $NfoFormat = $Settings.'sort.format.nfo' + $ScreenshotImgFormat = $Settings.'sort.format.screenshotimg' + $ScreenshotFolderFormat = $Settings.'sort.format.screenshotfolder' + $ActorFolderFormat = $Settings.'sort.format.actressimgfolder' + $DisplayName = $Settings.'sort.metadata.nfo.displayname' + $AddTag = $Settings.'sort.metadata.nfo.seriesastag' + $NameOrder = $Settings.'sort.metadata.nfo.firstnameorder' + } + + $fileName = Convert-JVString -Data $Data -Format $FileFormat -PartNumber $PartNumber + $folderName = Convert-JVString -Data $Data -Format $FolderFormat + $nfoName = Convert-JVString -Data $Data -Format $NfoFormat + $thumbName = Convert-JVString -Data $Data -Format $ThumbnailFormat + $posterName = Convert-JVString -Data $Data -Format $PosterFormat + $trailerName = Convert-JVString -Data $Data -Format $TrailerFormat + $screenshotImgName = Convert-JVString -Data $Data -Format $ScreenshotImgFormat + $screenshotFolderName = Convert-JVString -Data $Data -Format $ScreenshotFolderFormat + $actorFolderName = Convert-JVString -Data $Data -Format $ActorFolderFormat + + if ($MoveToFolder) { + if ($DestinationPath) { + $folderPath = Join-Path -Path $DestinationPath -ChildPath $folderName + } else { + $folderPath = Join-Path -Path $Path -ChildPath $folderName + } + } else { + if ($DestinationPath) { + $folderPath = $DestinationPath + } else { + $folderPath = (Get-Item -LiteralPath $Path).Directory + } + } + + Write-JLog -Level Debug -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] The destination folderPath is [$folderPath]" + + <# $pathLength = (Join-Path -Path $folderPath -ChildPath $fileName).Length + if ($pathLength -gt $MaxPathLength) { + Write-Warning "[$(Get-TimeStamp)][$($MyInvocation.MyCommand.Name)] Skipped: [$($DataObject.OriginalFileName)] Folder path length limitations: [$pathLength characters]" + continue + } #> + + if ($Force -or $PSCmdlet.ShouldProcess($Path)) { + # We do not want to recreate the destination folder if it already exists + try { + if (!(Test-Path -LiteralPath $folderPath)) { + New-Item -Path $folderPath -ItemType Directory | Out-Null + Write-JLog -Level Debug -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] New directory created at path [$folderPath]" + } + } catch { + Write-JLog -Level Error -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Error occurred when creating destination folder path [$folderPath]: $PSItem" + return + } + + if ($CreateNfo) { + Write-JLog -Level Info "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Creating nfo file" + try { + $nfoPath = Join-Path -Path $folderPath -ChildPath "$nfoName.nfo" + $nfoContents = $Data | Get-JVNfo -NameOrder $NameOrder -AddTag $AddTag + $nfoContents | Out-File -FilePath $nfoPath + Write-JLog -Level Debug -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Nfo file created at path [$nfoPath]" + } catch { + Write-JLog -Level Error -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Error occurred when creating nfo file [$nfoPath]: $PSItem" + return + } + } + + if ($DownloadThumbImg) { + if ($null -ne $Data.CoverUrl) { + Write-JLog -Level Info "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Downloading thumbnail image" + try { + $webClient = New-Object System.Net.WebClient + $thumbPath = Join-Path -Path $folderPath -ChildPath "$thumbName.jpg" + if ($Force) { + $webClient.DownloadFile(($Data.CoverUrl).ToString(), $thumbPath) + } elseif ((!(Test-Path -LiteralPath $thumbPath))) { + $webClient.DownloadFile(($Data.CoverUrl).ToString(), $thumbPath) + } + Write-JLog -Level Debug -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Thumbnail image [$($Data.CoverUrl)] downloaded to path [$thumbPath]" + } catch { + Write-JLog -Level Error -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Error occurred when creating thumbnail image file [$thumbPath]: $PSItem" + return + } + + if ($DownloadPosterImg) { + Write-JLog -Level Info "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Creating poster image" + try { + $cropScript = Join-Path -Path ((Get-Item $PSScriptRoot).Parent) -ChildPath 'crop.py' + Write-JLog -Level Debug "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] crop.py path located at path [$cropScript]" + $posterPath = Join-Path $folderPath -ChildPath "$posterName.jpg" + $pythonThumbPath = $thumbPath -replace '\\', '/' + $pythonPosterPath = $posterPath -replace '\\', '/' + + if ($Force) { + if ([System.Environment]::OSVersion.Platform -eq 'Win32NT') { + python $cropScript $pythonThumbPath $pythonPosterPath + } elseif ([System.Environment]::OSVersion.Platform -eq 'Unix') { + python3 $cropScript $pythonThumbPath $pythonPosterPath + } + } elseif (!(Test-Path -LiteralPath $posterPath)) { + if ([System.Environment]::OSVersion.Platform -eq 'Win32NT') { + python $cropScript $pythonThumbPath $pythonPosterPath + } elseif ([System.Environment]::OSVersion.Platform -eq 'Unix') { + python3 $cropScript $pythonThumbPath $pythonPosterPath + } + } + Write-JLog -Level Debug -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Poster image [$thumbPath] cropped to path [$posterPath]" + } catch { + Write-JLog -Level Error -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Error occurred when creating poster image file [$posterPath]: $PSItem" + return + } + } + } + } + + if ($DownloadActressImg) { + if ($null -ne $Data.Actress) { + Write-JLog -Level Info "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Downloading actress images" + try { + $webClient = New-Object System.Net.WebClient + $actorFolderPath = Join-Path -Path $folderPath -ChildPath $actorFolderName + if (!(Test-Path -LiteralPath $actorFolderPath)) { + New-Item -Path $actorFolderPath -ItemType Directory -Force:$Force | Out-Null + } + + $nfoXML = [xml]$nfoContents + foreach ($actress in $nfoXML.movie.actor) { + if ($actress.thumb -ne '') { + $newName = ($actress.name -split ' ') -join '_' + $actressThumbPath = Join-Path -Path $actorFolderPath -ChildPath "$newName.jpg" + + if ($Force) { + $webClient.DownloadFile($actress.thumb, $actressThumbPath) + } elseif (!(Test-Path -LiteralPath $actressThumbPath)) { + $webClient.DownloadFile($actress.thumb, $actressThumbPath) + } + Write-JLog -Level Debug -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Actress image file [$($actress.thumb)] downloaded to path [$actressThumbPath]" + } + } + } catch { + Write-JLog -Level Error -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Error occurred when creating actress image files: $PSItem" + return + } + } + } + + if ($DownloadScreenshotImg) { + if ($null -ne $Data.ScreenshotUrl) { + Write-JLog -Level Info "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Downloading screenshot images" + try { + $index = 1 + $webClient = New-Object System.Net.WebClient + $screenshotFolderPath = Join-Path $folderPath -ChildPath $screenshotFolderName + if (!(Test-Path -LiteralPath $screenshotFOlderPath)) { + New-Item -Path $screenshotFolderPath -ItemType Directory -Force:$Force -ErrorAction SilentlyContinue | Out-Null + } + + foreach ($screenshot in $Data.ScreenshotUrl) { + $screenshotPath = Join-Path -Path $screenshotFolderPath -ChildPath "$screenshotImgName$index.jpg" + if ($Force.IsPresent) { + $webClient.DownloadFile($screenshot, $screenshotPath) + } elseif (!(Test-Path -LiteralPath $screenshotPath)) { + $webClient.DownloadFile($screenshot, $screenshotPath) + } + $index++ + Write-JLog -Level Debug -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Screenshot image file [$screenshot] downloaded to path [$screenshotPath]" + } + } catch { + Write-JLog -Level Error -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Error occurred when creating screenshot image files: $PSItem" + return + } + } + } + + if ($DownloadTrailerVid) { + if ($null -ne $Data.TrailerUrl) { + Write-JLog -Level Info "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Downloading trailer video" + try { + $trailerPath = Join-Path -Path $folderPath -ChildPath "$trailerName.mp4" + if ($Force.IsPresent) { + $webClient.DownloadFile($Data.TrailerUrl, $trailerPath) + } elseif (!(Test-Path -LiteralPath $trailerPath)) { + $webClient.DownloadFile($Data.TrailerUrl, $trailerPath) + } + Write-JLog -Level Debug -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Trailer video [$($Data.TrailerUrl)] downloaded to path [$trailerPath]" + } catch { + Write-JLog -Level Error -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Error occurred when creating trailer video file [$($Data.TrailerUrl)] to [$trailerName]: $PSItem" + return + } + } + } + + if ($RenameFile) { + try { + $filePath = Join-Path -Path $folderPath -ChildPath "$fileName$((Get-Item -LiteralPath $Path).Extension)" + if ((Get-Item -LiteralPath $DestinationPath).Directory -ne (Get-Item -LiteralPath $Path).Directory) { + Move-Item -LiteralPath $Path -Destination $filePath + Write-JLog -Level Info "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Completed sort on file [$Path] to [$filePath]" + } + } catch { + Write-JLog -Level Error -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Error occurred when renaming and moving file [$Path] to [$filePath]: $PSItem" + return + } + } else { + try { + $filePath = Join-Path -Path $folderPath -ChildPath (Get-Item -LiteralPath $Path).Name + if ((Get-Item -LiteralPath $DestinationPath).Directory -ne (Get-Item -LiteralPath $Path).Directory) { + Move-Item -LiteralPath $Path -Destination $filePath + Write-JLog -Level Info "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Completed sort on file [$Path] to [$filePath]" + } + } catch { + Write-JLog -Level Error -Message "[$($Data.Id)] [$($MyInvocation.MyCommand.Name)] Error occurred when renaming and moving file [$Path] to [$filePath]: $PSItem" + return + } + } + } + } +} diff --git a/src/Javinizer/javinizerSettings.json b/src/Javinizer/javinizerSettings.json index 0055fccb..d88a4a0b 100644 --- a/src/Javinizer/javinizerSettings.json +++ b/src/Javinizer/javinizerSettings.json @@ -4,13 +4,13 @@ "scraper.movie.javbus": 0, "scraper.movie.javbusja": 0, "scraper.movie.javlibrary": 1, - "scraper.movie.javlibraryja": 1, - "scraper.movie.javlibraryzh": 1, + "scraper.movie.javlibraryja": 0, + "scraper.movie.javlibraryzh": 0, "scraper.movie.r18": 1, "scraper.movie.r18zh": 0, "scraper.multiThrottle": 5, - "match.minFileSize": 0, - "match.includedFileExtension": [ + "match.minimumfilesize": 0, + "match.includedfileextension": [ ".asf", ".avi", ".flv", @@ -21,37 +21,37 @@ ".rmvb", ".wmv" ], - "match.excludedFileString": [ + "match.excludedfilestring": [ "*-trailer.*", "*-5.*" ], - "match.regex": 1, + "match.regex": 0, "match.regex.string": "([a-zA-Z|tT28]+-\\d+z{0,1}Z{0,1}e{0,1}E{0,1})(?:-pt){0,1}(\\d{1,2})?", - "match.regex.idMatch": 1, - "match.regex.ptMatch": 2, + "match.regex.idmatch": 1, + "match.regex.ptmatch": 2, "sort.movetofolder": 1, "sort.renamefile": 1, - "sort.maxtitlelength": 100, "sort.maxpathlength": 255, + "sort.maxtitlelength": 100, "sort.create.nfo": 1, - "sort.create.nfo.perfile": 1, - "sort.download.actressimg": 0, + "sort.create.nfoperfile": 1, + "sort.download.actressimg": 1, "sort.download.thumbimg": 1, "sort.download.posterimg": 1, "sort.download.screenshotimg": 1, "sort.download.trailervid": 1, - "sort.rename.file": "", - "sort.rename.folder": " [] - (<YEAR>)", - "sort.rename.poster": "folder", - "sort.rename.thumbnail": "fanart", - "sort.rename.trailer": "<ID>-trailer", - "sort.rename.nfo": "<ID>", - "sort.rename.screenshot.imgprefix": "fanart", - "sort.rename.screenshot.folder": "extrafanart", - "sort.rename.actorimg.folder": ".actors", - "sort.metadata.displayname": "[<ID>] <TITLE>", - "sort.metadata.seriesastag": 1, - "sort.metadata.firstnameorder": 0, + "sort.format.file": "<ID>", + "sort.format.folder": "<ID> - <TITLE> (<YEAR>)", + "sort.format.posterimg": "folder", + "sort.format.thumbimg": "fanart", + "sort.format.trailervid": "<ID>-trailer", + "sort.format.nfo": "<ID>", + "sort.format.screenshotimg": "fanart", + "sort.format.screenshotfolder": "extrafanart", + "sort.format.actressimgfolder": ".actors", + "sort.metadata.nfo.displayname": "[<ID>] <TITLE>", + "sort.metadata.nfo.seriesastag": 1, + "sort.metadata.nfo.firstnameorder": 1, "sort.metadata.thumbcsv": 1, "sort.metadata.thumbcsv.convertalias": 1, "sort.metadata.genre.normalize": 0, @@ -59,7 +59,7 @@ "Featured Actress", "Hi-Def" ], - "sort.metadata.requiredFields": [ + "sort.metadata.requiredfield": [ "actress", "coverUrl", "genre",