diff --git a/plugins/stats/stats.js b/plugins/stats/stats.js index b54951ee..39addc03 100644 --- a/plugins/stats/stats.js +++ b/plugins/stats/stats.js @@ -15,8 +15,14 @@ statEl.appendChild(statHeading); } + // *** filter *** + // filter for * without StashID const noStashIDFilter = { stash_id_endpoint: { modifier: "NOT_NULL" } }; + // filter for missing image + const noImageFilter = { is_missing: "image" }; + // *** fetch helpers *** + // fetch performers with filter async function findPerformers(filter) { const query = `query ($filter: PerformerFilterType) { findPerformers(performer_filter: $filter) { count } }`; return await csLib @@ -24,6 +30,7 @@ .then((data) => data.findPerformers.count); } + // fetch scenes with filter async function findScenes(filter) { const query = `query ($filter: SceneFilterType) { findScenes(scene_filter: $filter) { count }}`; return await csLib @@ -31,6 +38,7 @@ .then((data) => data.findScenes.count); } + // fetch studios with filter async function findStudios(filter) { const query = `query ($filter: StudioFilterType) { findStudios(studio_filter: $filter) { count }}`; return await csLib @@ -38,9 +46,28 @@ .then((data) => data.findStudios.count); } + // fetch tags with filter + async function findTags(filter) { + const query = `query ($filter: TagFilterType) { findTags(tag_filter: $filter) { count }}`; + return await csLib + .callGQL({ query, variables: { filter } }) + .then((data) => data.findTags.count); + } + + // fetch movies with filter + async function findMovies(filter) { + const query = `query ($filter: MovieFilterType) { findMovies(movie_filter: $filter) { count }}`; + return await csLib + .callGQL({ query, variables: { filter } }) + .then((data) => data.findMovies.count); + } + + // percentage helper const percentage = (portion, total) => ((portion / total) * 100).toFixed(2) + "%"; + // *** actual stats fetching *** + // performer of scenes with any StashID async function createSceneStashIDPct(row) { const stashIdCount = await findScenes(noStashIDFilter); const totalCount = await findScenes(); @@ -52,6 +79,7 @@ ); } + // percentage of performers with any StashID async function createPerformerStashIDPct(row) { const stashIdCount = await findPerformers(noStashIDFilter); const totalCount = await findPerformers(); @@ -63,6 +91,7 @@ ); } + // percentage of studios with any StashID async function createStudioStashIDPct(row) { const stashIdCount = await findStudios(noStashIDFilter); const totalCount = await findStudios(); @@ -74,6 +103,7 @@ ); } + // number of favourite performers async function createPerformerFavorites(row) { const filter = { filter_favorites: true }; const perfCount = await findPerformers(filter); @@ -81,6 +111,7 @@ createStatElement(row, perfCount, "Favorite Performers"); } + // number of markers async function createMarkersStat(row) { const query = `query { findSceneMarkers { count }}`; const totalCount = (await csLib.callGQL({ query })).findSceneMarkers.count; @@ -88,23 +119,87 @@ createStatElement(row, totalCount, "Markers"); } + // second row stats + // tags with images + async function createTagHasImage(row) { + const missingImgCount = await findTags(noImageFilter); + const totalCount = await findTags(); + const hasImgCount = totalCount - missingImgCount; + + createStatElement(row, percentage(hasImgCount, totalCount), "Tag Images"); + } + + // studios with images + async function createStudioHasimage(row) { + const missingImgCount = await findStudios(noImageFilter); + const totalCount = await findStudios(); + const hasImgCount = totalCount - missingImgCount; + + createStatElement( + row, + percentage(hasImgCount, totalCount), + "Studio Images" + ); + } + + // performers with images + async function createPerformerHasImage(row) { + const missingImgCount = await findPerformers(noImageFilter); + const totalCount = await findPerformers(); + const hasImgCount = totalCount - missingImgCount; + + createStatElement( + row, + percentage(hasImgCount, totalCount), + "Performer Images" + ); + } + + // movies with cover images + async function createMovieHasCover(row) { + const filter = { is_missing: "front_image" }; + const missingImgCount = await findMovies(filter); + const totalCount = await findMovies(); + const hasImgCount = totalCount - missingImgCount; + + createStatElement(row, percentage(hasImgCount, totalCount), "Movie Covers"); + } + + // scenes over WEB_HD (540p) + async function createSceneOverWebHD(row) { + const filter = { + resolution: { modifier: "GREATER_THAN", value: "WEB_HD" }, + }; + const sceneCount = await findScenes(filter); + const totalCount = await findScenes(); + + createStatElement(row, percentage(sceneCount, totalCount), "Scenes HD"); + } + csLib.PathElementListener( "/stats", "div.container-fluid div.mt-5", setupStats ); function setupStats(el) { - if (document.getElementById("custom-stats-row")) return; + if (document.querySelector(".custom-stats-row")) return; const changelog = el.querySelector("div.changelog"); - const row = document.createElement("div"); - row.id = "custom-stats-row"; - row.classList = "col col-sm-8 m-sm-auto row stats"; - el.insertBefore(row, changelog); - - createSceneStashIDPct(row); - createStudioStashIDPct(row); - createPerformerStashIDPct(row); - createPerformerFavorites(row); - createMarkersStat(row); + const rowOne = document.createElement("div"); + rowOne.classList = "custom-stats-row col col-sm-8 m-sm-auto row stats"; + el.insertBefore(rowOne, changelog); + const rowTwo = rowOne.cloneNode(); + el.insertBefore(rowTwo, changelog); + // row one + createSceneStashIDPct(rowOne); + createStudioStashIDPct(rowOne); + createPerformerStashIDPct(rowOne); + createPerformerFavorites(rowOne); + createMarkersStat(rowOne); + // row two + createTagHasImage(rowTwo); + createStudioHasimage(rowTwo); + createPerformerHasImage(rowTwo); + createMovieHasCover(rowTwo); + createSceneOverWebHD(rowTwo); } })(); diff --git a/plugins/stats/stats.yml b/plugins/stats/stats.yml index 2cd9fd06..ce10caea 100644 --- a/plugins/stats/stats.yml +++ b/plugins/stats/stats.yml @@ -1,7 +1,7 @@ name: Extended Stats #requires: CommunityScriptsUILibrary description: Adds new stats to the stats page -version: 1.0 +version: 1.1 ui: requires: - CommunityScriptsUILibrary