def test_highLevelFunctions(self):
        remoteSubModVersionJSONString = """
		{
			"id" : "Onikakushi Ch.1/full",
			"files":[
				{"id": "cg",                  "version": "1.0.0"},
				{"id": "cgalt",               "version": "1.0.0"},
				{"id": "movie",               "version": "1.0.0"},
				{"id": "voices",              "version": "1.0.0"},
				{"id": "script",              "version": "6.1.0"},
				{"id": "movie-unix",          "version": "1.0.0"},
				{"id": "ui-windows",          "version": "1.0.0"},
				{"id": "ui-unix",             "version": "1.0.0"}
			]
		}
		"""
        remoteVersionObject = fileVersionManagement.SubModVersionInfo(
            json.loads(remoteSubModVersionJSONString))

        test_dir = tempfile.mkdtemp()

        modList = self.getModListFromDummyJSON()
        mod = modList[0]
        submod = mod['submods'][0]

        subModConfig = installConfiguration.SubModConfig(mod, submod)
        fullConfig = installConfiguration.FullInstallConfiguration(
            subModConfig, test_dir, True)

        originalModFileList = fullConfig.buildFileListSorted('datadir')

        # If there is no file present, all files should require download
        fileVersionManager = fileVersionManagement.VersionManager(
            subMod=subModConfig,
            modFileList=originalModFileList,
            localVersionFolder=test_dir,
            _testRemoteSubModVersion=remoteVersionObject)

        self.assertEqual(fileVersionManager.getFilesRequiringUpdate(),
                         originalModFileList)
        self.assertEqual(fileVersionManager.fullUpdateRequired(), True)

        fileVersionManager.saveVersionInstallFinished()

        # If there is a file present which is identical, no files should require download
        fileVersionManagerIdentical = fileVersionManagement.VersionManager(
            subMod=subModConfig,
            modFileList=originalModFileList,
            localVersionFolder=test_dir,
            _testRemoteSubModVersion=remoteVersionObject)

        self.assertEqual(fileVersionManagerIdentical.getFilesRequiringUpdate(),
                         [])
        self.assertEqual(fileVersionManagerIdentical.fullUpdateRequired(),
                         False)

        shutil.rmtree(test_dir)
Пример #2
0
def main(*, game_name, game_path, mod_type, mod_options=[], is_steam=True):
    sys.stdout = logger.Logger(common.Globals.LOG_FILE_PATH)
    logger.setGlobalLogger(sys.stdout)
    sys.stderr = logger.StdErrRedirector(sys.stdout)
    common.Globals.scanForExecutables()
    gui_main.check07thModServerConnection()
    modList = gui_main.getModList()
    subModList = gui_main.getSubModConfigList(modList)
    print("\n")
    suitableSubMods = [
        x
        for x in subModList
        if all(y in x.modName.lower().split() for y in game_name.lower().split("-"))
        and x.subModName == mod_type
    ]
    if len(suitableSubMods) != 1:
        print(f'Could not find a mod matching "{game_name}"')
        return
    neededSubMod = suitableSubMods[0]
    neededModOptions = []
    for i in mod_options:
        neededModOption = [
            x
            for x in neededSubMod.modOptions
            if all(y in x.id.lower().split() for y in i.lower().split("-"))
        ]
        if len(neededModOption) == 1:
            neededModOptions += neededModOption
    if len(neededModOptions) != len(mod_options):
        print("Couldn't find specified mod options.")
        return
    for i in neededSubMod.modOptions:
        if i.id in [x.id for x in neededModOptions]:
            i.value = True
    install_config = installConfiguration.FullInstallConfiguration(
        neededSubMod, game_path, is_steam
    )
    if neededSubMod.family == "umineko":
        uminekoInstaller.mainUmineko(install_config)
    elif neededSubMod.family == "umineko_nscripter":
        uminekoNScripterInstaller.main(install_config)
    elif neededSubMod.family == "higurashi":
        higurashiInstaller.main(install_config)
    else:
        print(
            f"Submod family is not recognised, the script may be out of date."
            "Please ask us to update it."
        )
Пример #3
0
def scanForFullInstallConfigs(subModConfigList,
                              possiblePaths=None,
                              scanExtraPaths=True):
    # type: (List[installConfiguration.SubModConfig], [str], bool) -> [installConfiguration.FullInstallConfiguration, List[str]]
    """
	This function has two purposes:
		- When given a specific game path ('possiblePaths' argument), it checks if any of the given SubModConfig
		  can be installed into that path. Each SubModConfig which can be installed into that path will be returned
		  as a FullInstallConfiguration object.

		- When not given a specific game path, it searches the computer for valid installations where the given
		  SubModConfig could be installed to. Each valid (installation + SubModConfig) combination will be returned
		  as a FullInstallConfiguration object.

	:param subModConfigList: A **list** of SubModConfig which are to be searched for on disk
	:param possiblePaths: (Optional) Specify folders to check if the given SubModConfig can be installed into that path.
	:return:    1. A list of FullInstallConfig, each representing a valid install path that the
				given SubModConfig(s) couldbe installed into.
				2. A list of games which were "partially uninstalled" by Steam - steam deletes game files, but not the mod
				files. The user should be notified to delete these files manually.
	"""

    returnedFullConfigs = []
    returnedPartiallyUninstalledPaths = []
    pathsToBeScanned = possiblePaths

    if not pathsToBeScanned:
        pathsToBeScanned = getMaybeGamePaths()

    # Build a mapping from subModIdentifier -> List[subMod]
    # This tells us, for each identifier, which subMods are compatible with that identifier (can be installed)
    # In all our games, the identifiers are the same for each subMod (but different for each Mod),
    # but it is easier to work with in the installer if we work with subMods

    from collections import defaultdict
    subModConfigDictionary = defaultdict(
        list)  #type: defaultdict[List[installConfiguration.SubModConfig]]
    for subMod in subModConfigList:
        # If autodetection is disabled, and autodetection requested, do not scan for this submod
        if not subMod.autodetect and possiblePaths is None:
            continue

        for identifier in subMod.identifiers:
            subModConfigDictionary[identifier].append(subMod)

    # If there are no identifiers to be matched, give up immediately as we'll never find a match
    if not subModConfigDictionary:
        return [], []

    if scanExtraPaths:
        extraPaths = []
        for gamePath in pathsToBeScanned:
            # MacOS: Any subpath with '.app' is also checked in case the containing path was manually entered
            extraPaths.extend(glob.glob(os.path.join(gamePath, "*.app")))
            # GOG Linux: Higurashi might be inside a 'game' subfolder
            extraPaths.extend(glob.glob(os.path.join(gamePath, "game")))

        pathsToBeScanned += extraPaths

    logger.printNoTerminal("Scanning:\n\t- " + "\n\t- ".join(pathsToBeScanned))

    for gamePath in pathsToBeScanned:
        possibleIdentifiers = getPossibleIdentifiersFromFolder(gamePath)
        subModConfigsInThisGamePath = set()

        possibleSteamPaths = [
            os.path.join(gamePath, "steam_api.dll"),
            os.path.join(gamePath, "Contents/Plugins/CSteamworks.bundle"),
            os.path.join(gamePath, "libsteam_api.so")
        ]

        isSteam = False
        for possibleSteamPath in possibleSteamPaths:
            if os.path.exists(possibleSteamPath):
                isSteam = True

        if gamePathIsPartiallyUninstalled(gamePath):
            returnedPartiallyUninstalledPaths.append(gamePath)

        for possibleIdentifier in possibleIdentifiers:
            try:
                # Add each submod which is compatible with the found identifier, unless it has already been detected at this path.
                for subModConfig in subModConfigDictionary[possibleIdentifier]:
                    if subModConfig not in subModConfigsInThisGamePath:
                        subModConfigsInThisGamePath.add(subModConfig)
                        returnedFullConfigs.append(
                            installConfiguration.FullInstallConfiguration(
                                subModConfig, gamePath, isSteam))
                        print("Found Game [{}] at [{}] id [{}]".format(
                            subModConfig.modName, gamePath,
                            possibleIdentifier))

            except KeyError:
                pass

    return returnedFullConfigs, returnedPartiallyUninstalledPaths
Пример #4
0
	def test_filterFileListInner(self):
		modList = self.getModListFromDummyJSON()

		mod = modList[0]
		submod = mod['submods'][0]

		subModConfig = installConfiguration.SubModConfig(mod, submod)
		fullConfig = installConfiguration.FullInstallConfiguration(subModConfig, '.', True)
		fileList = fullConfig.buildFileListSorted('datadir')

		# Test if versions have not changed
		unchangedTestSet = (json.loads("""
		{
			"id" : "Onikakushi Ch.1/full",
			"lastAttemptedInstallID" : "Onikakushi Ch.1/full",
			"files":[
				{"id": "cg",      "version": "1.0.0"},
				{"id": "cgalt",   "version": "1.0.0"},
				{"id": "movie",   "version": "1.0.0"},
				{"id": "voices",  "version": "1.0.0"},
				{"id": "script",  "version": "6.1.0"},
				{"id": "ui-windows",  "version": "2.1.0"}
			]
		}
		"""), json.loads("""
		{
			"id" : "Onikakushi Ch.1/full",
			"lastAttemptedInstallID" : "Onikakushi Ch.1/full",
			"files":[
				{"id": "cg",      "version": "1.0.0"},
				{"id": "cgalt",   "version": "1.0.0"},
				{"id": "movie",   "version": "1.0.0"},
				{"id": "voices",  "version": "1.0.0"},
				{"id": "script",  "version": "6.1.0"},
				{"id": "ui-windows",  "version": "2.1.0"}
			]
		}
		"""))

		updateInformation = fileVersionManagement.getFilesNeedingUpdate(fileList,
		                                            fileVersionManagement.SubModVersionInfo(unchangedTestSet[0]),
		                                            fileVersionManagement.SubModVersionInfo(unchangedTestSet[1]))

		result = convertUpdateInformationToModFileList(fileList, updateInformation)

		self.assertEqual(result, [])
		print("Unchanged", [x.id for x in result])

		# Test if 'cg' version changes, that both 'cg' and 'script' need update
		dependencyTestSet = (json.loads("""
		{
			"id" : "Onikakushi Ch.1/full",
			"lastAttemptedInstallID" : "Onikakushi Ch.1/full",
			"files":[
				{"id": "cg",      "version": "1.0.0"},
				{"id": "cgalt",   "version": "1.0.0"},
				{"id": "movie",   "version": "1.0.0"},
				{"id": "voices",  "version": "1.0.0"},
				{"id": "script",  "version": "6.1.0"},
				{"id": "ui-windows",  "version": "2.1.0"}
			]
		}
		"""), json.loads("""
		{
			"id" : "Onikakushi Ch.1/full",
			"lastAttemptedInstallID" : "Onikakushi Ch.1/full",
			"files":[
				{"id": "cg",      "version": "1.0.1"},
				{"id": "cgalt",   "version": "1.0.0"},
				{"id": "movie",   "version": "1.0.0"},
				{"id": "voices",  "version": "1.0.0"},
				{"id": "script",  "version": "6.1.0"},
				{"id": "ui-windows",  "version": "2.1.0"}
			]
		}
		"""))

		updateInformation = fileVersionManagement.getFilesNeedingUpdate(fileList, fileVersionManagement.SubModVersionInfo(dependencyTestSet[0]),
		                                            fileVersionManagement.SubModVersionInfo(dependencyTestSet[1]))

		result = convertUpdateInformationToModFileList(fileList, updateInformation)

		idSet = set(x.id for x in result)
		self.assertIn('cg', idSet) #cg changed version
		self.assertIn('script', idSet) #script is a dependency of cg (must overwrite cg)
		idSet.remove('cg')
		idSet.remove('script')
		self.assertEqual(idSet, set()) #no other items should remain in the list