< Summary - Jellyfin

Information
Class: MediaBrowser.Providers.Plugins.MusicBrainz.MusicBrainzArtistProvider
Assembly: MediaBrowser.Providers
File(s): /srv/git/jellyfin/MediaBrowser.Providers/Plugins/MusicBrainz/MusicBrainzArtistProvider.cs
Line coverage
0%
Covered lines: 0
Uncovered lines: 48
Coverable lines: 48
Total lines: 131
Line coverage: 0%
Branch coverage
0%
Covered branches: 0
Total branches: 28
Branch coverage: 0%
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Coverage history

Coverage history 0 25 50 75 100 2/13/2026 - 12:11:21 AM Line coverage: 54.2% (19/35) Branch coverage: 25% (3/12) Total lines: 1864/15/2026 - 12:14:34 AM Line coverage: 52.7% (19/36) Branch coverage: 25% (3/12) Total lines: 1904/19/2026 - 12:14:27 AM Line coverage: 26.7% (19/71) Branch coverage: 9.3% (3/32) Total lines: 1905/7/2026 - 12:15:44 AM Line coverage: 0% (0/48) Branch coverage: 0% (0/28) Total lines: 131 2/13/2026 - 12:11:21 AM Line coverage: 54.2% (19/35) Branch coverage: 25% (3/12) Total lines: 1864/15/2026 - 12:14:34 AM Line coverage: 52.7% (19/36) Branch coverage: 25% (3/12) Total lines: 1904/19/2026 - 12:14:27 AM Line coverage: 26.7% (19/71) Branch coverage: 9.3% (3/32) Total lines: 1905/7/2026 - 12:15:44 AM Line coverage: 0% (0/48) Branch coverage: 0% (0/28) Total lines: 131

Coverage delta

Coverage delta 27 -27

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity Line coverage
get_Name()100%210%
get_Order()100%210%
GetSearchResults()0%7280%
GetResultsFromResponse()0%2040%
GetResultFromResponse(...)0%7280%
GetMetadata()0%7280%
GetImageResponse(...)100%210%

File(s)

/srv/git/jellyfin/MediaBrowser.Providers/Plugins/MusicBrainz/MusicBrainzArtistProvider.cs

#LineLine coverage
 1using System;
 2using System.Collections.Generic;
 3using System.Linq;
 4using System.Net.Http;
 5using System.Threading;
 6using System.Threading.Tasks;
 7using Jellyfin.Extensions;
 8using MediaBrowser.Controller.Entities.Audio;
 9using MediaBrowser.Controller.Providers;
 10using MediaBrowser.Model.Entities;
 11using MediaBrowser.Model.Providers;
 12using MediaBrowser.Providers.Music;
 13using MetaBrainz.MusicBrainz;
 14using MetaBrainz.MusicBrainz.Interfaces.Entities;
 15using MetaBrainz.MusicBrainz.Interfaces.Searches;
 16
 17namespace MediaBrowser.Providers.Plugins.MusicBrainz;
 18
 19/// <summary>
 20/// MusicBrainz artist provider.
 21/// </summary>
 22public class MusicBrainzArtistProvider : IRemoteMetadataProvider<MusicArtist, ArtistInfo>, IHasOrder
 23{
 24    /// <inheritdoc />
 025    public string Name => "MusicBrainz";
 26
 27    /// <inheritdoc />
 28    /// Runs first to populate the MusicBrainz artist ID used by downstream providers.
 029    public int Order => 0;
 30
 31    /// <inheritdoc />
 32    public async Task<IEnumerable<RemoteSearchResult>> GetSearchResults(ArtistInfo searchInfo, CancellationToken cancell
 33    {
 034        var query = MusicBrainz.Plugin.Instance!.MusicBrainzQuery;
 035        var artistId = searchInfo.GetMusicBrainzArtistId();
 36
 037        if (!string.IsNullOrWhiteSpace(artistId))
 38        {
 039            var artistResult = await query.LookupArtistAsync(new Guid(artistId), Include.Aliases, null, null, cancellati
 040            return GetResultFromResponse(artistResult).SingleItemAsEnumerable();
 41        }
 42
 043        var artistSearchResults = await query.FindArtistsAsync($"\"{searchInfo.Name}\"", null, null, false, cancellation
 044            .ConfigureAwait(false);
 045        if (artistSearchResults.Results.Count > 0)
 46        {
 047            return GetResultsFromResponse(artistSearchResults.Results);
 48        }
 49
 050        if (searchInfo.Name.HasDiacritics())
 51        {
 52            // Try again using the search with an accented characters query
 053            var artistAccentsSearchResults = await query.FindArtistsAsync($"artistaccent:\"{searchInfo.Name}\"", null, n
 054                .ConfigureAwait(false);
 055            if (artistAccentsSearchResults.Results.Count > 0)
 56            {
 057                return GetResultsFromResponse(artistAccentsSearchResults.Results);
 58            }
 59        }
 60
 061        return Enumerable.Empty<RemoteSearchResult>();
 062    }
 63
 64    private IEnumerable<RemoteSearchResult> GetResultsFromResponse(IEnumerable<ISearchResult<IArtist>>? releaseSearchRes
 65    {
 066        if (releaseSearchResults is null)
 67        {
 068            yield break;
 69        }
 70
 071        foreach (var result in releaseSearchResults)
 72        {
 073            yield return GetResultFromResponse(result.Item);
 74        }
 075    }
 76
 77    private RemoteSearchResult GetResultFromResponse(IArtist artist)
 78    {
 079        var searchResult = new RemoteSearchResult
 080        {
 081            Name = artist.Name,
 082            ProductionYear = artist.LifeSpan?.Begin?.Year,
 083            PremiereDate = artist.LifeSpan?.Begin?.NearestDate,
 084            SearchProviderName = Name,
 085        };
 86
 087        searchResult.SetProviderId(MetadataProvider.MusicBrainzArtist, artist.Id.ToString());
 88
 089        return searchResult;
 90    }
 91
 92    /// <inheritdoc />
 93    public async Task<MetadataResult<MusicArtist>> GetMetadata(ArtistInfo info, CancellationToken cancellationToken)
 94    {
 095        var result = new MetadataResult<MusicArtist> { Item = new MusicArtist() };
 96
 097        var musicBrainzId = info.GetMusicBrainzArtistId();
 98
 099        if (string.IsNullOrWhiteSpace(musicBrainzId))
 100        {
 0101            var searchResults = await GetSearchResults(info, cancellationToken).ConfigureAwait(false);
 102
 0103            var singleResult = searchResults.FirstOrDefault();
 104
 0105            if (singleResult is not null)
 106            {
 0107                musicBrainzId = singleResult.GetProviderId(MetadataProvider.MusicBrainzArtist);
 0108                result.Item.Overview = singleResult.Overview;
 109
 0110                if (Plugin.Instance!.Configuration.ReplaceArtistName)
 111                {
 0112                    result.Item.Name = singleResult.Name;
 113                }
 114            }
 115        }
 116
 0117        if (!string.IsNullOrWhiteSpace(musicBrainzId))
 118        {
 0119            result.HasMetadata = true;
 0120            result.Item.SetProviderId(MetadataProvider.MusicBrainzArtist, musicBrainzId);
 121        }
 122
 0123        return result;
 0124    }
 125
 126    /// <inheritdoc />
 127    public Task<HttpResponseMessage> GetImageResponse(string url, CancellationToken cancellationToken)
 128    {
 0129        throw new NotImplementedException();
 130    }
 131}