finder = new Finder(); $this->basePath = $basePath; $this->moviesPath = $moviesPath; $this->tvShowsPath = $tvShowsPath; $this->filesystem = $filesystem; } public function getPathByType(string $mediaType): string { if ('movies' === $mediaType) { return $this->moviesPath; } elseif ('tvshows' === $mediaType) { return $this->tvShowsPath; } throw new \Exception(sprintf('A path for media type %s does not exist.', $mediaType)); } public function getBasePath(): string { return $this->basePath; } public function getMoviesPath(): string { return $this->moviesPath; } public function getTvShowsPath(): string { return $this->tvShowsPath; } public function getMovieDirs(): Map { $results = []; foreach ($this->finder->in($this->moviesPath)->directories() as $file) { $results[] = $file; } return Map::from($results); } public function getTvShowDirs(): Map { $results = []; foreach ($this->finder->in($this->tvShowsPath)->directories() as $file) { $results[] = $file; } return Map::from($results); } public function getEpisodes(string $path, bool $onlyFilenames = true): Map { if (!str_starts_with($path, $this->tvShowsPath)) { $path = $this->tvShowsPath . DIRECTORY_SEPARATOR . $path; } if (false === $this->filesystem->exists($path)) { $this->filesystem->mkdir($path); } $results = []; foreach ($this->finder->in($path)->files() as $file) { if ($onlyFilenames) { $results[] = $file->getRelativePathname(); } else { $results[] = $file; } } return Map::from($results); } public function createMovieDirectory(string $path): string { $path = $this->moviesPath . DIRECTORY_SEPARATOR . $path; if (false === $this->filesystem->exists($path)) { $this->filesystem->mkdir($path); } return $path; } public function createTvShowDirectory(string $path): string { $path = $this->tvShowsPath . DIRECTORY_SEPARATOR . $path; if (false === $this->filesystem->exists($path)) { $this->filesystem->mkdir($path); } return $path; } public function createDirectory(string $path): string { if (false === $this->filesystem->exists($path)) { $this->filesystem->mkdir($path); } return $path; } public function episodeExists(string $tvshowTitle, int $seasonNumber, int $episodeNumber) { $existingEpisodes = $this->getEpisodes($tvshowTitle, false); if ($existingEpisodes->isEmpty()) { return false; } /** @var SplFileInfo $episode */ foreach ($existingEpisodes as $episode) { $ptn = (object) (new PTN())->parse($episode->getFilename()); if (!property_exists($ptn, 'season') || !property_exists($ptn, 'episode')) { continue; } if ($ptn->season === $seasonNumber && $ptn->episode === $episodeNumber) { return $episode; } } return false; } public function movieExists(string $title) { $filepath = $this->moviesPath . DIRECTORY_SEPARATOR . $title; $directoryExists = $this->filesystem->exists($filepath); if (false === $directoryExists) { return false; } if (false === $this->finder->in($filepath)->files()->hasResults()) { return false; } $files = Map::from($this->finder->in($filepath)->files())->filter(function (SplFileInfo $file) { $validExtensions = ['mkv', 'mp4', 'mpeg']; return in_array($file->getExtension(), $validExtensions); })->values(); if (false === $files->isEmpty()) { return $files[0]; } return false; } public function getDownloadPath(Download $download): string { $basePath = $this->getBasePath(); if ($download->getMediaType() === 'movies') { $basePath = $this->getMoviesPath(); if ($download->getUser()->hasUserPreference('movie_folder')) { $basePath .= DIRECTORY_SEPARATOR . $download->getTitle(); } } elseif ($download->getMediaType() === 'tvshows') { $basePath = $this->getTvShowsPath() . DIRECTORY_SEPARATOR . $download->getTitle(); } $filepath = $basePath . DIRECTORY_SEPARATOR . $download->getFilename(); if (false === $this->filesystem->exists($filepath)) { throw new \Exception(sprintf('File %s does not exist.', $filepath)); } return $filepath; } public function renameFile(string $oldFile, string $newFile) { $this->filesystem->rename($oldFile, $newFile); } public function setFilePermissions(string $filepath, int $permissions) { $this->filesystem->chmod($filepath, $permissions); } }