2020-12-26 15:11:32 +00:00
|
|
|
import yaml
|
|
|
|
import json
|
2021-01-04 14:19:10 +00:00
|
|
|
import os
|
2022-02-03 16:40:15 +00:00
|
|
|
from datetime import datetime
|
2020-12-26 16:32:56 +00:00
|
|
|
from time import time
|
|
|
|
from sys import argv
|
|
|
|
from os.path import getmtime
|
2020-12-26 15:32:28 +00:00
|
|
|
from zipfile import ZipFile, ZIP_DEFLATED
|
2020-12-26 15:11:32 +00:00
|
|
|
|
|
|
|
DEFAULTS = {
|
|
|
|
'IsHide': False,
|
|
|
|
'IsTestingExclusive': False,
|
|
|
|
'ApplicableVersion': 'any',
|
|
|
|
}
|
|
|
|
|
|
|
|
DUPLICATES = {
|
|
|
|
'DownloadLinkInstall': ['DownloadLinkTesting', 'DownloadLinkUpdate'],
|
|
|
|
}
|
|
|
|
|
2020-12-26 15:32:28 +00:00
|
|
|
TRIMMED_KEYS = [
|
|
|
|
'Author',
|
|
|
|
'Name',
|
|
|
|
'Description',
|
|
|
|
'InternalName',
|
|
|
|
'AssemblyVersion',
|
|
|
|
'RepoUrl',
|
|
|
|
'ApplicableVersion',
|
|
|
|
'Tags',
|
|
|
|
'DalamudApiLevel',
|
2021-09-24 21:45:33 +00:00
|
|
|
'Punchline',
|
|
|
|
'IconUrl',
|
|
|
|
'ImageUrls',
|
2020-12-26 15:32:28 +00:00
|
|
|
]
|
|
|
|
|
2020-12-26 15:11:32 +00:00
|
|
|
def main():
|
2021-06-04 01:34:14 +00:00
|
|
|
plugins_dir = argv[1] if len(argv) > 1 else 'plugins'
|
|
|
|
master_name = 'pluginmaster.json' if plugins_dir == 'plugins' else f'{plugins_dir}.json'
|
|
|
|
info = {
|
|
|
|
'plugins_dir': plugins_dir,
|
|
|
|
'master_name': master_name,
|
|
|
|
}
|
|
|
|
|
2021-01-04 14:19:10 +00:00
|
|
|
# extract the manifests from inside the zip files
|
2021-06-04 01:34:14 +00:00
|
|
|
master = extract_manifests(info)
|
2020-12-26 15:32:28 +00:00
|
|
|
|
2021-01-04 14:19:10 +00:00
|
|
|
# trim the manifests
|
|
|
|
master = [trim_manifest(manifest) for manifest in master]
|
|
|
|
|
|
|
|
# convert the list of manifests into a master list
|
2021-06-04 01:34:14 +00:00
|
|
|
add_extra_fields(info, master)
|
2021-01-04 14:19:10 +00:00
|
|
|
|
|
|
|
# write the master
|
2021-06-04 01:34:14 +00:00
|
|
|
write_master(info, master)
|
2020-12-26 15:32:28 +00:00
|
|
|
|
2022-02-03 16:40:15 +00:00
|
|
|
# update the LastUpdate field in master
|
|
|
|
last_update(info)
|
2020-12-26 16:32:56 +00:00
|
|
|
|
2021-06-04 01:34:14 +00:00
|
|
|
def extract_manifests(info):
|
2021-01-04 14:19:10 +00:00
|
|
|
manifests = []
|
|
|
|
|
2021-06-04 01:34:14 +00:00
|
|
|
for dirpath, dirnames, filenames in os.walk(f'./{info["plugins_dir"]}'):
|
2021-01-04 14:19:10 +00:00
|
|
|
if len(filenames) == 0 or 'latest.zip' not in filenames:
|
|
|
|
continue
|
|
|
|
plugin_name = dirpath.split('/')[-1]
|
|
|
|
latest_zip = f'{dirpath}/latest.zip'
|
|
|
|
with ZipFile(latest_zip) as z:
|
|
|
|
manifest = json.loads(z.read(f'{plugin_name}.json').decode('utf-8'))
|
|
|
|
manifests.append(manifest)
|
|
|
|
|
|
|
|
return manifests
|
|
|
|
|
2021-06-04 01:34:14 +00:00
|
|
|
def add_extra_fields(info, manifests):
|
2021-01-04 14:19:10 +00:00
|
|
|
for manifest in manifests:
|
|
|
|
# generate the download link from the internal assembly name
|
2023-08-24 18:11:37 +00:00
|
|
|
manifest['DownloadLinkInstall'] = f'https://git.anna.lgbt/anna/plugin_repo/raw/branch/main/{info["plugins_dir"]}/{manifest["InternalName"]}/latest.zip'
|
2021-01-04 14:19:10 +00:00
|
|
|
# add default values if missing
|
|
|
|
for k, v in DEFAULTS.items():
|
|
|
|
if k not in manifest:
|
|
|
|
manifest[k] = v
|
|
|
|
# duplicate keys as specified in DUPLICATES
|
2020-12-26 15:11:32 +00:00
|
|
|
for source, keys in DUPLICATES.items():
|
|
|
|
for k in keys:
|
2021-01-04 14:19:10 +00:00
|
|
|
if k not in manifest:
|
|
|
|
manifest[k] = manifest[source]
|
|
|
|
|
2021-06-04 01:34:14 +00:00
|
|
|
def write_master(info, master):
|
2020-12-26 15:11:32 +00:00
|
|
|
# write as pretty json
|
2021-06-04 01:34:14 +00:00
|
|
|
with open(info['master_name'], 'w') as f:
|
2020-12-26 15:11:32 +00:00
|
|
|
json.dump(master, f, indent=4)
|
|
|
|
|
2020-12-26 15:32:28 +00:00
|
|
|
def trim_manifest(plugin):
|
|
|
|
return {k: plugin[k] for k in TRIMMED_KEYS if k in plugin}
|
|
|
|
|
2022-02-03 16:40:15 +00:00
|
|
|
def last_update(info):
|
2021-06-04 01:34:14 +00:00
|
|
|
with open(info['master_name']) as f:
|
2020-12-26 16:32:56 +00:00
|
|
|
master = json.load(f)
|
|
|
|
|
|
|
|
for plugin in master:
|
2021-06-04 01:34:14 +00:00
|
|
|
latest = f'{info["plugins_dir"]}/{plugin["InternalName"]}/latest.zip'
|
2020-12-26 16:32:56 +00:00
|
|
|
|
2022-02-03 16:40:15 +00:00
|
|
|
modified = 0
|
|
|
|
with ZipFile(latest) as z:
|
|
|
|
for zip_info in z.infolist():
|
|
|
|
info_mod = datetime(*zip_info.date_time).timestamp()
|
|
|
|
if info_mod > modified:
|
|
|
|
modified = int(info_mod)
|
|
|
|
|
2022-02-03 16:41:42 +00:00
|
|
|
if modified == 0:
|
2022-02-03 16:40:15 +00:00
|
|
|
modified = int(getmtime(latest))
|
|
|
|
|
|
|
|
if 'LastUpdate' not in plugin or modified != int(plugin['LastUpdate']):
|
|
|
|
plugin['LastUpdate'] = str(modified)
|
2020-12-26 16:32:56 +00:00
|
|
|
|
2021-06-04 01:34:14 +00:00
|
|
|
with open(info['master_name'], 'w') as f:
|
2020-12-26 16:32:56 +00:00
|
|
|
json.dump(master, f, indent=4)
|
|
|
|
|
2020-12-26 15:11:32 +00:00
|
|
|
if __name__ == '__main__':
|
|
|
|
main()
|