Torrent fixes
All checks were successful
continuous-integration/drone/push Build is passing

This commit is contained in:
Elias Jansson
2025-08-24 23:23:21 +02:00
parent 85f559a607
commit 77f6d2a475
6 changed files with 71 additions and 63 deletions

View File

@@ -70,7 +70,10 @@ public class TorrentController : Controller
Leechers = t.Leechers,
TorrentUrl = t.TorrentUrl,
Metadata = t.Metadata,
IsNew = t.InfoHash != null && !seenHashes.Contains(t.InfoHash)
IsNew = t.InfoHash != null && !seenHashes.Contains(t.InfoHash),
AvailableOn = !string.IsNullOrEmpty(t.Metadata?.Providers)
? t.Metadata.Providers.Split(',').ToList()
: new List<string>()
})
.ToList();

View File

@@ -1,4 +1,5 @@
using System.Text;
using System.Net.Http;
using System.Text;
using System.Text.Json;
namespace Aberwyn.Data
@@ -7,6 +8,8 @@ namespace Aberwyn.Data
{
private readonly HttpClient _http;
private readonly string _apiKey = "6a666b45";
private readonly string _tpiKey = "6a666b45";
public MovieMetadataService(HttpClient httpClient)
{
@@ -44,59 +47,54 @@ namespace Aberwyn.Data
return null;
}
}
public async Task<Node?> SearchMovieAsync(string title, string country = "SE")
{
var query = new
{
query = @"
query SearchTitle($query: String!, $country: Country!) {
searchTitles(
country: $country,
filter: { searchQuery: $query },
first: 1
) {
edges {
node {
id
title
releaseYear
content {
imdbId
}
offers {
provider {
id
clearName
}
monetizationType
}
}
}
}
}",
variables = new
{
query = title,
country = country
}
};
var requestBody = new StringContent(JsonSerializer.Serialize(query), Encoding.UTF8, "application/json");
_http.DefaultRequestHeaders.Add("Accept", "application/json");
_http.DefaultRequestHeaders.Add("User-Agent", "Mozilla/5.0");
var response = await _http.PostAsync("https://apis.justwatch.com/graphql", requestBody);
if (!response.IsSuccessStatusCode)
return null;
var result = await response.Content.ReadFromJsonAsync<JustWatchResponse>();
return result?.data?.searchTitles?.edges?.FirstOrDefault()?.node;
}
}
public class TmdbService
{
private readonly HttpClient _http = new();
private readonly string _apiKey = "aef2f49296b77b9b9c269678d04bdbc6";
private readonly string _country = "SE";
public async Task<string> GetWatchProvidersByTitleAsync(string title, int? year = null)
{
var query = Uri.EscapeDataString(title);
var url = $"https://api.themoviedb.org/3/search/movie?api_key={_apiKey}&query={query}";
if (year.HasValue)
url += $"&year={year.Value}";
var searchResult = await _http.GetFromJsonAsync<TmdbSearchResponse>(url);
var movie = searchResult?.Results?.FirstOrDefault();
if (movie == null) return "";
var providersUrl = $"https://api.themoviedb.org/3/movie/{movie.Id}/watch/providers?api_key={_apiKey}";
var providersResult = await _http.GetFromJsonAsync<WatchProvidersResponse>(providersUrl);
if (providersResult?.Results?.ContainsKey(_country) == true)
{
var seProviders = providersResult.Results[_country];
var names = new List<string>();
if (seProviders.Flatrate != null) names.AddRange(seProviders.Flatrate.Select(p => p.ProviderName));
if (seProviders.Rent != null) names.AddRange(seProviders.Rent.Select(p => p.ProviderName));
if (seProviders.Buy != null) names.AddRange(seProviders.Buy.Select(p => p.ProviderName));
return string.Join(", ", names.Distinct());
}
return "";
}
}
// JSON-klasser för TMDb
public class TmdbSearchResponse { public List<TmdbMovie> Results { get; set; } = new(); }
public class TmdbMovie { public int Id { get; set; } }
public class WatchProvidersResponse { public Dictionary<string, CountryProviders> Results { get; set; } = new(); }
public class CountryProviders
{
public List<Provider>? Flatrate { get; set; }
public List<Provider>? Rent { get; set; }
public List<Provider>? Buy { get; set; }
}
public class Provider { public string ProviderName { get; set; } = ""; }
}

View File

@@ -84,15 +84,9 @@ namespace Aberwyn.Data
if (metadata != null)
{
torrentItem.Metadata = metadata;
var movie = await _movieMetadataService.SearchMovieAsync(torrentItem.MovieName);
if (movie?.offers != null)
{
metadata.Providers = movie.offers
.Where(o => o.monetizationType == "FLATRATE") // typ Netflix, Prime
.Select(o => o.provider.clearName)
.Distinct()
.ToString();
}
var tmdbService = new TmdbService();
torrentItem.Metadata.Providers = await tmdbService.GetWatchProvidersByTitleAsync(torrentItem.Title, torrentItem.Year);
}
_context.TorrentItems.Add(torrentItem);

View File

@@ -106,6 +106,7 @@ public class TorrentListItemViewModel
public string? TorrentUrl { get; set; }
public MovieMetadata? Metadata { get; set; }
public bool IsNew { get; set; } = false;
public List<string> AvailableOn { get; set; } = new();
}
public class JustWatchResponse
{

View File

@@ -75,6 +75,12 @@
⭐ @main.Metadata.ImdbRating
</a>
}
@if (main.AvailableOn?.Any() == true)
{
<div class="available-on">
Tillgänglig på: @string.Join(", ", main.AvailableOn)
</div>
}
</div>
</div>
</div>

View File

@@ -185,4 +185,10 @@
.imdb:hover {
text-decoration: underline;
}
}
.available-on {
font-size: 0.85rem;
color: #888;
margin-top: 4px;
}