/********* ** Public methods *********/ /// <summary>Get manifest metadata for each folder in the given root path.</summary> /// <param name="rootPath">The root path to search for mods.</param> /// <param name="jsonHelper">The JSON helper with which to read manifests.</param> /// <param name="modDatabase">Handles access to SMAPI's internal mod metadata list.</param> /// <returns>Returns the manifests by relative folder.</returns> public IEnumerable <IModMetadata> ReadManifests(string rootPath, JsonHelper jsonHelper, ModDatabase modDatabase) { foreach (DirectoryInfo modDir in this.GetModFolders(rootPath)) { // read file Manifest manifest = null; string path = Path.Combine(modDir.FullName, "manifest.json"); string error = null; try { manifest = jsonHelper.ReadJsonFile <Manifest>(path); if (manifest == null) { error = File.Exists(path) ? "its manifest is invalid." : "it doesn't have a manifest."; } } catch (SParseException ex) { error = $"parsing its manifest failed: {ex.Message}"; } catch (Exception ex) { error = $"parsing its manifest failed:\n{ex.GetLogSummary()}"; } // parse internal data record (if any) ParsedModDataRecord dataRecord = modDatabase.GetParsed(manifest); // get display name string displayName = manifest?.Name; if (string.IsNullOrWhiteSpace(displayName)) { displayName = dataRecord?.DisplayName; } if (string.IsNullOrWhiteSpace(displayName)) { displayName = PathUtilities.GetRelativePath(rootPath, modDir.FullName); } // apply defaults if (manifest != null && dataRecord != null) { if (dataRecord.UpdateKey != null) { manifest.UpdateKeys = new[] { dataRecord.UpdateKey } } ; } // build metadata ModMetadataStatus status = error == null ? ModMetadataStatus.Found : ModMetadataStatus.Failed; yield return(new ModMetadata(displayName, modDir.FullName, manifest, dataRecord).SetStatus(status, error)); } }