forked from Github/Axter-Stash
Added UI interface for DupFileManager
This commit is contained in:
36
plugins/DupFileManager/DupFileManager.css
Normal file
36
plugins/DupFileManager/DupFileManager.css
Normal file
@@ -0,0 +1,36 @@
|
|||||||
|
.scene-card__date {
|
||||||
|
color: #bfccd6;
|
||||||
|
font-size: 0.85em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.scene-card__performer {
|
||||||
|
display: inline-block;
|
||||||
|
font-weight: 500;
|
||||||
|
margin-right: 0.5em;
|
||||||
|
}
|
||||||
|
.scene-card__performer a {
|
||||||
|
color: #137cbd;
|
||||||
|
}
|
||||||
|
|
||||||
|
.scene-card__performers,
|
||||||
|
.scene-card__tags {
|
||||||
|
-webkit-box-orient: vertical;
|
||||||
|
display: -webkit-box;
|
||||||
|
-webkit-line-clamp: 1;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
.scene-card__performers:hover,
|
||||||
|
.scene-card__tags:hover {
|
||||||
|
-webkit-line-clamp: unset;
|
||||||
|
overflow: visible;
|
||||||
|
}
|
||||||
|
|
||||||
|
.scene-card__tags .tag-item {
|
||||||
|
margin-left: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.scene-performer-popover .image-thumbnail {
|
||||||
|
margin: 1em;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*# sourceMappingURL=DupFileManager.css.map */
|
||||||
1
plugins/DupFileManager/DupFileManager.css.map
Normal file
1
plugins/DupFileManager/DupFileManager.css.map
Normal file
@@ -0,0 +1 @@
|
|||||||
|
{"version":3,"sourceRoot":"","sources":["../src/DupFileManager.scss"],"names":[],"mappings":"AAAA;EACE;EACA;;;AAGF;EACE;EACA;EACA;;AAEA;EACE;;;AAIJ;AAAA;EAEE;EACA;EACA;EACA;;AAEA;AAAA;EACE;EACA;;;AAIJ;EACE;;;AAGF;EACE","file":"DupFileManager.css"}
|
||||||
191
plugins/DupFileManager/DupFileManager.js
Normal file
191
plugins/DupFileManager/DupFileManager.js
Normal file
File diff suppressed because one or more lines are too long
1
plugins/DupFileManager/DupFileManager.js.map
Normal file
1
plugins/DupFileManager/DupFileManager.js.map
Normal file
@@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"DupFileManager.js","sourceRoot":"","sources":["../src/DupFileManager.tsx"],"names":[],"mappings":"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"}
|
||||||
@@ -4,7 +4,7 @@
|
|||||||
# Note: To call this script outside of Stash, pass argument --url
|
# Note: To call this script outside of Stash, pass argument --url
|
||||||
# Example: python DupFileManager.py --url http://localhost:9999 -a
|
# Example: python DupFileManager.py --url http://localhost:9999 -a
|
||||||
import ModulesValidate
|
import ModulesValidate
|
||||||
ModulesValidate.modulesInstalled(["send2trash", "requests"])
|
ModulesValidate.modulesInstalled(["send2trash", "requests"], silent=True)
|
||||||
import os, sys, time, pathlib, argparse, platform, shutil, traceback, logging, requests
|
import os, sys, time, pathlib, argparse, platform, shutil, traceback, logging, requests
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
from StashPluginHelper import StashPluginHelper
|
from StashPluginHelper import StashPluginHelper
|
||||||
@@ -46,11 +46,17 @@ stash = StashPluginHelper(
|
|||||||
DebugFieldName="zzDebug",
|
DebugFieldName="zzDebug",
|
||||||
)
|
)
|
||||||
stash.convertToAscii = True
|
stash.convertToAscii = True
|
||||||
|
doJsonReturnModeTypes = ["tag_duplicates_task", "removeDupTag", "addExcludeTag", "removeExcludeTag", "mergeTags", "getLocalDupReportPath", "createDuplicateReportWithoutTagging", "deleteLocalDupReportHtmlFiles"]
|
||||||
|
doJsonReturn = False
|
||||||
|
if stash.PLUGIN_TASK_NAME in doJsonReturnModeTypes:
|
||||||
|
doJsonReturn = True
|
||||||
|
stash.log_to_norm = stash.LogTo.FILE
|
||||||
|
|
||||||
stash.Log("******************* Starting *******************")
|
stash.Log("******************* Starting *******************")
|
||||||
if len(sys.argv) > 1:
|
if len(sys.argv) > 1:
|
||||||
stash.Log(f"argv = {sys.argv}")
|
stash.Log(f"argv = {sys.argv}")
|
||||||
else:
|
else:
|
||||||
stash.Trace(f"No command line arguments. JSON_INPUT['args'] = {stash.JSON_INPUT['args']}")
|
stash.Trace(f"No command line arguments. JSON_INPUT['args'] = {stash.JSON_INPUT['args']}; PLUGIN_TASK_NAME = {stash.PLUGIN_TASK_NAME}")
|
||||||
stash.status(logLevel=logging.DEBUG)
|
stash.status(logLevel=logging.DEBUG)
|
||||||
|
|
||||||
|
|
||||||
@@ -482,6 +488,8 @@ def logReason(DupFileToKeep, Scene, reason):
|
|||||||
reasonDict[DupFileToKeep['id']] = reason
|
reasonDict[DupFileToKeep['id']] = reason
|
||||||
stash.Debug(f"Replacing {DupFileToKeep['files'][0]['path']} with {Scene['files'][0]['path']} for candidate to keep. Reason={reason}")
|
stash.Debug(f"Replacing {DupFileToKeep['files'][0]['path']} with {Scene['files'][0]['path']} for candidate to keep. Reason={reason}")
|
||||||
|
|
||||||
|
htmlReportName = f"{stash.PLUGINS_PATH}{os.sep}{stash.Setting('htmlReportName')}"
|
||||||
|
|
||||||
def mangeDupFiles(merge=False, deleteDup=False, tagDuplicates=False):
|
def mangeDupFiles(merge=False, deleteDup=False, tagDuplicates=False):
|
||||||
global reasonDict
|
global reasonDict
|
||||||
duplicateMarkForDeletion_descp = 'Tag added to duplicate scenes so-as to tag them for deletion.'
|
duplicateMarkForDeletion_descp = 'Tag added to duplicate scenes so-as to tag them for deletion.'
|
||||||
@@ -490,7 +498,6 @@ def mangeDupFiles(merge=False, deleteDup=False, tagDuplicates=False):
|
|||||||
stash.Trace(f"dupTagId={dupTagId} name={duplicateMarkForDeletion}")
|
stash.Trace(f"dupTagId={dupTagId} name={duplicateMarkForDeletion}")
|
||||||
createHtmlReport = stash.Setting('createHtmlReport')
|
createHtmlReport = stash.Setting('createHtmlReport')
|
||||||
previewOrStream = "stream" if stash.Setting('streamOverPreview') else "preview"
|
previewOrStream = "stream" if stash.Setting('streamOverPreview') else "preview"
|
||||||
htmlReportName = f"{stash.PLUGINS_PATH}{os.sep}{stash.Setting('htmlReportName')}"
|
|
||||||
htmlReportNameHomePage = htmlReportName
|
htmlReportNameHomePage = htmlReportName
|
||||||
htmlReportTableRow = stash.Setting('htmlReportTableRow')
|
htmlReportTableRow = stash.Setting('htmlReportTableRow')
|
||||||
htmlReportTableData = stash.Setting('htmlReportTableData')
|
htmlReportTableData = stash.Setting('htmlReportTableData')
|
||||||
@@ -661,9 +668,11 @@ def mangeDupFiles(merge=False, deleteDup=False, tagDuplicates=False):
|
|||||||
elif moveToTrashCan:
|
elif moveToTrashCan:
|
||||||
sendToTrash(DupFileName)
|
sendToTrash(DupFileName)
|
||||||
stash.destroyScene(DupFile['id'], delete_file=True)
|
stash.destroyScene(DupFile['id'], delete_file=True)
|
||||||
elif tagDuplicates:
|
elif tagDuplicates or fileHtmlReport != None:
|
||||||
QtyTagForDel+=1
|
QtyTagForDel+=1
|
||||||
QtyTagForDelPaginate+=1
|
QtyTagForDelPaginate+=1
|
||||||
|
didAddTag = False
|
||||||
|
if tagDuplicates:
|
||||||
didAddTag = setTagId_withRetry(duplicateMarkForDeletion, DupFile, DupFileToKeep, ignoreAutoTag=True)
|
didAddTag = setTagId_withRetry(duplicateMarkForDeletion, DupFile, DupFileToKeep, ignoreAutoTag=True)
|
||||||
if fileHtmlReport != None:
|
if fileHtmlReport != None:
|
||||||
stash.Debug(f"Adding scene {DupFile['id']} to HTML report.")
|
stash.Debug(f"Adding scene {DupFile['id']} to HTML report.")
|
||||||
@@ -698,9 +707,9 @@ def mangeDupFiles(merge=False, deleteDup=False, tagDuplicates=False):
|
|||||||
|
|
||||||
fileHtmlReport.write("</table>")
|
fileHtmlReport.write("</table>")
|
||||||
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Delete file and remove scene from stash\" value=\"Duplicate\" id=\"{DupFile['id']}\">[Delete]</button>")
|
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Delete file and remove scene from stash\" value=\"Duplicate\" id=\"{DupFile['id']}\">[Delete]</button>")
|
||||||
if dupFileExist:
|
if dupFileExist and tagDuplicates:
|
||||||
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Remove duplicate tag from scene\" value=\"RemoveDupTag\" id=\"{DupFile['id']}\">[Remove Tag]</button>")
|
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Remove duplicate tag from scene\" value=\"removeDupTag\" id=\"{DupFile['id']}\">[Remove Tag]</button>")
|
||||||
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Add exclude scene from deletion tag\" value=\"AddExcludeTag\" id=\"{DupFile['id']}\">[Add Exclude Tag]</button>")
|
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Add exclude scene from deletion tag\" value=\"addExcludeTag\" id=\"{DupFile['id']}\">[Add Exclude Tag]</button>")
|
||||||
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Merge duplicate scene tags with ToKeep scene tags\" value=\"mergeTags\" id=\"{DupFile['id']}:{DupFileToKeep['id']}\">[Merge Tags]</button>")
|
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Merge duplicate scene tags with ToKeep scene tags\" value=\"mergeTags\" id=\"{DupFile['id']}:{DupFileToKeep['id']}\">[Merge Tags]</button>")
|
||||||
if dupFileExist:
|
if dupFileExist:
|
||||||
fileHtmlReport.write(f"<a class=\"link-items\" title=\"Open folder\" href=\"file://{getPath(DupFile, True)}\">[Folder]</a>")
|
fileHtmlReport.write(f"<a class=\"link-items\" title=\"Open folder\" href=\"file://{getPath(DupFile, True)}\">[Folder]</a>")
|
||||||
@@ -718,7 +727,7 @@ def mangeDupFiles(merge=False, deleteDup=False, tagDuplicates=False):
|
|||||||
fileHtmlReport.write(f"<tr class=\"scene-details\"><td>{DupFileToKeep['files'][0]['width']}x{DupFileToKeep['files'][0]['height']}</td><td>{DupFileToKeep['files'][0]['duration']}</td><td>{DupFileToKeep['files'][0]['bit_rate']}</td><td>{DupFileToKeep['files'][0]['video_codec']}</td><td>{DupFileToKeep['files'][0]['frame_rate']}</td><td>{DupFileToKeep['files'][0]['size']}</td><td>{DupFileToKeep['id']}</td></tr></table>")
|
fileHtmlReport.write(f"<tr class=\"scene-details\"><td>{DupFileToKeep['files'][0]['width']}x{DupFileToKeep['files'][0]['height']}</td><td>{DupFileToKeep['files'][0]['duration']}</td><td>{DupFileToKeep['files'][0]['bit_rate']}</td><td>{DupFileToKeep['files'][0]['video_codec']}</td><td>{DupFileToKeep['files'][0]['frame_rate']}</td><td>{DupFileToKeep['files'][0]['size']}</td><td>{DupFileToKeep['id']}</td></tr></table>")
|
||||||
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Delete [DupFileToKeep] and remove scene from stash\" value=\"ToKeep\" id=\"{DupFileToKeep['id']}\">[Delete]</button>")
|
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Delete [DupFileToKeep] and remove scene from stash\" value=\"ToKeep\" id=\"{DupFileToKeep['id']}\">[Delete]</button>")
|
||||||
if isTaggedExcluded(DupFileToKeep):
|
if isTaggedExcluded(DupFileToKeep):
|
||||||
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Remove exclude scene from deletion tag\" value=\"RemoveExcludeTag\" id=\"{DupFileToKeep['id']}\">[Remove Exclude Tag]</button>")
|
fileHtmlReport.write(f"<button class=\"link-button\" title=\"Remove exclude scene from deletion tag\" value=\"removeExcludeTag\" id=\"{DupFileToKeep['id']}\">[Remove Exclude Tag]</button>")
|
||||||
fileHtmlReport.write(f"<a class=\"link-items\" title=\"Open folder\" href=\"file://{getPath(DupFileToKeep, True)}\">[Folder]</a>")
|
fileHtmlReport.write(f"<a class=\"link-items\" title=\"Open folder\" href=\"file://{getPath(DupFileToKeep, True)}\">[Folder]</a>")
|
||||||
if toKeepFileExist:
|
if toKeepFileExist:
|
||||||
fileHtmlReport.write(f"<a class=\"link-items\" title=\"Play file locally\" href=\"file://{getPath(DupFileToKeep)}\">[Play]</a>")
|
fileHtmlReport.write(f"<a class=\"link-items\" title=\"Play file locally\" href=\"file://{getPath(DupFileToKeep)}\">[Play]</a>")
|
||||||
@@ -762,7 +771,7 @@ def mangeDupFiles(merge=False, deleteDup=False, tagDuplicates=False):
|
|||||||
fileHtmlReport.write(f"{stash.Setting('htmlReportTable')}\n")
|
fileHtmlReport.write(f"{stash.Setting('htmlReportTable')}\n")
|
||||||
fileHtmlReport.write(f"{htmlReportTableRow}{htmlReportTableHeader}Scene</th>{htmlReportTableHeader}Duplicate to Delete</th>{htmlReportTableHeader}Scene-ToKeep</th>{htmlReportTableHeader}Duplicate to Keep</th></tr>\n")
|
fileHtmlReport.write(f"{htmlReportTableRow}{htmlReportTableHeader}Scene</th>{htmlReportTableHeader}Duplicate to Delete</th>{htmlReportTableHeader}Scene-ToKeep</th>{htmlReportTableHeader}Duplicate to Keep</th></tr>\n")
|
||||||
|
|
||||||
if graylistTagging and stash.startsWithInList(graylist, DupFile['files'][0]['path']):
|
if tagDuplicates and graylistTagging and stash.startsWithInList(graylist, DupFile['files'][0]['path']):
|
||||||
stash.addTag(DupFile, graylistMarkForDeletion, ignoreAutoTag=True)
|
stash.addTag(DupFile, graylistMarkForDeletion, ignoreAutoTag=True)
|
||||||
if didAddTag:
|
if didAddTag:
|
||||||
QtyNewlyTag+=1
|
QtyNewlyTag+=1
|
||||||
@@ -831,6 +840,7 @@ def mangeDupFiles(merge=False, deleteDup=False, tagDuplicates=False):
|
|||||||
stash.optimise_database()
|
stash.optimise_database()
|
||||||
if doGeneratePhash:
|
if doGeneratePhash:
|
||||||
stash.metadata_generate({"phashes": True})
|
stash.metadata_generate({"phashes": True})
|
||||||
|
sys.stdout.write("Report complete")
|
||||||
|
|
||||||
def findCurrentTagId(tagNames):
|
def findCurrentTagId(tagNames):
|
||||||
tagNames = [i for n, i in enumerate(tagNames) if i not in tagNames[:n]]
|
tagNames = [i for n, i in enumerate(tagNames) if i not in tagNames[:n]]
|
||||||
@@ -932,34 +942,42 @@ def manageTagggedDuplicates(deleteScenes=False, clearTag=False, setGrayListTag=F
|
|||||||
stash.metadata_generate({"phashes": True})
|
stash.metadata_generate({"phashes": True})
|
||||||
|
|
||||||
def removeDupTag():
|
def removeDupTag():
|
||||||
if 'removeDupTag' not in stash.JSON_INPUT['args']:
|
if 'Target' not in stash.JSON_INPUT['args']:
|
||||||
stash.Error(f"Could not find removeDupTag in JSON_INPUT ({stash.JSON_INPUT['args']})")
|
stash.Error(f"Could not find Target in JSON_INPUT ({stash.JSON_INPUT['args']})")
|
||||||
return
|
return
|
||||||
sceneToRemoveTag = stash.JSON_INPUT['args']['removeDupTag']
|
scene = stash.JSON_INPUT['args']['Target']
|
||||||
stash.removeTag(sceneToRemoveTag, duplicateMarkForDeletion)
|
stash.Log(f"Processing scene ID# {scene}")
|
||||||
stash.Log(f"Done removing tag from scene {sceneToRemoveTag}.")
|
stash.removeTag(scene, duplicateMarkForDeletion)
|
||||||
|
stash.Log(f"Done removing tag from scene {scene}.")
|
||||||
|
jsonReturn = "{'removeDupTag' : 'complete', 'id': '" + f"{scene}" + "'}"
|
||||||
|
stash.Log(f"Sending json value {jsonReturn}")
|
||||||
|
sys.stdout.write(jsonReturn)
|
||||||
|
|
||||||
def addExcludeForDelTag():
|
def addExcludeTag():
|
||||||
if 'addExcludeForDelTag' not in stash.JSON_INPUT['args']:
|
if 'Target' not in stash.JSON_INPUT['args']:
|
||||||
stash.Error(f"Could not find addExcludeForDelTag in JSON_INPUT ({stash.JSON_INPUT['args']})")
|
stash.Error(f"Could not find Target in JSON_INPUT ({stash.JSON_INPUT['args']})")
|
||||||
return
|
return
|
||||||
scene = stash.JSON_INPUT['args']['addExcludeForDelTag']
|
scene = stash.JSON_INPUT['args']['Target']
|
||||||
|
stash.Log(f"Processing scene ID# {scene}")
|
||||||
stash.addTag(scene, excludeDupFileDeleteTag)
|
stash.addTag(scene, excludeDupFileDeleteTag)
|
||||||
stash.Log(f"Done adding exclude tag to scene {scene}.")
|
stash.Log(f"Done adding exclude tag to scene {scene}.")
|
||||||
|
sys.stdout.write("{" + f"addExcludeTag : 'complete', id: '{scene}'" + "}")
|
||||||
|
|
||||||
def removeExcludeForDelTag():
|
def removeExcludeTag():
|
||||||
if 'removeExcludeForDelTag' not in stash.JSON_INPUT['args']:
|
if 'Target' not in stash.JSON_INPUT['args']:
|
||||||
stash.Error(f"Could not find removeExcludeForDelTag in JSON_INPUT ({stash.JSON_INPUT['args']})")
|
stash.Error(f"Could not find Target in JSON_INPUT ({stash.JSON_INPUT['args']})")
|
||||||
return
|
return
|
||||||
scene = stash.JSON_INPUT['args']['removeExcludeForDelTag']
|
scene = stash.JSON_INPUT['args']['Target']
|
||||||
|
stash.Log(f"Processing scene ID# {scene}")
|
||||||
stash.removeTag(scene, excludeDupFileDeleteTag)
|
stash.removeTag(scene, excludeDupFileDeleteTag)
|
||||||
stash.Log(f"Done removing exclude tag from scene {scene}.")
|
stash.Log(f"Done removing exclude tag from scene {scene}.")
|
||||||
|
sys.stdout.write("{" + f"removeExcludeTag : 'complete', id: '{scene}'" + "}")
|
||||||
|
|
||||||
def mergeTags():
|
def mergeTags():
|
||||||
if 'mergeScenes' not in stash.JSON_INPUT['args']:
|
if 'Target' not in stash.JSON_INPUT['args']:
|
||||||
stash.Error(f"Could not find mergeScenes in JSON_INPUT ({stash.JSON_INPUT['args']})")
|
stash.Error(f"Could not find Target in JSON_INPUT ({stash.JSON_INPUT['args']})")
|
||||||
return
|
return
|
||||||
mergeScenes = stash.JSON_INPUT['args']['mergeScenes']
|
mergeScenes = stash.JSON_INPUT['args']['Target']
|
||||||
scenes = mergeScenes.split(":")
|
scenes = mergeScenes.split(":")
|
||||||
if len(scenes) < 2:
|
if len(scenes) < 2:
|
||||||
stash.Error(f"Could not get both scenes from string {mergeScenes}")
|
stash.Error(f"Could not get both scenes from string {mergeScenes}")
|
||||||
@@ -969,6 +987,55 @@ def mergeTags():
|
|||||||
scene2 = stash.find_scene(int(scenes[1]))
|
scene2 = stash.find_scene(int(scenes[1]))
|
||||||
stash.mergeMetadata(scene1, scene2)
|
stash.mergeMetadata(scene1, scene2)
|
||||||
stash.Log(f"Done merging scenes for scene {scenes[0]} and scene {scenes[1]}")
|
stash.Log(f"Done merging scenes for scene {scenes[0]} and scene {scenes[1]}")
|
||||||
|
sys.stdout.write("{" + f"mergeTags : 'complete', id1: '{scene1}', id2: '{scene2}'" + "}")
|
||||||
|
|
||||||
|
def openWebpage():
|
||||||
|
htmlReportName = f"{stash.PLUGINS_PATH}{os.sep}{stash.Setting('htmlReportName')}"
|
||||||
|
stash.Log(f"Opening web page {htmlReportName}")
|
||||||
|
# chromePath = r"C:\Program Files (x86)\Google\Chrome\Application\chrome.exe"
|
||||||
|
chromePath = r"C:\PROGRA~2\Google\Chrome\Application\chrome.exe"
|
||||||
|
firefox = r"C:\PROGRA~1\MOZILL~1\firefox.exe"
|
||||||
|
browserPath = chromePath
|
||||||
|
if os.path.isfile(browserPath):
|
||||||
|
stash.Log(f"Opening web page {htmlReportName} with user {os.getlogin()} using {browserPath}")
|
||||||
|
# pw_record = pwd.getpwnam(os.getlogin())
|
||||||
|
# uid = pw_record.pw_uid
|
||||||
|
# gid = pw_record.pw_gid
|
||||||
|
# os.setgid(gid)
|
||||||
|
# os.setuid(uid)
|
||||||
|
# stash.Log(f"Using uid={uid} and gid={gid}")
|
||||||
|
# stash.executeProcess(f"\"{browserPath}\" -incognito --new-window \"file://{htmlReportName}\"", ExecDetach=True)
|
||||||
|
os.system(f"{browserPath} -incognito --new-window \"file://{htmlReportName}\"")
|
||||||
|
# else:
|
||||||
|
import webbrowser
|
||||||
|
webbrowser.open(htmlReportName, new=2, autoraise=True)
|
||||||
|
os.system(f"start file:///{htmlReportName}")
|
||||||
|
|
||||||
|
def getLocalDupReportPath():
|
||||||
|
htmlReportExist = "true" if os.path.isfile(htmlReportName) else "false"
|
||||||
|
# htmlReportExist = "false"
|
||||||
|
localPath = htmlReportName.replace("\\", "\\\\")
|
||||||
|
jsonReturn = "{'LocalDupReportExist' : " + f"{htmlReportExist}" + ", 'Path': '" + f"{localPath}" + "'}"
|
||||||
|
stash.Log(f"Sending json value {jsonReturn}")
|
||||||
|
sys.stdout.write(jsonReturn)
|
||||||
|
|
||||||
|
def deleteLocalDupReportHtmlFiles():
|
||||||
|
htmlReportExist = "true" if os.path.isfile(htmlReportName) else "false"
|
||||||
|
if os.path.isfile(htmlReportName):
|
||||||
|
stash.Log(f"Deleting file {htmlReportName}")
|
||||||
|
os.remove(htmlReportName)
|
||||||
|
for x in range(2, 9999):
|
||||||
|
fileName = htmlReportName.replace(".html", f"_{x-1}.html")
|
||||||
|
stash.Debug(f"Checking if file '{fileName}' exist.")
|
||||||
|
if not os.path.isfile(fileName):
|
||||||
|
break
|
||||||
|
stash.Log(f"Deleting file {fileName}")
|
||||||
|
os.remove(fileName)
|
||||||
|
else:
|
||||||
|
stash.Log(f"Report file does not exist: {htmlReportName}")
|
||||||
|
jsonReturn = "{'LocalDupReportExist' : " + f"{htmlReportExist}" + ", 'Path': '" + f"{htmlReportName}" + "', 'qty': '" + f"{x}" + "'}"
|
||||||
|
stash.Log(f"Sending json value {jsonReturn}")
|
||||||
|
sys.stdout.write(jsonReturn)
|
||||||
|
|
||||||
# ToDo: Add additional menu items option only for bottom of report:
|
# ToDo: Add additional menu items option only for bottom of report:
|
||||||
# Remove from stash all files no longer part of stash library
|
# Remove from stash all files no longer part of stash library
|
||||||
@@ -993,18 +1060,27 @@ try:
|
|||||||
elif stash.PLUGIN_TASK_NAME == "generate_phash_task":
|
elif stash.PLUGIN_TASK_NAME == "generate_phash_task":
|
||||||
stash.metadata_generate({"phashes": True})
|
stash.metadata_generate({"phashes": True})
|
||||||
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
||||||
elif stash.PLUGIN_TASK_NAME == "remove_a_duplicate_tag":
|
elif stash.PLUGIN_TASK_NAME == "removeDupTag":
|
||||||
removeDupTag()
|
removeDupTag()
|
||||||
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
||||||
elif stash.PLUGIN_TASK_NAME == "add_an_exclude_tag":
|
elif stash.PLUGIN_TASK_NAME == "addExcludeTag":
|
||||||
addExcludeForDelTag()
|
addExcludeTag()
|
||||||
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
||||||
elif stash.PLUGIN_TASK_NAME == "remove_an_exclude_tag":
|
elif stash.PLUGIN_TASK_NAME == "removeExcludeTag":
|
||||||
removeExcludeForDelTag()
|
removeExcludeTag()
|
||||||
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
||||||
elif stash.PLUGIN_TASK_NAME == "merge_tags":
|
elif stash.PLUGIN_TASK_NAME == "mergeTags":
|
||||||
mergeTags()
|
mergeTags()
|
||||||
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
||||||
|
elif stash.PLUGIN_TASK_NAME == "getLocalDupReportPath":
|
||||||
|
getLocalDupReportPath()
|
||||||
|
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
||||||
|
elif stash.PLUGIN_TASK_NAME == "deleteLocalDupReportHtmlFiles":
|
||||||
|
deleteLocalDupReportHtmlFiles()
|
||||||
|
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
||||||
|
elif stash.PLUGIN_TASK_NAME == "createDuplicateReportWithoutTagging":
|
||||||
|
mangeDupFiles(tagDuplicates=False, merge=mergeDupFilename)
|
||||||
|
stash.Debug(f"{stash.PLUGIN_TASK_NAME} EXIT")
|
||||||
elif parse_args.dup_tag:
|
elif parse_args.dup_tag:
|
||||||
stash.PLUGIN_TASK_NAME = "dup_tag"
|
stash.PLUGIN_TASK_NAME = "dup_tag"
|
||||||
mangeDupFiles(tagDuplicates=True, merge=mergeDupFilename)
|
mangeDupFiles(tagDuplicates=True, merge=mergeDupFilename)
|
||||||
@@ -1030,5 +1106,7 @@ except Exception as e:
|
|||||||
killScanningJobs()
|
killScanningJobs()
|
||||||
stash.convertToAscii = False
|
stash.convertToAscii = False
|
||||||
stash.Error(f"Error: {e}\nTraceBack={tb}")
|
stash.Error(f"Error: {e}\nTraceBack={tb}")
|
||||||
|
if doJsonReturn:
|
||||||
|
sys.stdout.write("{" + f"Exception : '{e}; See log file for TraceBack' " + "}")
|
||||||
|
|
||||||
stash.Log("\n*********************************\nEXITING ***********************\n*********************************")
|
stash.Log("\n*********************************\nEXITING ***********************\n*********************************")
|
||||||
|
|||||||
@@ -2,6 +2,13 @@ name: DupFileManager
|
|||||||
description: Manages duplicate files.
|
description: Manages duplicate files.
|
||||||
version: 0.1.6
|
version: 0.1.6
|
||||||
url: https://github.com/David-Maisonave/Axter-Stash/tree/main/plugins/DupFileManager
|
url: https://github.com/David-Maisonave/Axter-Stash/tree/main/plugins/DupFileManager
|
||||||
|
ui:
|
||||||
|
javascript:
|
||||||
|
- DupFileManager.js
|
||||||
|
css:
|
||||||
|
- DupFileManager.css
|
||||||
|
- DupFileManager.css.map
|
||||||
|
- DupFileManager.js.map
|
||||||
settings:
|
settings:
|
||||||
mergeDupFilename:
|
mergeDupFilename:
|
||||||
displayName: Merge Duplicate Tags
|
displayName: Merge Duplicate Tags
|
||||||
|
|||||||
@@ -118,7 +118,17 @@ table, th, td {border:1px solid black;}
|
|||||||
</style>
|
</style>
|
||||||
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.7.1/jquery.min.js"></script>
|
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.7.1/jquery.min.js"></script>
|
||||||
<script>
|
<script>
|
||||||
var superQuery = `{ mutation SceneDestroy($input:SceneDestroyInput!) {sceneDestroy(input: $input)} }`
|
function RunPluginDupFileManager(Mode, ActionID, chkBxRemoveValid, button) {
|
||||||
|
$.ajax({method: "POST", url: "http://127.0.0.1:9999/graphql", contentType: "application/json", dataType: "text",
|
||||||
|
data: JSON.stringify({
|
||||||
|
query: `mutation RunPluginOperation($plugin_id:ID!,$args:Map!){runPluginOperation(plugin_id:$plugin_id,args:$args)}`,
|
||||||
|
variables: {"plugin_id": "DupFileManager", "args": { "Target" : ActionID, "mode":Mode}},
|
||||||
|
}), success: function(result){
|
||||||
|
console.log(result);
|
||||||
|
button.style.visibility = 'hidden';
|
||||||
|
if (!chkBxRemoveValid.checked) alert("Action " + Mode + " for scene(s) ID# " + ActionID + " complete.")
|
||||||
|
}});
|
||||||
|
}
|
||||||
$(document).ready(function(){
|
$(document).ready(function(){
|
||||||
$("button").click(function(){
|
$("button").click(function(){
|
||||||
chkBxRemoveValid = document.getElementById("RemoveValidatePrompt");
|
chkBxRemoveValid = document.getElementById("RemoveValidatePrompt");
|
||||||
@@ -128,64 +138,19 @@ $(document).ready(function(){
|
|||||||
if (!chkBxDisableDeleteConfirm.checked && !confirm("Are you sure you want to delete this file and remove scene from stash?")) {
|
if (!chkBxDisableDeleteConfirm.checked && !confirm("Are you sure you want to delete this file and remove scene from stash?")) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
const SceneId = this.id;
|
||||||
$.ajax({method: "POST", url: "http://127.0.0.1:9999/graphql", contentType: "application/json",
|
$.ajax({method: "POST", url: "http://127.0.0.1:9999/graphql", contentType: "application/json",
|
||||||
data: JSON.stringify({
|
data: JSON.stringify({
|
||||||
query: `mutation SceneDestroy($input:SceneDestroyInput!) {sceneDestroy(input: $input)}`,
|
query: `mutation SceneDestroy($input:SceneDestroyInput!) {sceneDestroy(input: $input)}`,
|
||||||
variables: {"input":{"delete_file":true,"id":this.id}},
|
variables: {"input":{"delete_file":true,"id":SceneId}},
|
||||||
}), success: function(result){
|
}), success: function(result){
|
||||||
$("#div1").html(result);
|
console.log(result);
|
||||||
|
if (!chkBxRemoveValid.checked) alert("Delete request received for scene ID# " + SceneId)
|
||||||
}});
|
}});
|
||||||
this.style.visibility = 'hidden';
|
this.style.visibility = 'hidden';
|
||||||
if (!chkBxRemoveValid.checked) alert("Sent delete request for scene ID# " + this.id)
|
|
||||||
}
|
|
||||||
else if (this.value === "RemoveDupTag")
|
|
||||||
{
|
|
||||||
$.ajax({method: "POST", url: "http://127.0.0.1:9999/graphql", contentType: "application/json",
|
|
||||||
data: JSON.stringify({
|
|
||||||
query: `mutation RunPluginOperation($plugin_id:ID!,$args:Map!){runPluginOperation(plugin_id:$plugin_id,args:$args)}`,
|
|
||||||
variables: {"plugin_id": "DupFileManager", "args": {"removeDupTag":this.id, "mode":"remove_a_duplicate_tag"}},
|
|
||||||
}), success: function(result){
|
|
||||||
$("#div1").html(result);
|
|
||||||
}});
|
|
||||||
this.style.visibility = 'hidden';
|
|
||||||
if (!chkBxRemoveValid.checked) alert("Sent remove duplicate tag request for scene ID# " + this.id)
|
|
||||||
}
|
|
||||||
else if (this.value === "AddExcludeTag")
|
|
||||||
{
|
|
||||||
$.ajax({method: "POST", url: "http://127.0.0.1:9999/graphql", contentType: "application/json",
|
|
||||||
data: JSON.stringify({
|
|
||||||
query: `mutation RunPluginOperation($plugin_id:ID!,$args:Map!){runPluginOperation(plugin_id:$plugin_id,args:$args)}`,
|
|
||||||
variables: {"plugin_id": "DupFileManager", "args": {"addExcludeForDelTag":this.id, "mode":"add_an_exclude_tag"}},
|
|
||||||
}), success: function(result){
|
|
||||||
$("#div1").html(result);
|
|
||||||
}});
|
|
||||||
this.style.visibility = 'hidden';
|
|
||||||
if (!chkBxRemoveValid.checked) alert("Sent add exclude tag request for scene ID# " + this.id)
|
|
||||||
}
|
|
||||||
else if (this.value === "RemoveExcludeTag")
|
|
||||||
{
|
|
||||||
$.ajax({method: "POST", url: "http://127.0.0.1:9999/graphql", contentType: "application/json",
|
|
||||||
data: JSON.stringify({
|
|
||||||
query: `mutation RunPluginOperation($plugin_id:ID!,$args:Map!){runPluginOperation(plugin_id:$plugin_id,args:$args)}`,
|
|
||||||
variables: {"plugin_id": "DupFileManager", "args": {"removeExcludeForDelTag":this.id, "mode":"remove_an_exclude_tag"}},
|
|
||||||
}), success: function(result){
|
|
||||||
$("#div1").html(result);
|
|
||||||
}});
|
|
||||||
this.style.visibility = 'hidden';
|
|
||||||
if (!chkBxRemoveValid.checked) alert("Sent remove exclude tag request for scene ID# " + this.id)
|
|
||||||
}
|
|
||||||
else if (this.value === "mergeTags")
|
|
||||||
{
|
|
||||||
$.ajax({method: "POST", url: "http://127.0.0.1:9999/graphql", contentType: "application/json",
|
|
||||||
data: JSON.stringify({
|
|
||||||
query: `mutation RunPluginOperation($plugin_id:ID!,$args:Map!){runPluginOperation(plugin_id:$plugin_id,args:$args)}`,
|
|
||||||
variables: {"plugin_id": "DupFileManager", "args": {"mergeScenes":this.id, "mode":"merge_tags"}},
|
|
||||||
}), success: function(result){
|
|
||||||
$("#div1").html(result);
|
|
||||||
}});
|
|
||||||
this.style.visibility = 'hidden';
|
|
||||||
if (!chkBxRemoveValid.checked) alert("Sent merge scene request for scenes " + this.id)
|
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
RunPluginDupFileManager(this.value, this.id, chkBxRemoveValid, this)
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@@ -627,7 +627,7 @@ class StashPluginHelper(StashInterface):
|
|||||||
|
|
||||||
def removeTag(self, scene, tagName): # scene can be scene ID or scene metadata
|
def removeTag(self, scene, tagName): # scene can be scene ID or scene metadata
|
||||||
scene_details = scene
|
scene_details = scene
|
||||||
if 'id' not in scene:
|
if isinstance(scene, int) or 'id' not in scene:
|
||||||
scene_details = self.find_scene(scene)
|
scene_details = self.find_scene(scene)
|
||||||
tagIds = []
|
tagIds = []
|
||||||
doesHaveTagName = False
|
doesHaveTagName = False
|
||||||
@@ -649,7 +649,7 @@ class StashPluginHelper(StashInterface):
|
|||||||
if errMsg != None:
|
if errMsg != None:
|
||||||
self.Warn(errMsg)
|
self.Warn(errMsg)
|
||||||
scene_details = scene
|
scene_details = scene
|
||||||
if 'id' not in scene:
|
if isinstance(scene, int) or 'id' not in scene:
|
||||||
scene_details = self.find_scene(scene)
|
scene_details = self.find_scene(scene)
|
||||||
tagIds = [self.createTagId(tagName, tagName_descp=tagName_descp, ignoreAutoTag=ignoreAutoTag)]
|
tagIds = [self.createTagId(tagName, tagName_descp=tagName_descp, ignoreAutoTag=ignoreAutoTag)]
|
||||||
for tag in scene_details['tags']:
|
for tag in scene_details['tags']:
|
||||||
@@ -884,7 +884,8 @@ class mergeMetadata: # A class to merge scene metadata from source scene to dest
|
|||||||
self.mergeItems('tags', 'tag_ids', [], excludeName=self.excludeMergeTags)
|
self.mergeItems('tags', 'tag_ids', [], excludeName=self.excludeMergeTags)
|
||||||
self.mergeItems('performers', 'performer_ids', [])
|
self.mergeItems('performers', 'performer_ids', [])
|
||||||
self.mergeItems('galleries', 'gallery_ids', [])
|
self.mergeItems('galleries', 'gallery_ids', [])
|
||||||
self.mergeItems('movies', 'movies', [])
|
# ToDo: Need to find out why the following line no longer works in new Stash version
|
||||||
|
# self.mergeItems('movies', 'movies', [])
|
||||||
self.mergeItems('urls', listToAdd=self.destData['urls'], NotStartWith=self.stash.STASH_URL)
|
self.mergeItems('urls', listToAdd=self.destData['urls'], NotStartWith=self.stash.STASH_URL)
|
||||||
self.mergeItem('studio', 'studio_id', 'id')
|
self.mergeItem('studio', 'studio_id', 'id')
|
||||||
self.mergeItem('title')
|
self.mergeItem('title')
|
||||||
|
|||||||
@@ -627,7 +627,7 @@ class StashPluginHelper(StashInterface):
|
|||||||
|
|
||||||
def removeTag(self, scene, tagName): # scene can be scene ID or scene metadata
|
def removeTag(self, scene, tagName): # scene can be scene ID or scene metadata
|
||||||
scene_details = scene
|
scene_details = scene
|
||||||
if 'id' not in scene:
|
if isinstance(scene, int) or 'id' not in scene:
|
||||||
scene_details = self.find_scene(scene)
|
scene_details = self.find_scene(scene)
|
||||||
tagIds = []
|
tagIds = []
|
||||||
doesHaveTagName = False
|
doesHaveTagName = False
|
||||||
@@ -649,7 +649,7 @@ class StashPluginHelper(StashInterface):
|
|||||||
if errMsg != None:
|
if errMsg != None:
|
||||||
self.Warn(errMsg)
|
self.Warn(errMsg)
|
||||||
scene_details = scene
|
scene_details = scene
|
||||||
if 'id' not in scene:
|
if isinstance(scene, int) or 'id' not in scene:
|
||||||
scene_details = self.find_scene(scene)
|
scene_details = self.find_scene(scene)
|
||||||
tagIds = [self.createTagId(tagName, tagName_descp=tagName_descp, ignoreAutoTag=ignoreAutoTag)]
|
tagIds = [self.createTagId(tagName, tagName_descp=tagName_descp, ignoreAutoTag=ignoreAutoTag)]
|
||||||
for tag in scene_details['tags']:
|
for tag in scene_details['tags']:
|
||||||
@@ -884,7 +884,8 @@ class mergeMetadata: # A class to merge scene metadata from source scene to dest
|
|||||||
self.mergeItems('tags', 'tag_ids', [], excludeName=self.excludeMergeTags)
|
self.mergeItems('tags', 'tag_ids', [], excludeName=self.excludeMergeTags)
|
||||||
self.mergeItems('performers', 'performer_ids', [])
|
self.mergeItems('performers', 'performer_ids', [])
|
||||||
self.mergeItems('galleries', 'gallery_ids', [])
|
self.mergeItems('galleries', 'gallery_ids', [])
|
||||||
self.mergeItems('movies', 'movies', [])
|
# ToDo: Need to find out why the following line no longer works in new Stash version
|
||||||
|
# self.mergeItems('movies', 'movies', [])
|
||||||
self.mergeItems('urls', listToAdd=self.destData['urls'], NotStartWith=self.stash.STASH_URL)
|
self.mergeItems('urls', listToAdd=self.destData['urls'], NotStartWith=self.stash.STASH_URL)
|
||||||
self.mergeItem('studio', 'studio_id', 'id')
|
self.mergeItem('studio', 'studio_id', 'id')
|
||||||
self.mergeItem('title')
|
self.mergeItem('title')
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
# Note: To call this script outside of Stash, pass argument --url and the Stash URL.
|
# Note: To call this script outside of Stash, pass argument --url and the Stash URL.
|
||||||
# Example: python filemonitor.py --url http://localhost:9999
|
# Example: python filemonitor.py --url http://localhost:9999
|
||||||
import ModulesValidate
|
import ModulesValidate
|
||||||
ModulesValidate.modulesInstalled(["watchdog", "schedule", "requests"])
|
ModulesValidate.modulesInstalled(["stashapp-tools", "watchdog", "schedule", "requests"])
|
||||||
from StashPluginHelper import StashPluginHelper
|
from StashPluginHelper import StashPluginHelper
|
||||||
import os, sys, time, pathlib, argparse, platform, traceback, logging
|
import os, sys, time, pathlib, argparse, platform, traceback, logging
|
||||||
from StashPluginHelper import taskQueue
|
from StashPluginHelper import taskQueue
|
||||||
|
|||||||
@@ -627,7 +627,7 @@ class StashPluginHelper(StashInterface):
|
|||||||
|
|
||||||
def removeTag(self, scene, tagName): # scene can be scene ID or scene metadata
|
def removeTag(self, scene, tagName): # scene can be scene ID or scene metadata
|
||||||
scene_details = scene
|
scene_details = scene
|
||||||
if 'id' not in scene:
|
if isinstance(scene, int) or 'id' not in scene:
|
||||||
scene_details = self.find_scene(scene)
|
scene_details = self.find_scene(scene)
|
||||||
tagIds = []
|
tagIds = []
|
||||||
doesHaveTagName = False
|
doesHaveTagName = False
|
||||||
@@ -649,7 +649,7 @@ class StashPluginHelper(StashInterface):
|
|||||||
if errMsg != None:
|
if errMsg != None:
|
||||||
self.Warn(errMsg)
|
self.Warn(errMsg)
|
||||||
scene_details = scene
|
scene_details = scene
|
||||||
if 'id' not in scene:
|
if isinstance(scene, int) or 'id' not in scene:
|
||||||
scene_details = self.find_scene(scene)
|
scene_details = self.find_scene(scene)
|
||||||
tagIds = [self.createTagId(tagName, tagName_descp=tagName_descp, ignoreAutoTag=ignoreAutoTag)]
|
tagIds = [self.createTagId(tagName, tagName_descp=tagName_descp, ignoreAutoTag=ignoreAutoTag)]
|
||||||
for tag in scene_details['tags']:
|
for tag in scene_details['tags']:
|
||||||
@@ -884,7 +884,8 @@ class mergeMetadata: # A class to merge scene metadata from source scene to dest
|
|||||||
self.mergeItems('tags', 'tag_ids', [], excludeName=self.excludeMergeTags)
|
self.mergeItems('tags', 'tag_ids', [], excludeName=self.excludeMergeTags)
|
||||||
self.mergeItems('performers', 'performer_ids', [])
|
self.mergeItems('performers', 'performer_ids', [])
|
||||||
self.mergeItems('galleries', 'gallery_ids', [])
|
self.mergeItems('galleries', 'gallery_ids', [])
|
||||||
self.mergeItems('movies', 'movies', [])
|
# ToDo: Need to find out why the following line no longer works in new Stash version
|
||||||
|
# self.mergeItems('movies', 'movies', [])
|
||||||
self.mergeItems('urls', listToAdd=self.destData['urls'], NotStartWith=self.stash.STASH_URL)
|
self.mergeItems('urls', listToAdd=self.destData['urls'], NotStartWith=self.stash.STASH_URL)
|
||||||
self.mergeItem('studio', 'studio_id', 'id')
|
self.mergeItem('studio', 'studio_id', 'id')
|
||||||
self.mergeItem('title')
|
self.mergeItem('title')
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
# Get the latest developers version from following link: https://github.com/David-Maisonave/Axter-Stash/tree/main/plugins/RenameFile
|
# Get the latest developers version from following link: https://github.com/David-Maisonave/Axter-Stash/tree/main/plugins/RenameFile
|
||||||
# Based on source code from https://github.com/Serechops/Serechops-Stash/tree/main/plugins/Renamer
|
# Based on source code from https://github.com/Serechops/Serechops-Stash/tree/main/plugins/Renamer
|
||||||
import ModulesValidate
|
import ModulesValidate
|
||||||
ModulesValidate.modulesInstalled(["requests"])
|
ModulesValidate.modulesInstalled(["stashapp-tools", "requests"])
|
||||||
import os, sys, shutil, json, hashlib, pathlib, logging, time, traceback
|
import os, sys, shutil, json, hashlib, pathlib, logging, time, traceback
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
import stashapi.log as log # Importing stashapi.log as log for critical events ONLY
|
import stashapi.log as log # Importing stashapi.log as log for critical events ONLY
|
||||||
|
|||||||
Reference in New Issue
Block a user