add option to get storage usage per library (#242)

See how much space each library uses.
This commit is contained in:
Kilian von Pflugk 2024-08-10 10:25:06 +00:00 committed by GitHub
parent bf5402d2bd
commit 92aa5fef88
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 93 additions and 4 deletions

View File

@ -541,7 +541,7 @@
<h3 style="margin:0">Introduction timestamp editor</h3> <h3 style="margin:0">Introduction timestamp editor</h3>
<p style="margin:0">All times are displayed in the format (HH:MM:SS)</p> <p style="margin:0">All times are displayed in the format (HH:MM:SS)</p>
<br /> <br />
<table class="detailTable"> <table class="detailTable">
<tr> <tr>
<th scope="col" class="detailTableHeaderCell">Episode</th> <th scope="col" class="detailTableHeaderCell">Episode</th>
<th scope="col" class="detailTableHeaderCell">Section</th> <th scope="col" class="detailTableHeaderCell">Section</th>
@ -639,7 +639,7 @@
<br /> <br />
<br /> <br />
<div id="eraseSeasonContainer" style="display: none;"> <div id="eraseSeasonContainer" style="display: none;">
<button id="btnEraseSeasonTimestamps" type="button"> <button id="btnEraseSeasonTimestamps" type="button">
Erase all timestamps for this season Erase all timestamps for this season
</button> </button>
@ -647,7 +647,7 @@
<input type="checkbox" id="eraseSeasonCacheCheckbox" style="margin-left: 10px;"> <input type="checkbox" id="eraseSeasonCacheCheckbox" style="margin-left: 10px;">
<label for="eraseSeasonCacheCheckbox" style="margin-left: 5px;">Erase cached fingerprint files</label> <label for="eraseSeasonCacheCheckbox" style="margin-left: 5px;">Erase cached fingerprint files</label>
</div> </div>
<hr /> <br />
<button id="btnEraseIntroTimestamps"> <button id="btnEraseIntroTimestamps">
Erase all introduction timestamps (globally) Erase all introduction timestamps (globally)
@ -662,6 +662,15 @@
<input type="checkbox" id="eraseModeCacheCheckbox" style="margin-left: 10px;"> <input type="checkbox" id="eraseModeCacheCheckbox" style="margin-left: 10px;">
<label for="eraseModeCacheCheckbox" style="margin-left: 5px;">Erase cached fingerprint files</label> <label for="eraseModeCacheCheckbox" style="margin-left: 5px;">Erase cached fingerprint files</label>
</details> </details>
<details id="storage">
<br />
<summary>Storage Usage</summary>
<div class="fieldDescription">
See how much space each library uses.
</div>
<textarea id="storage" rows="20" cols="75" readonly></textarea>
</details>
</fieldset> </fieldset>
</div> </div>
</div> </div>
@ -683,6 +692,7 @@
// settings elements // settings elements
var visualizer = document.querySelector("details#visualizer"); var visualizer = document.querySelector("details#visualizer");
var support = document.querySelector("details#support"); var support = document.querySelector("details#support");
var storage = document.querySelector("details#storage");
var btnEraseIntroTimestamps = document.querySelector("button#btnEraseIntroTimestamps"); var btnEraseIntroTimestamps = document.querySelector("button#btnEraseIntroTimestamps");
var btnEraseCreditTimestamps = document.querySelector("button#btnEraseCreditTimestamps"); var btnEraseCreditTimestamps = document.querySelector("button#btnEraseCreditTimestamps");
@ -852,6 +862,21 @@
} }
} }
// fetch the storage whenever the detail section is opened.
async function storageToggled() {
if (!storage.open) {
return;
}
// Fetch the support bundle
const bundle = await fetchWithAuth("IntroSkipper/Storage", "GET", null);
const bundleText = await bundle.text();
// Display it to the user
const ta = document.querySelector("textarea#storage");
ta.value = bundleText;
}
// show changed, populate seasons // show changed, populate seasons
async function showChanged() { async function showChanged() {
clearSelect(selectSeason); clearSelect(selectSeason);
@ -1149,6 +1174,7 @@
visualizer.addEventListener("toggle", visualizerToggled); visualizer.addEventListener("toggle", visualizerToggled);
support.addEventListener("toggle", supportToggled); support.addEventListener("toggle", supportToggled);
storage.addEventListener("toggle", storageToggled);
txtOffset.addEventListener("change", renderTroubleshooter); txtOffset.addEventListener("change", renderTroubleshooter);
selectShow.addEventListener("change", showChanged); selectShow.addEventListener("change", showChanged);
selectSeason.addEventListener("change", seasonChanged); selectSeason.addEventListener("change", seasonChanged);

View File

@ -1,9 +1,11 @@
using System; using System;
using System.Globalization;
using System.IO;
using System.Net.Mime; using System.Net.Mime;
using System.Text; using System.Text;
using MediaBrowser.Common; using MediaBrowser.Common;
using MediaBrowser.Common.Api; using MediaBrowser.Common.Api;
using MediaBrowser.Common.Configuration; using MediaBrowser.Controller.Library;
using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging; using Microsoft.Extensions.Logging;
@ -19,6 +21,7 @@ namespace ConfusedPolarBear.Plugin.IntroSkipper.Controllers;
[Route("IntroSkipper")] [Route("IntroSkipper")]
public class TroubleshootingController : ControllerBase public class TroubleshootingController : ControllerBase
{ {
private readonly ILibraryManager _libraryManager;
private readonly IApplicationHost _applicationHost; private readonly IApplicationHost _applicationHost;
private readonly ILogger<TroubleshootingController> _logger; private readonly ILogger<TroubleshootingController> _logger;
@ -26,11 +29,14 @@ public class TroubleshootingController : ControllerBase
/// Initializes a new instance of the <see cref="TroubleshootingController"/> class. /// Initializes a new instance of the <see cref="TroubleshootingController"/> class.
/// </summary> /// </summary>
/// <param name="applicationHost">Application host.</param> /// <param name="applicationHost">Application host.</param>
/// <param name="libraryManager">Library Manager.</param>
/// <param name="logger">Logger.</param> /// <param name="logger">Logger.</param>
public TroubleshootingController( public TroubleshootingController(
IApplicationHost applicationHost, IApplicationHost applicationHost,
ILibraryManager libraryManager,
ILogger<TroubleshootingController> logger) ILogger<TroubleshootingController> logger)
{ {
_libraryManager = libraryManager;
_applicationHost = applicationHost; _applicationHost = applicationHost;
_logger = logger; _logger = logger;
} }
@ -85,4 +91,61 @@ public class TroubleshootingController : ControllerBase
return bundle.ToString(); return bundle.ToString();
} }
/// <summary>
/// Gets a Markdown formatted support bundle.
/// </summary>
/// <response code="200">Support bundle created.</response>
/// <returns>Support bundle.</returns>
[HttpGet("Storage")]
[Produces(MediaTypeNames.Text.Plain)]
public ActionResult<string> GetFreeSpace()
{
ArgumentNullException.ThrowIfNull(Plugin.Instance);
var bundle = new StringBuilder();
var libraries = _libraryManager.GetVirtualFolders();
foreach (var library in libraries)
{
try
{
DriveInfo driveInfo = new DriveInfo(library.Locations[0]);
// Get available free space in bytes
long availableFreeSpace = driveInfo.AvailableFreeSpace;
// Get total size of the drive in bytes
long totalSize = driveInfo.TotalSize;
// Get total used space in Percentage
double usedSpacePercentage = totalSize > 0 ? (totalSize - availableFreeSpace) / (double)totalSize * 100 : 0;
bundle.Append(CultureInfo.CurrentCulture, $"Library: {library.Name}\n");
bundle.Append(CultureInfo.CurrentCulture, $"Drive: {driveInfo.Name}\n");
bundle.Append(CultureInfo.CurrentCulture, $"Total Size: {GetHumanReadableSize(totalSize)}\n");
bundle.Append(CultureInfo.CurrentCulture, $"Available Free Space: {GetHumanReadableSize(availableFreeSpace)}\n");
bundle.Append(CultureInfo.CurrentCulture, $"Total used in Percentage: {Math.Round(usedSpacePercentage, 2)}%\n\n");
}
catch (Exception ex)
{
_logger.LogWarning("Unable to get DriveInfo: {Exception}", ex);
}
}
return bundle.ToString().TrimEnd('\n');
}
private string GetHumanReadableSize(long bytes)
{
string[] sizes = ["Bytes", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"];
double len = bytes;
int order = 0;
while (len >= 1024 && order < sizes.Length - 1)
{
order++;
len = len / 1024;
}
return $"{len:0.##} {sizes[order]}";
}
} }