from plexapi.server import PlexServer from config.config import Config from models.movie import UpdatedMovie from tmdbv3api import TMDb, Movie from datetime import datetime as dt import yaml, os, urllib.request, logging logging.basicConfig(filename='plexAutoCollectionUpdater.log', level=logging.INFO) logger = logging.getLogger("CollectionUpdater") ch = logging.StreamHandler() formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s') ch.setFormatter(formatter) logger.addHandler(ch) # Instantiate Tmdb object tmdb = TMDb() tmdb.api_key = Config.tmdbApiKey tmdb.language = Config.tmdbLanguage # Connect to Plex Server baseurl = Config.plexBaseUrl token = Config.plexToken plex = PlexServer(baseurl, token) def MovieCollectionList(library): plexMoviesLibrary = plex.library.section(library) plexMoviesLibrary = plexMoviesLibrary.search() MoviesList = [] logger.info(f"Retrieving {len(plexMoviesLibrary)} Movies from Plex {library} library and Updating TMDb information...") for item in plexMoviesLibrary: movie = UpdatedMovie() tmdbMovie = Movie() movie.PlexTitle = item.title for guid in item.guids: if "tmdb://" in guid.id: movie.TMDbId = guid.id[7:] elif "imdb://" in guid.id: movie.ImdbId = guid.id[7:] # Search for the movie on TMDb try: tmdbMovieDetails = tmdbMovie.details(movie_id=movie.TMDbId) logger.debug(f'Getting TMDb details for {movie.PlexTitle}') except: logger.warning(f"CollectionUpdater :: Cannot get details of {movie.PlexTitle} from TMDb") if tmdbMovieDetails['belongs_to_collection']: movie.MovieTMDbCollectionName = tmdbMovieDetails['belongs_to_collection'].name[:len(tmdbMovieDetails['belongs_to_collection'].name) - 7] movie.MovieTMDbCollectionTMDbId = tmdbMovieDetails['belongs_to_collection'].id movie.MovieTMDbCollectionPosterPath = tmdbMovieDetails['belongs_to_collection'].poster_path movie.TMDbTitle = tmdbMovieDetails.title # Add movie to the list of Movies if movie.MovieTMDbCollectionTMDbId: logger.info(f'Movie {movie.PlexTitle} has been added to Collection List') MoviesList.append(movie) logger.info(f"Retrieved Movies from Plex and Updated TMDb information for {len(MoviesList)} movies...") i = 0 count = 0 MovieListFinal = [] ExistingCollectionId = [] while i < len(MoviesList): for movie in MoviesList: if MoviesList[i].MovieTMDbCollectionTMDbId == movie.MovieTMDbCollectionTMDbId: count += 1 if count > 2: if not MoviesList[i].MovieTMDbCollectionTMDbId in ExistingCollectionId: logger.info(f"Keeping collection {MoviesList[i].MovieTMDbCollectionName} which contains 3 or more movies") ExistingCollectionId.append(MoviesList[i].MovieTMDbCollectionTMDbId) MovieListFinal.append(MoviesList[i]) i += 1 count = 0 logger.info(f"Found a total of {len(MovieListFinal)} collections, updating config file now !") return MovieListFinal def UpdateYAML(configFile, MovieListFinal): try: with open(configFile, 'r') as f: try: currentYaml = yaml.safe_load(f) except yaml.YAMLError as exc: print(exc) except: logger.warning(f"Could not find the config file with path: {configFile}") currentYamlCollections = [] for movies in currentYaml['collections']: currentYamlCollections.append(movies) for collection in MovieListFinal: if collection.MovieTMDbCollectionName not in currentYamlCollections: with open(configFile, 'r') as f: new_col1 = {f'{collection.MovieTMDbCollectionName}':{'template':{'name': 'Movie', 'collection': collection.MovieTMDbCollectionTMDbId, 'summary': collection.MovieTMDbCollectionTMDbId}}} currentYaml['collections'].update(new_col1) if currentYaml: logger.info(f"Adding new collection: {collection.MovieTMDbCollectionName} to {configFile} file...") with open(configFile, 'w') as f: yaml.safe_dump(currentYaml, f) if not os.path.exists( Config.PlexAutoCollectionConfigFileImagesPath + f"/{collection.MovieTMDbCollectionName}"): logger.info(f"Download poster for new collection {collection.MovieTMDbCollectionName}...") os.mkdir(Config.PlexAutoCollectionConfigFileImagesPath + f"/{collection.MovieTMDbCollectionName}") urllib.request.urlretrieve(Config.tmdbImgUrl + f"{collection.MovieTMDbCollectionPosterPath}", Config.PlexAutoCollectionConfigFileImagesPath + f"/{collection.MovieTMDbCollectionName}/poster.jpeg") MovieListFinal = MovieCollectionList('Movies') UpdateYAML(Config.PlexAutoCollectionConfigFilePath, MovieListFinal) MovieListFinal = MovieCollectionList('4K Movies') UpdateYAML(Config.PlexAutoCollectionConfigFilePath4K, MovieListFinal) logger.info(f"All collections have been updated in plex...")