def content_preview_modal(request): content_discovery = TmdbDiscovery() # Get the ID from the URL tmdb_id = request.GET.get("tmdb_id", None) content_type = request.GET.get("content_type", None) if tmdb_id and content_type: # Fetch and process content = content_discovery.get_by_tmdb_id(tmdb_id, content_type, obtain_extras=False) set_single_availability(content) preprocess_tmdb_result(content) # Check if the user has already requested this requested = False if UserRequest.objects.filter( content_id=content["id"], content_type=content["content_type"], ): requested = True context = {"content": content, "requested": requested} template = loader.get_template("modal/content_preview.html") return HttpResponse(template.render(context, request))
def discover_movies(request): content_discovery = TmdbDiscovery() discover_filter = request.GET.get("filter", "") filter_name = titlecase(discover_filter.replace("-", " ")) page = int(request.GET.get("page", 1)) # Get content filter_params = {} if discover_filter == "custom": filter_params = request.GET.dict() filter_params.pop("filter") if discover_filter: add_values = preset_filter_extras(request) tmdb_results = content_discovery.discover_movie_by_filter( filter_name=discover_filter, page_number=page, add_values=add_values, **filter_params, )["results"] else: tmdb_results = content_discovery.movies(page)["results"] # Set the availability for all cards set_many_availability(tmdb_results) context = { "all_cards": tmdb_results, "content_type": "movie", "page_name": "Movies", "filter_name": filter_name, } template = loader.get_template("viewport/discover.html") return HttpResponse(template.render(context, request))
def recommended(request): tmdb_id = request.GET.get("tmdb_id", None) content_type = request.GET.get("content_type", None) if tmdb_id and content_type: content_discovery = TmdbDiscovery() tmdb_recommended = content_discovery.similar_and_recommended( tmdb_id, content_type) if not isinstance(tmdb_recommended, dict) or not tmdb_recommended: tmdb_recommended = None else: set_many_availability(tmdb_recommended["results"]) # Detect situation where all results don't have TVDB IDs results_contain_valid_id = False if is_key_value_in_list("conreq_valid_id", True, tmdb_recommended["results"]): results_contain_valid_id = True context = { "recommended": tmdb_recommended, "results_contain_valid_id": results_contain_valid_id, } template = loader.get_template( "viewport/components/more_info_recommended.html") return HttpResponse(template.render(context, request))
def search(request): content_discovery = TmdbDiscovery() searcher = TmdbSearch() # Get the ID from the URL query = request.GET.get("query", "") content_type = request.GET.get("content_type", None) page = int(request.GET.get("page", 1)) # Determine which search method to use (tv/movie/all) if content_type == "tv": tmdb_results = searcher.television(query, page) elif content_type == "movie": tmdb_results = searcher.movie(query, page) else: tmdb_results = searcher.all(query, page) if tmdb_results: tmdb_results = tmdb_results.get("results") # Determine the availability content_discovery.determine_id_validity(tmdb_results) set_many_availability(tmdb_results) context = { "all_cards": tmdb_results, "content_type": content_type, "search_query": query, } template = loader.get_template("viewport/search.html") return HttpResponse(template.render(context, request))
def generate_requests_cards(user_requests): """Takes in a DB query containing requests, and pops out a list of their current request status""" content_discovery = TmdbDiscovery() all_cards = [] function_list = [] for request in user_requests: function_list.append({ "function": __generate_request_card, "args": [request, content_discovery], }) all_cards = threaded_execution_unique_args(function_list) content_discovery.determine_id_validity(all_cards) set_many_availability(all_cards) return all_cards
def arr_auto_resolve_movie(issue_id, tmdb_id, resolutions): """Queues a background task to automatically resolve a reported issue.""" # TODO: Intelligently resolve based on "resolutions" # Check if auto resolution is turned on conreq_config = ConreqConfig.get_solo() if conreq_config.conreq_auto_resolve_issues: content_manager = ArrManager() content_discovery = TmdbDiscovery() # Grab the movie from Radarr movie = content_manager.get(force_update_cache=True, tmdb_id=tmdb_id) # Delete if movie if it exists if movie: content_manager.delete(radarr_id=movie["id"]) # Add or re-add the movie radarr_params = obtain_radarr_parameters(content_discovery, content_manager, tmdb_id) movie = content_manager.add( tmdb_id=tmdb_id, quality_profile_id=radarr_params["radarr_profile_id"], root_dir=radarr_params["radarr_root"], ) # Search for a replacement content_manager.request(radarr_id=movie["id"]) issue = ReportedIssue.objects.get(pk=issue_id) issue.auto_resolve_in_progress = True issue.save()
def set_single_availability(card): """Sets the availabily on a single card.""" content_manager = ArrManager() content_discovery = TmdbDiscovery() try: # Compute the availability of a Sonarr card if card.__contains__("tvdbId"): content = content_manager.get(tvdb_id=card["tvdbId"]) if content is not None: card["availability"] = content["availability"] # Compute the availability of a Radarr card elif card.__contains__("tmdbId"): content = content_manager.get(tmdb_id=card["tmdbId"]) if content is not None: card["availability"] = content["availability"] # Compute the availability of TV show elif card.__contains__("name"): external_id = content_discovery.get_external_ids(card["id"], "tv") content = content_manager.get(tvdb_id=external_id["tvdb_id"]) if content is not None: card["availability"] = content["availability"] # Compute the availability of movie elif card.__contains__("title"): content = content_manager.get(tmdb_id=card["id"]) if content is not None: card["availability"] = content["availability"] # Something unexpected was passed in else: log.handler( "Card did not contain content_type, title, or name!", log.WARNING, _logger, ) return card except: log.handler( "Could not determine the availability of card!\n" + str(card), log.ERROR, _logger, ) return card
def collection(request): collection_id = request.GET.get("collection_id", None) if collection_id: content_discovery = TmdbDiscovery() tmdb_collection = content_discovery.collections(collection_id) if not isinstance(tmdb_collection, dict) or not tmdb_collection: tmdb_collection = None else: set_many_availability(tmdb_collection["parts"]) context = {"collection": tmdb_collection} template = loader.get_template( "viewport/components/more_info_collection.html") return HttpResponse(template.render(context, request))
def request_content(request): # User submitted a new request if request.method == "POST": request_parameters = json.loads(request.body.decode("utf-8")) log.handler( "Request received: " + str(request_parameters), log.INFO, _logger, ) content_manager = ArrManager() content_discovery = TmdbDiscovery() # TV show was requested if request_parameters["content_type"] == "tv": # Try to obtain a TVDB ID (from params or fetch it from TMDB) tmdb_id = request_parameters["tmdb_id"] tvdb_id = content_discovery.get_external_ids(tmdb_id, "tv").get("tvdb_id") # Request the show by the TVDB ID if tvdb_id: sonarr_request( tvdb_id, tmdb_id, request, request_parameters, content_manager, content_discovery, ) else: return HttpResponseForbidden() # Movie was requested elif request_parameters["content_type"] == "movie": tmdb_id = request_parameters["tmdb_id"] radarr_request(tmdb_id, request, content_manager, content_discovery) # The request succeeded return JsonResponse({"success": True}) return HttpResponseForbidden()
def more_info(request): content_discovery = TmdbDiscovery() template = loader.get_template("viewport/more_info.html") # Get the ID from the URL tmdb_id = request.GET.get("tmdb_id", None) content_type = request.GET.get("content_type", None) # Get all the basic metadata for a given ID content = content_discovery.get_by_tmdb_id(tmdb_id, content_type) # Determine the availability of the current TMDB ID set_single_availability(content) # Pre-process data attributes within tmdb_result preprocess_tmdb_result(content) # Get collection information if (content.__contains__("belongs_to_collection") and content["belongs_to_collection"] is not None): tmdb_collection_id = content["belongs_to_collection"]["id"] else: tmdb_collection_id = None # Check if the user has already requested this requested = False if UserRequest.objects.filter( content_id=content["id"], content_type=content["content_type"], ): requested = True # Generate context for page rendering context = { "content": content, "collection_id": tmdb_collection_id, "content_type": content["content_type"], "requested": requested, } # Render the page return HttpResponse(template.render(context, request))
def series_modal(request): content_discovery = TmdbDiscovery() content_manager = ArrManager() report_modal = str_to_bool(request.GET.get("report_modal", "false")) # Get the ID from the URL tmdb_id = request.GET.get("tmdb_id", None) tvdb_id = content_discovery.get_external_ids(tmdb_id, "tv").get("tvdb_id") # Check if the show is already within Sonarr's collection requested_show = content_manager.get(tvdb_id=tvdb_id) # If it doesn't already exists, add then add it if requested_show is None: sonarr_params = obtain_sonarr_parameters(content_discovery, content_manager, tmdb_id, tvdb_id) requested_show = content_manager.add( tvdb_id=tvdb_id, quality_profile_id=sonarr_params["sonarr_profile_id"], root_dir=sonarr_params["sonarr_root"], series_type=sonarr_params["series_type"], season_folders=sonarr_params["season_folders"], ) # Keep refreshing until we get the series from Sonarr series = wait_for_series_info(tvdb_id, content_manager) # Series successfully obtained from Sonarr if series: context = { "seasons": series["seasons"], "tmdb_id": tmdb_id, "report_modal": report_modal, } template = loader.get_template("modal/series_selection.html") return HttpResponse(template.render(context, request)) # Sonarr couldn't process this request return HttpResponseNotFound()
def post(self, request, tmdb_id): """Request a movie by TMDB ID.""" content_manager = ArrManager() content_discovery = TmdbDiscovery() # Request the show by the TMDB ID radarr_request( tmdb_id, request, content_manager, content_discovery, ) return Response(self.msg)
def post(self, request, tmdb_id): """Request a TV show by TMDB ID. Optionally, you can request specific seasons or episodes.""" content_manager = ArrManager() content_discovery = TmdbDiscovery() tvdb_id = content_discovery.get_external_ids(tmdb_id, "tv") request_parameters = json.loads(request.body.decode("utf-8")) # Request the show by the TVDB ID if tvdb_id: sonarr_request( tvdb_id["tvdb_id"], tmdb_id, request, request_parameters, content_manager, content_discovery, ) return Response(self.msg) return Response({ "success": False, "detail": "Could not determine TVDB ID." })
def auto_resolve_watchdog(): """Checks to see if an auto resolution has finished completely.""" # Check if auto resolution is turned on conreq_config = ConreqConfig.get_solo() if conreq_config.conreq_auto_resolve_issues: content_manager = ArrManager() issues = ReportedIssue.objects.filter(auto_resolve_in_progress=True) newly_resolved_issues = [] for issue in issues: # Check if TV issues have been resolved if issue.content_type == "tv": content_discovery = TmdbDiscovery() tvdb_id = content_discovery.get_external_ids( issue.content_id, "tv").get("tvdb_id") show = content_manager.get(tvdb_id=tvdb_id) if show and show.get("availability") == "available": issue.auto_resolve_in_progress = False issue.auto_resolved = True issue.resolved = True newly_resolved_issues.append(issue) # Check if movie issues have been resolved if issue.content_type == "movie": movie = content_manager.get(tmdb_id=issue.content_id) if movie and movie.get("hasFile"): issue.auto_resolve_in_progress = False issue.auto_resolved = True issue.resolved = True newly_resolved_issues.append(issue) # Save the resolution status if newly_resolved_issues: ReportedIssue.objects.bulk_update( newly_resolved_issues, ["auto_resolve_in_progress", "auto_resolved", "resolved"], )
def generate_issue_cards(reported_issues): """Retruns a list of cards""" content_discovery = TmdbDiscovery() all_cards = [] card = None for entry in reported_issues.values( "id", "reported_by__username", "content_id", "resolved", "auto_resolved", "auto_resolve_in_progress", "date_reported", "content_type", "issues", "seasons", "episodes", ): # Fetch TMDB entry card = content_discovery.get_by_tmdb_id( tmdb_id=entry["content_id"], content_type=entry["content_type"], obtain_extras=False, ) if card is not None: all_cards.append({**card, **entry}) if card is None: log.handler( entry["content_type"] + " with ID " + entry["content_id"] + " no longer exists!", log.WARNING, _logger, ) return all_cards
def arr_auto_resolve_tv(issue_id, tmdb_id, seasons, episode_ids, resolutions): """Queues a background task to automatically resolve a reported issue.""" # TODO: Intelligently resolve based on "resolutions" # Check if auto resolution is turned on conreq_config = ConreqConfig.get_solo() if conreq_config.conreq_auto_resolve_issues: content_manager = ArrManager() content_discovery = TmdbDiscovery() tvdb_id = content_discovery.get_external_ids(tmdb_id, "tv").get("tvdb_id") # Grab the show from Sonarr show = content_manager.get(force_update_cache=True, obtain_season_info=True, tvdb_id=tvdb_id) # Show doesn't exist, add it if not show: # Add the show sonarr_params = obtain_sonarr_parameters(content_discovery, content_manager, tmdb_id) show = content_manager.add( tvdb_id=tvdb_id, quality_profile_id=sonarr_params["sonarr_profile_id"], root_dir=sonarr_params["sonarr_root"], series_type=sonarr_params["series_type"], season_folders=sonarr_params["season_folders"], ) # Show already exists, handle whole show if show and not seasons and not episode_ids: # Delete the whole show content_manager.delete(sonarr_id=show.get("id")) # Re-add the show sonarr_params = obtain_sonarr_parameters(content_discovery, content_manager, tmdb_id, tvdb_id) show = content_manager.add( tvdb_id=tvdb_id, quality_profile_id=sonarr_params["sonarr_profile_id"], root_dir=sonarr_params["sonarr_root"], series_type=sonarr_params["series_type"], season_folders=sonarr_params["season_folders"], ) # Show already exists, handle individual seasons/episodes if show and seasons or episode_ids: # Obtain the seasons and episodes for season in show.get("seasons", []): for episode in season.get("episodes"): if ( # User reported an episode, check if the episode has a file episode.get("id") in episode_ids and episode.get("hasFile") ) or ( # User reported a season, check if the season has episode files to be deleted season.get("seasonNumber") in seasons and episode.get("hasFile")): content_manager.delete( episode_file_id=episode.get("episodeFileId")) # Keep refreshing until we get the series from Sonarr show = wait_for_series_info(tvdb_id, content_manager) # Download new copies content_manager.request(sonarr_id=show.get("id"), seasons=seasons, episode_ids=episode_ids) issue = ReportedIssue.objects.get(pk=issue_id) issue.auto_resolve_in_progress = True issue.save()
def person(request): content_discovery = TmdbDiscovery() template = loader.get_template("viewport/person.html") context = {} # Get the ID from the URL person_id = request.GET.get("id", None) # Fetch the person from TMDB if person_id: results = content_discovery.person(person_id) # Preprocessing before passing into HTML preprocess_tmdb_person(results) if results["tv_credits"]["cast"]: content_discovery.determine_id_validity( results["tv_credits"]["cast"]) set_many_availability(results["tv_credits"]["cast"]) if results["tv_credits"]["crew"]: content_discovery.determine_id_validity( results["tv_credits"]["crew"]) set_many_availability(results["tv_credits"]["crew"]) if results["movie_credits"]["cast"]: content_discovery.determine_id_validity( results["movie_credits"]["cast"]) set_many_availability(results["movie_credits"]["cast"]) if results["movie_credits"]["crew"]: content_discovery.determine_id_validity( results["movie_credits"]["crew"]) set_many_availability(results["movie_credits"]["crew"]) tv_cast_contain_valid_id = is_key_value_in_list( "conreq_valid_id", True, results["tv_credits"]["cast"]) tv_crew_contain_valid_id = is_key_value_in_list( "conreq_valid_id", True, results["tv_credits"]["crew"]) if results.get("popularity"): results["popularity"] = int(results["popularity"] * 10) # Generate context for page rendering context = { "person": results, "tv_cast_contain_valid_id": tv_cast_contain_valid_id, "tv_crew_contain_valid_id": tv_crew_contain_valid_id, } # Render the page return HttpResponse(template.render(context, request))