using Microsoft.Extensions.Logging; using Microsoft.Extensions.Options; using System.Collections.Concurrent; using System.IO; using System.Text; using System.Xml.Linq; namespace zero.Backoffice.Services; public class IconService : IIconService { protected IOptions Options { get; set; } protected IBackofficeAssetFileSystem FileSystem { get; set; } protected ILogger Logger { get; set; } protected ConcurrentBag CachedSets { get; private set; } = new(); protected string CachedSvg { get; set; } protected bool IsLoaded { get; set; } public IconService(IOptions options, IBackofficeAssetFileSystem fileSystem, ILogger logger) { Options = options; FileSystem = fileSystem; Logger = logger; } /// public async Task> GetSets() { await EnsureIconsAreLoaded(); return CachedSets; } /// public async Task GetCompiledSvg() { await EnsureIconsAreLoaded(); return CachedSvg; } async Task EnsureIconsAreLoaded() { if (IsLoaded) { return; } StringBuilder svg = new(); foreach (BackofficeIconSet set in Options.Value.IconSets) { if (!await FileSystem.Exists(set.SpritePath)) { Logger.LogWarning("Could not load icon set {alias} from path {path}", set.Alias, FileSystem.Map(set.SpritePath)); continue; } using Stream stream = await FileSystem.StreamFile(set.SpritePath); XDocument xml = XDocument.Load(stream); IEnumerable symbols = xml.Descendants().Where(x => x.Name.LocalName == "symbol"); if (!symbols.Any()) { Logger.LogWarning("Icon set {alias} does not contain any ", set.Alias); continue; } HashSet icons = new(); foreach (XElement symbol in symbols) { string symbolAlias = set.Prefix + "-" + symbol.Attribute("id").Value.ToString(); symbol.SetAttributeValue("id", symbolAlias); svg.Append(symbol.ToString().RemoveNewLines()); icons.Add(symbolAlias); } CachedSets.Add(new() { Alias = set.Alias, Name = set.Name, Prefix = set.Prefix, Icons = icons }); } CachedSvg = svg.ToString(); IsLoaded = true; } } public interface IIconService { /// /// Get all registered icon sets with all their containing icons /// Task> GetSets(); /// /// Get compiled SVG string for alle registered icon sets /// Task GetCompiledSvg(); }