Skip to content

Commit

Permalink
Merge pull request #8 from Fazzani/feature/add-codacy
Browse files Browse the repository at this point in the history
feat: Add Codacy CI
  • Loading branch information
Fazzani committed Jan 1, 2025
2 parents 7ab66d4 + 85addef commit 2b30bbf
Show file tree
Hide file tree
Showing 13 changed files with 76 additions and 40 deletions.
1 change: 1 addition & 0 deletions .github/FUNDING.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
github: [Fazzani]
4 changes: 2 additions & 2 deletions .github/pull_request_template.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,8 @@ _Put an `x` in the boxes that apply_
- [ ] Bugfix (non-breaking change which fixes an issue)
- [ ] New feature (non-breaking change which adds functionality)
- [ ] Breaking change (fix or feature that would cause existing functionality to not work as expected)
- [ ] Documentation Update (if none of the other choices apply)
- [ ] CI/CD or unit tests improvements
- [ ] Documentation Update
- [ ] CI/CD or unit tests improvements (if none of the other choices apply)

## Further comments

Expand Down
8 changes: 7 additions & 1 deletion .github/workflows/pr.yml
Original file line number Diff line number Diff line change
Expand Up @@ -55,4 +55,10 @@ jobs:
if: github.event_name == 'pull_request'
with:
recreate: true
path: code-coverage-results.md
path: code-coverage-results.md

- name: Run codacy-coverage-reporter
uses: codacy/[email protected]
with:
project-token: ${{ secrets.CODACY_PROJECT_TOKEN }}
coverage-reports: coverage/**/coverage.cobertura.xml
7 changes: 6 additions & 1 deletion CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -38,4 +38,9 @@ If you have a suggestion that would make this better, please fork the repo and c
```sh
dotnet run ./src/Proxarr.Api/Proxarr.Api.csproj
```
<p align="right"><a href="#readme-top"><img src="images/back-to-top.png" alt="back to top" width="35" /></a></p>

<p align="right">
<a href="#readme-top">
<img src="images/back-to-top.png" alt="back to top" width="35" />
</a>
</p>
24 changes: 14 additions & 10 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -65,22 +65,22 @@ It uses TMDB to find out which streaming services are available in the selected

* Acquire TMDB API KEY
[How](https://dev.to/codexive_zech/streamlining-your-contribution-how-to-get-your-tmdb-api-key-for-ldbflix-contribution-52gf#:~:text=How%20to%20Obtain%20a%20TMDB%20API%20Key)
* Obtain SONARR/RADARR API KEY<br/>
<img src="images/arr_api_key.png" width="230">
* Obtain SONARR/RADARR API KEY
<br/><img src="images/arr_api_key.png" width="230">

### Installation with Docker compose

1. Prepare your [config.yml][config-yml] to fit your setup
2. On your Radarr/Sonarr instances we have to do some changes
- tag all indexers by the TAG_NAME defined in your [config.yml][config-yml] (`q` by default)<br/>
<img src="images/tagging-indexers.png" width="250" alt="tag indexers" />
- tag all indexers by the TAG_NAME defined in your [config.yml][config-yml] (`q` by default)
<br/><img src="images/tagging-indexers.png" width="250" alt="tag indexers" />
- specify Application URL: is essential because it is used by Proxarr to determine to which instance should return the response<br/>
<img src="images/application_url.png" width="250" alt="Application Url config"/>
- establish a Webhook connection between Sonarr/Radarr and Proxarr<br/>
<img src="images/webhook_config.png" width="250" alt="Application Url config"/><br/>
_Note_ : Webhook URL is `http://<Proxarr_Instance>/api/qualifier
3. Add the following to your docker-compose.yml (to be adapted according to your stack)<br/>
[docker-compose.yml](docker-compose.yml) is an another full example of how to integrate Proxarr with Sonarr and Radarr.
- establish a Webhook connection between Sonarr/Radarr and Proxarr
<br/><img src="images/webhook_config.png" width="250" alt="Application Url config"/>
<br/>_Note_ : Webhook URL is `http://<Proxarr_Instance>/api/qualifier
3. Add the following to your docker-compose.yml (to be adapted according to your stack)
<br/>[docker-compose.yml](docker-compose.yml) is an another full example of how to integrate Proxarr with Sonarr and Radarr.
```yaml
proxarr:
image: synker/proxarr:latest
Expand Down Expand Up @@ -117,7 +117,11 @@ It uses TMDB to find out which streaming services are available in the selected
docker run -itd --rm -e LOG_LEVEL=Debug -p 8880:8880 -v ${PWD}/config:/app/config --name proxarr synker/proxarr:latest
```

<p align="right"><a href="#readme-top"><img src="images/back-to-top.png" alt="back to top" width="35" /></a></p>
<p align="right">
<a href="#readme-top">
<img src="images/back-to-top.png" alt="back to top" width="35" />
</a>
</p>

### Watching providers configuration

Expand Down
13 changes: 6 additions & 7 deletions src/Proxarr.Api.Tests/RadarrServiceTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ public async Task Qualify_ShouldReturnNotFound_WhenMovieNotFoundIntoRadarr()
};
var cancellationToken = new CancellationToken();

_tmdbClientMock.Setup(x => x.GetMovieAsync(123, MovieMethods.WatchProviders, cancellationToken))
_tmdbClientMock.Setup(x => x.GetMovieAsync(123, cancellationToken, MovieMethods.WatchProviders))
.ReturnsAsync(new TMDbLib.Objects.Movies.Movie { WatchProviders = new SingleResultContainer<Dictionary<string, WatchProviders>> { Results = [] } });

_radarrClientMock.Setup(x => x.MovieGET2Async(1, cancellationToken))
Expand All @@ -86,7 +86,7 @@ public async Task Qualify_ShouldReturnNotFound_WhenMovieNotFoundIntoTMDB()
};
var cancellationToken = new CancellationToken();

_tmdbClientMock.Setup(x => x.GetMovieAsync(123, MovieMethods.WatchProviders, cancellationToken))
_tmdbClientMock.Setup(x => x.GetMovieAsync(123, cancellationToken, MovieMethods.WatchProviders))
.ReturnsAsync((TMDbLib.Objects.Movies.Movie)null);

_radarrClientMock.Setup(x => x.MovieGET2Async(1, cancellationToken))
Expand Down Expand Up @@ -121,7 +121,7 @@ public async Task Qualify_ShouldUpdateTags_WhenMovieFound()

var seriesResource = new MovieResource { Id = 1, Title = "Test Series", Tags = [] };

_tmdbClientMock.Setup(x => x.GetMovieAsync(123, MovieMethods.WatchProviders, cancellationToken))
_tmdbClientMock.Setup(x => x.GetMovieAsync(123, cancellationToken, MovieMethods.WatchProviders))
.ReturnsAsync(new TMDbLib.Objects.Movies.Movie { WatchProviders = watchProviders });

_radarrClientMock.Setup(x => x.MovieGET2Async(1, cancellationToken))
Expand Down Expand Up @@ -163,7 +163,7 @@ public async Task Qualify_Should_NotBeTagged_When_MatchedWatchProvider()

var movieResource = new MovieResource { Id = 1, Title = "Test Series", Tags = [] };

_tmdbClientMock.Setup(x => x.GetMovieAsync(123, MovieMethods.WatchProviders, cancellationToken))
_tmdbClientMock.Setup(x => x.GetMovieAsync(123, cancellationToken, MovieMethods.WatchProviders))
.ReturnsAsync(new TMDbLib.Objects.Movies.Movie { WatchProviders = watchProviders });

_radarrClientMock.Setup(x => x.MovieGET2Async(1, cancellationToken))
Expand Down Expand Up @@ -210,7 +210,7 @@ public async Task Qualify_Should_BeTagged_When_MatchedWatchProvider()

var movieResource = new MovieResource { Id = 1, Title = "Test Series", Tags = [] };

_tmdbClientMock.Setup(x => x.GetMovieAsync(123, MovieMethods.WatchProviders, cancellationToken))
_tmdbClientMock.Setup(x => x.GetMovieAsync(123, cancellationToken, MovieMethods.WatchProviders))
.ReturnsAsync(new TMDbLib.Objects.Movies.Movie { WatchProviders = watchProviders });

_radarrClientMock.Setup(x => x.MovieGET2Async(1, cancellationToken))
Expand Down Expand Up @@ -246,10 +246,9 @@ public async Task Qualify_Should_BeTagged_When_NoWatchProviders()
};
var cancellationToken = new CancellationToken();


var movieResource = new MovieResource { Id = 1, Title = "Test Series", Tags = [] };

_tmdbClientMock.Setup(x => x.GetMovieAsync(123, MovieMethods.WatchProviders, cancellationToken))
_tmdbClientMock.Setup(x => x.GetMovieAsync(123, cancellationToken, MovieMethods.WatchProviders))
.ReturnsAsync(new TMDbLib.Objects.Movies.Movie());

_radarrClientMock.Setup(x => x.MovieGET2Async(1, cancellationToken))
Expand Down
14 changes: 7 additions & 7 deletions src/Proxarr.Api.Tests/SonarrServiceTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@ public async Task Qualify_ShouldReturnNotFound_WhenSeriesNotFoundIntoSonarr()
};
var cancellationToken = new CancellationToken();

_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, TvShowMethods.WatchProviders, null, null, cancellationToken))
_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, cancellationToken, TvShowMethods.WatchProviders))
.ReturnsAsync(new TvShow { WatchProviders = new SingleResultContainer<Dictionary<string, WatchProviders>> { Results = [] } });

_sonarrClientMock.Setup(x => x.SeriesGETAsync(1, false, cancellationToken))
Expand All @@ -85,7 +85,7 @@ public async Task Qualify_ShouldReturnNotFound_WhenSeriesNotFoundIntoTMDB()
};
var cancellationToken = new CancellationToken();

_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, TvShowMethods.WatchProviders, null, null, cancellationToken))
_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, cancellationToken, TvShowMethods.WatchProviders))
.ReturnsAsync((TvShow)null);

_sonarrClientMock.Setup(x => x.SeriesGETAsync(1, false, cancellationToken))
Expand Down Expand Up @@ -120,7 +120,7 @@ public async Task Qualify_ShouldUpdateTags_WhenSeriesFound()

var seriesResource = new SeriesResource { Id = 1, Title = "Test Series", Tags = [] };

_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, TvShowMethods.WatchProviders, null, null, cancellationToken))
_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, cancellationToken, TvShowMethods.WatchProviders))
.ReturnsAsync(new TvShow { WatchProviders = watchProviders });

_sonarrClientMock.Setup(x => x.SeriesGETAsync(1, false, cancellationToken))
Expand Down Expand Up @@ -162,7 +162,7 @@ public async Task Qualify_Should_NotBeTagged_When_MatchedWatchProvider()

var seriesResource = new SeriesResource { Id = 1, Title = "Test Series", Tags = [] };

_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, TvShowMethods.WatchProviders, null, null, cancellationToken))
_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, cancellationToken, TvShowMethods.WatchProviders))
.ReturnsAsync(new TvShow { WatchProviders = watchProviders });

_sonarrClientMock.Setup(x => x.SeriesGETAsync(1, false, cancellationToken))
Expand Down Expand Up @@ -208,7 +208,7 @@ public async Task Qualify_Should_BeTagged_When_MatchedWatchProvider()

var seriesResource = new SeriesResource { Id = 1, Title = "Test Series", Tags = [] };

_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, TvShowMethods.WatchProviders, null, null, cancellationToken))
_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, cancellationToken, TvShowMethods.WatchProviders))
.ReturnsAsync(new TvShow { WatchProviders = watchProviders });

_sonarrClientMock.Setup(x => x.SeriesGETAsync(1, false, cancellationToken))
Expand Down Expand Up @@ -244,8 +244,8 @@ public async Task Qualify_Should_BeTagged_When_NoWatchProvider()

var seriesResource = new SeriesResource { Id = 1, Title = "Test Series", Tags = [] };

_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, TvShowMethods.WatchProviders, null, null, cancellationToken))
.ReturnsAsync(new TvShow ());
_tmdbClientMock.Setup(x => x.GetTvShowAsync(123, cancellationToken, TvShowMethods.WatchProviders))
.ReturnsAsync(new TvShow());

_sonarrClientMock.Setup(x => x.SeriesGETAsync(1, false, cancellationToken))
.ReturnsAsync(seriesResource);
Expand Down
2 changes: 1 addition & 1 deletion src/Proxarr.Api/Configuration/ClientConfiguration.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ namespace Proxarr.Api.Configuration
[ExcludeFromCodeCoverage]
public sealed class ClientConfiguration
{
public const string SECTION_NAME = $"{AppConfiguration.SECTION_NAME}:Clients";
public static string SECTION_NAME { get; } = $"{AppConfiguration.SECTION_NAME}:Clients";

/// <summary>
/// Must be Sonarr or Radarr
Expand Down
7 changes: 6 additions & 1 deletion src/Proxarr.Api/Core/CronJobService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -28,10 +28,15 @@ protected virtual async Task ScheduleJob(CancellationToken cancellationToken)
while (!cancellationToken.IsCancellationRequested)
{
var next = _expression.GetNextOccurrence(DateTimeOffset.Now, timeZoneInfo);
if (!next.HasValue) continue;

if (!next.HasValue)
{
continue;
}

logger.LogInformation("{JobName}: scheduled next run at {NextRun}", GetType().Name, next.ToString());
var delay = next.Value - DateTimeOffset.Now;

if (delay.TotalMilliseconds <= 0) // prevent non-positive values from being passed into Timer
{
logger.LogInformation("{LoggerName}: scheduled next run is in the past. Moving to next.", GetType().Name);
Expand Down
6 changes: 5 additions & 1 deletion src/Proxarr.Api/Core/Http/BasicAuthenticationHandler.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,11 @@ namespace Proxarr.Api.Core.Http
[ExcludeFromCodeCoverage]
public class BasicAuthenticationDefaults
{
public const string AuthenticationScheme = "Basic";
protected BasicAuthenticationDefaults()
{
}

public static string AuthenticationScheme { get; } = "Basic";
}

[ExcludeFromCodeCoverage]
Expand Down
22 changes: 17 additions & 5 deletions src/Proxarr.Api/Core/TmdbProxy.cs
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,10 @@ namespace Proxarr.Api.Core
{
public interface ITmdbProxy
{
Task<Movie> GetMovieAsync(int movieId, MovieMethods extraMethods = MovieMethods.Undefined, CancellationToken cancellationToken = default);
Task<TvShow> GetTvShowAsync(int id, TvShowMethods extraMethods = TvShowMethods.Undefined, string language = null, string includeImageLanguage = null, CancellationToken cancellationToken = default);
Task<Movie> GetMovieAsync(int movieId, MovieMethods extraMethods = MovieMethods.Undefined);
Task<Movie> GetMovieAsync(int movieId, CancellationToken cancellationToken, MovieMethods extraMethods = MovieMethods.Undefined);
Task<TvShow> GetTvShowAsync(int id, TvShowMethods extraMethods = TvShowMethods.Undefined);
Task<TvShow> GetTvShowAsync(int id, CancellationToken cancellationToken, TvShowMethods extraMethods = TvShowMethods.Undefined);
}

[ExcludeFromCodeCoverage]
Expand All @@ -22,12 +24,22 @@ public TmdbProxy(TMDbClient tMDbClient)
_tMDbClient = tMDbClient;
}

public Task<TvShow> GetTvShowAsync(int id, TvShowMethods extraMethods = TvShowMethods.Undefined, string language = null, string includeImageLanguage = null, CancellationToken cancellationToken = default)
public Task<TvShow> GetTvShowAsync(int id, TvShowMethods extraMethods = TvShowMethods.Undefined)
{
return _tMDbClient.GetTvShowAsync(id, extraMethods, language, includeImageLanguage, cancellationToken);
return _tMDbClient.GetTvShowAsync(id, extraMethods, null, null, CancellationToken.None);
}

public Task<Movie> GetMovieAsync(int movieId, MovieMethods extraMethods = MovieMethods.Undefined, CancellationToken cancellationToken = default)
public Task<TvShow> GetTvShowAsync(int id, CancellationToken cancellationToken, TvShowMethods extraMethods = TvShowMethods.Undefined)
{
return _tMDbClient.GetTvShowAsync(id, extraMethods, null, null, cancellationToken);
}

public Task<Movie> GetMovieAsync(int movieId, MovieMethods extraMethods = MovieMethods.Undefined)
{
return _tMDbClient.GetMovieAsync(movieId, extraMethods, CancellationToken.None);
}

public Task<Movie> GetMovieAsync(int movieId, CancellationToken cancellationToken, MovieMethods extraMethods = MovieMethods.Undefined)
{
return _tMDbClient.GetMovieAsync(movieId, extraMethods, cancellationToken);
}
Expand Down
4 changes: 2 additions & 2 deletions src/Proxarr.Api/Services/RadarrService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ public async Task<string> Qualify(MovieAdded movieAdded, CancellationToken cance
_logger.LogInformation("Qualifying movie {Title}", movieAdded.Movie.Title);

var tmdbItem = await _tMDbClient
.GetMovieAsync(movieAdded.Movie.TmdbId, TMDbLib.Objects.Movies.MovieMethods.WatchProviders, cancellationToken)
.GetMovieAsync(movieAdded.Movie.TmdbId, cancellationToken, TMDbLib.Objects.Movies.MovieMethods.WatchProviders)
.ConfigureAwait(false);

if (tmdbItem != null)
Expand Down Expand Up @@ -135,7 +135,7 @@ private async Task<bool> AddTag(MovieResource movieRadarr,
{
_logger.LogInformation("Adding tag {Tag} for {Title}", tag.Label, movieRadarr.Title);
movieRadarr.Tags.Add(tag.Id);
updated = true;
return true;
}

return updated;
Expand Down
4 changes: 2 additions & 2 deletions src/Proxarr.Api/Services/SonarrService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ public async Task<string> Qualify(TvAdded tvAdded, CancellationToken cancellatio
_logger.LogInformation("Qualifying tv {Title}", tvAdded.Series.Title);

var tmdbItem = await _tMDbClient
.GetTvShowAsync(tvAdded.Series.TmdbId, TMDbLib.Objects.TvShows.TvShowMethods.WatchProviders, cancellationToken: cancellationToken)
.GetTvShowAsync(tvAdded.Series.TmdbId, cancellationToken, TMDbLib.Objects.TvShows.TvShowMethods.WatchProviders)
.ConfigureAwait(false);

if (tmdbItem != null)
Expand Down Expand Up @@ -135,7 +135,7 @@ private async Task<bool> AddTag(SeriesResource seriesSonarr,
{
_logger.LogInformation("Adding tag {Tag} for {Title}", tag.Label, seriesSonarr.Title);
seriesSonarr.Tags.Add(tag.Id);
updated = true;
return true;
}

return updated;
Expand Down

0 comments on commit 2b30bbf

Please sign in to comment.