diff --git a/lib/class/album.class.php b/lib/class/album.class.php index 5f720c46..f5a4bba3 100644 --- a/lib/class/album.class.php +++ b/lib/class/album.class.php @@ -69,6 +69,10 @@ class Album extends database_object implements library_item */ public $release_type; + /** + * @var int $catalog_id + */ + public $catalog_id; /** * @var int $song_count */ @@ -680,6 +684,17 @@ class Album extends database_object implements library_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array($this->catalog_id); + } + /** * Get item's owner. * @return int|null @@ -735,8 +750,8 @@ class Album extends database_object implements library_item public function update(array $data) { $year = $data['year'] ?: $this->year; - $artist = intval($data['artist']); - $album_artist = intval($data['album_artist']); + $artist = $data['artist'] ? intval($data['artist']) : $this->artist; + $album_artist = $data['album_artist'] ? intval($data['album_artist']) : $this->album_artist; $name = $data['name'] ?: $this->name; $disk = $data['disk'] ?: $this->disk; $mbid = $data['mbid'] ?: $this->mbid; @@ -802,7 +817,9 @@ class Album extends database_object implements library_item if ($data['apply_childs'] == 'checked') { $override_songs = true; } - $this->update_tags($data['edit_tags'], $override_songs, $current_id); + if (isset($data['edit_tags'])) { + $this->update_tags($data['edit_tags'], $override_songs, $current_id); + } return $current_id; diff --git a/lib/class/art.class.php b/lib/class/art.class.php index 74505746..7bac5eab 100644 --- a/lib/class/art.class.php +++ b/lib/class/art.class.php @@ -315,7 +315,7 @@ class Art extends database_object * @param string $mime * @return boolean */ - public function insert($source, $mime) + public function insert($source, $mime = '') { // Disabled in demo mode cause people suck and upload porn if (AmpConfig::get('demo_mode')) { return false; } diff --git a/lib/class/artist.class.php b/lib/class/artist.class.php index 2621debc..2e84a56f 100644 --- a/lib/class/artist.class.php +++ b/lib/class/artist.class.php @@ -369,7 +369,7 @@ class Artist extends database_object implements library_item $row = parent::get_from_cache('artist_extra',$this->id); } else { $uid = Dba::escape($this->id); - $sql = "SELECT `song`.`artist`,COUNT(DISTINCT `song`.`id`) AS `song_count`, COUNT(DISTINCT `song`.`album`) AS `album_count`, SUM(`song`.`time`) AS `time` FROM `song` LEFT JOIN `catalog` ON `catalog`.`id` = `song`.`catalog` " . + $sql = "SELECT `song`.`artist`,COUNT(DISTINCT `song`.`id`) AS `song_count`, COUNT(DISTINCT `song`.`album`) AS `album_count`, SUM(`song`.`time`) AS `time`, `song`.`catalog` as `catalog_id` FROM `song` LEFT JOIN `catalog` ON `catalog`.`id` = `song`.`catalog` " . "WHERE (`song`.`artist`='$uid' || `song`.`album_artist`='$uid') "; if ($catalog) { $sql .= "AND (`song`.`catalog` = '$catalog') "; @@ -392,6 +392,7 @@ class Artist extends database_object implements library_item $this->songs = $row['song_count']; $this->albums = $row['album_count']; $this->time = $row['time']; + $this->catalog_id = $row['catalog_id']; return $row; @@ -514,6 +515,17 @@ class Artist extends database_object implements library_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array($this->catalog_id); + } + /** * Get item's owner. * @return int|null @@ -633,7 +645,7 @@ class Artist extends database_object implements library_item // Save our current ID $name = $data['name'] ?: $this->name; $mbid = $data['mbid'] ?: $this->mbid; - + $current_id = $this->id; // Check if name is different than current name @@ -674,7 +686,7 @@ class Artist extends database_object implements library_item $sql = 'UPDATE `artist` SET `name` = ? WHERE `id` = ?'; Dba::write($sql, array($name, $current_id)); } - + $this->name = $name; $this->mbid = $mbid; @@ -682,7 +694,9 @@ class Artist extends database_object implements library_item if ($data['apply_childs'] == 'checked') { $override_childs = true; } - $this->update_tags($data['edit_tags'], $override_childs, $current_id); + if (isset($data['edit_tags'])) { + $this->update_tags($data['edit_tags'], $override_childs, $current_id); + } return $current_id; diff --git a/lib/class/broadcast.class.php b/lib/class/broadcast.class.php index c2180e9f..d6e1fac7 100644 --- a/lib/class/broadcast.class.php +++ b/lib/class/broadcast.class.php @@ -234,6 +234,17 @@ class Broadcast extends database_object implements library_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array(); + } + /** * Get item's owner. * @return int|null diff --git a/lib/class/channel.class.php b/lib/class/channel.class.php index ca97c0df..7d3186f5 100644 --- a/lib/class/channel.class.php +++ b/lib/class/channel.class.php @@ -430,6 +430,17 @@ class Channel extends database_object implements media, library_item return $chunk; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array(); + } + public static function play_url($oid, $additional_params='', $local=false) { $channel = new Channel($oid); diff --git a/lib/class/live_stream.class.php b/lib/class/live_stream.class.php index a43e78e2..3336f450 100644 --- a/lib/class/live_stream.class.php +++ b/lib/class/live_stream.class.php @@ -108,6 +108,17 @@ class Live_Stream extends database_object implements media, library_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array($this->catalog); + } + public function get_user_owner() { return null; diff --git a/lib/class/movie.class.php b/lib/class/movie.class.php index a5162e81..09008d85 100644 --- a/lib/class/movie.class.php +++ b/lib/class/movie.class.php @@ -86,12 +86,24 @@ class Movie extends Video { parent::update($data); - $trimmed = Catalog::trim_prefix(trim($data['original_name'])); - $name = $trimmed['string']; - $prefix = $trimmed['prefix']; + if (isset($data['original_name'])) { + $trimmed = Catalog::trim_prefix(trim($data['original_name'])); + $name = $trimmed['string']; + $prefix = $trimmed['prefix']; + } else { + $name = $this->original_name; + $prefix = $this->prefix; + } + $summary = $data['summary'] ?: $this->summary; + $year = $data['year'] ?: $this->year; $sql = "UPDATE `movie` SET `original_name` = ?, `prefix` = ?, `summary` = ?, `year` = ? WHERE `id` = ?"; - Dba::write($sql, array($name, $prefix, $data['summary'], $data['year'], $this->id)); + Dba::write($sql, array($name, $prefix, $summary, $year, $this->id)); + + $this->original_name = $name; + $this->prefix = $prefix; + $this->summary = $summary; + $this->year = $year; return $this->id; diff --git a/lib/class/playable_item.interface.php b/lib/class/playable_item.interface.php index d122583b..e3758869 100644 --- a/lib/class/playable_item.interface.php +++ b/lib/class/playable_item.interface.php @@ -63,4 +63,12 @@ interface playable_item */ public function get_medias($filter_type = null); + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs(); + } // end interface diff --git a/lib/class/playlist.class.php b/lib/class/playlist.class.php index ccab99a4..ca9c5920 100644 --- a/lib/class/playlist.class.php +++ b/lib/class/playlist.class.php @@ -274,10 +274,10 @@ class Playlist extends playlist_object */ public function update(array $data) { - if ($data['name'] != $this->name) { + if (isset($data['name']) && $data['name'] != $this->name) { $this->update_name($data['name']); } - if ($data['pl_type'] != $this->type) { + if (isset($data['pl_type']) && $data['pl_type'] != $this->type) { $this->update_type($data['pl_type']); } @@ -354,6 +354,19 @@ class Playlist extends playlist_object * This takes an array of song_ids and then adds it to the playlist */ public function add_songs($song_ids=array(),$ordered=false) + { + $medias = array(); + foreach ($song_ids as $song_id) { + $medias[] = array( + 'object_type' => 'song', + 'object_id' => $song_id, + ); + } + $this->add_medias($medias); + + } // add_songs + + public function add_medias($medias) { /* We need to pull the current 'end' track and then use that to * append, rather then integrate take end track # and add it to @@ -363,31 +376,29 @@ class Playlist extends playlist_object $db_results = Dba::read($sql, array($this->id)); $data = Dba::fetch_assoc($db_results); $base_track = $data['track']; - debug_event('add_songs', 'Track number: '.$base_track, '5'); + debug_event('add_medias', 'Track number: '.$base_track, '5'); $i = 0; - foreach ($song_ids as $song_id) { - /* We need the songs track */ - $song = new Song($song_id); + foreach ($medias as $data) { + $media = new $data['object_type']($data['object_id']); // Based on the ordered prop we use track + base or just $i++ - if (!$ordered) { - $track = $song->track + $base_track; + if (!$ordered && $data['object_type'] == 'song') { + $track = $media->track + $base_track; } else { $i++; $track = $base_track + $i; } - /* Don't insert dead songs */ - if ($song->id) { + /* Don't insert dead media */ + if ($media->id) { $sql = "INSERT INTO `playlist_data` (`playlist`,`object_id`,`object_type`,`track`) " . - " VALUES (?, ?, 'song', ?)"; - Dba::write($sql, array($this->id, $song->id, $track)); + " VALUES (?, ?, ?, ?)"; + Dba::write($sql, array($this->id, $data['object_id'], $data['object_type'], $track)); } // if valid id - } // end foreach songs - - } // add_songs + } // end foreach medias + } /** * create diff --git a/lib/class/playlist_object.abstract.php b/lib/class/playlist_object.abstract.php index 6b9f7f1e..1f9912c2 100644 --- a/lib/class/playlist_object.abstract.php +++ b/lib/class/playlist_object.abstract.php @@ -126,5 +126,15 @@ abstract class playlist_object extends database_object implements library_item return 'default'; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array(); + } } // end playlist_object diff --git a/lib/class/plex_api.class.php b/lib/class/plex_api.class.php index 9e7dd9f1..bcabd48d 100644 --- a/lib/class/plex_api.class.php +++ b/lib/class/plex_api.class.php @@ -203,7 +203,7 @@ class Plex_Api $GLOBALS['user']->access = 50; } } - + if (($GLOBALS['user']->access < $level || AmpConfig::get('demo_mode'))) { debug_event('plex', 'User ' . $GLOBALS['user']->username . ' is unauthorized to complete the action.', '3'); self::createError(401); @@ -774,33 +774,62 @@ class Plex_Api $view = $params[1]; $gtypes = $catalog->get_gather_types(); if ($gtypes[0] == 'music') { + $type = 'artist'; + if ($_GET['type']) { + $type = Plex_XML_Data::getAmpacheType($_GET['type']); + } + if ($view == "all") { - Plex_XML_Data::setSectionAll_Artists($r, $catalog); + switch ($type) { + case 'artist': + Plex_XML_Data::setSectionAll_Artists($r, $catalog); + break; + case 'album': + Plex_XML_Data::setSectionAll_Albums($r, $catalog); + break; + } } elseif ($view == "albums") { Plex_XML_Data::setSectionAlbums($r, $catalog); } elseif ($view == "recentlyadded") { Plex_XML_Data::setCustomSectionView($r, $catalog, Stats::get_recent('album', 25, $key)); } elseif ($view == "genre") { - $type = Plex_XML_Data::getAmpacheType($_GET['type']); - Plex_XML_Data::setSectionTags($r, $catalog, $type); + Plex_XML_Data::setSectionTags($r, $catalog, 'song'); } } elseif ($gtypes[0] == "tvshow") { + $type = 'tvshow'; + if ($_GET['type']) { + $type = Plex_XML_Data::getAmpacheType($_GET['type']); + } + if ($view == "all") { - Plex_XML_Data::setSectionAll_TVShows($r, $catalog); + switch ($type) { + case 'tvshow': + Plex_XML_Data::setSectionAll_TVShows($r, $catalog); + break; + case 'season': + Plex_XML_Data::setSectionAll_Seasons($r, $catalog); + break; + case 'episode': + Plex_XML_Data::setSectionAll_Episodes($r, $catalog); + break; + } } elseif ($view == "recentlyadded") { Plex_XML_Data::setCustomSectionView($r, $catalog, Stats::get_recent('tvshow_episode', 25, $key)); } elseif ($view == "genre") { - $type = Plex_XML_Data::getAmpacheType($_GET['type']); - Plex_XML_Data::setSectionTags($r, $catalog, $type); + Plex_XML_Data::setSectionTags($r, $catalog, 'video'); } } elseif ($gtypes[0] == "movie") { + $type = 'tvshow'; + if ($_GET['type']) { + $type = Plex_XML_Data::getAmpacheType($_GET['type']); + } + if ($view == "all") { Plex_XML_Data::setSectionAll_Movies($r, $catalog); } elseif ($view == "recentlyadded") { Plex_XML_Data::setCustomSectionView($r, $catalog, Stats::get_recent('movie', 25, $key)); } elseif ($view == "genre") { - $type = Plex_XML_Data::getAmpacheType($_GET['type']); - Plex_XML_Data::setSectionTags($r, $catalog, $type); + Plex_XML_Data::setSectionTags($r, $catalog, 'video'); } } } @@ -814,121 +843,163 @@ class Plex_Api { $r = Plex_XML_Data::createLibContainer(); $n = count($params); + $litem = null; + + $createMode = ($_SERVER['REQUEST_METHOD'] == 'POST'); + $editMode = ($_SERVER['REQUEST_METHOD'] == 'PUT'); + if ($n > 0) { $key = $params[0]; $id = Plex_XML_Data::getAmpacheId($key); - $editMode = ($_SERVER['REQUEST_METHOD'] == 'PUT'); if ($editMode) { self::check_access(50); } - + if ($n == 1) { // Should we check that files still exists here? $checkFiles = $_REQUEST['checkFiles']; + $extra = $_REQUEST['includeExtra']; if (Plex_XML_Data::isArtist($key)) { - $artist = new Artist($id); - $artist->format(); + $litem = new Artist($id); + $litem->format(); if ($editMode) { $dmap = array( 'title' => 'name', 'summary' => null, ); - $artist->update(self::get_data_from_map($dmap)); + $litem->update(self::get_data_from_map($dmap)); } - Plex_XML_Data::addArtist($r, $artist); + Plex_XML_Data::addArtist($r, $litem); } elseif (Plex_XML_Data::isAlbum($key)) { - $album = new Album($id); - $album->format(); + $litem = new Album($id); + $litem->format(); if ($editMode) { $dmap = array( 'title' => 'name', 'year' => null, ); - $album->update(self::get_data_from_map($dmap)); + $litem->update(self::get_data_from_map($dmap)); } - Plex_XML_Data::addAlbum($r, $album); + Plex_XML_Data::addAlbum($r, $litem); } elseif (Plex_XML_Data::isTrack($key)) { - $song = new Song($id); - $song->format(); + $litem = new Song($id); + $litem->format(); if ($editMode) { $dmap = array( 'title' => null, ); - $song->update(self::get_data_from_map($dmap)); + $litem->update(self::get_data_from_map($dmap)); } - Plex_XML_Data::addSong($r, $song); + Plex_XML_Data::addSong($r, $litem); } elseif (Plex_XML_Data::isTVShow($key)) { - $tvshow = new TVShow($id); - $tvshow->format(); - Plex_XML_Data::addTVShow($r, $tvshow); + $litem = new TVShow($id); + $litem->format(); + if ($editMode) { + $dmap = array( + 'title' => 'name', + 'year' => null, + 'summary' => null, + ); + $litem->update(self::get_data_from_map($dmap)); + } + Plex_XML_Data::addTVShow($r, $litem); } elseif (Plex_XML_Data::isTVShowSeason($key)) { - $season = new TVShow_Season($id); - $season->format(); - Plex_XML_Data::addTVShowSeason($r, $season); + $litem = new TVShow_Season($id); + $litem->format(); + Plex_XML_Data::addTVShowSeason($r, $litem); } elseif (Plex_XML_Data::isVideo($key)) { - $video = Video::create_from_id($id); - $video->format(); + $litem = Video::create_from_id($id); - $subtype = strtolower(get_class($video)); + if ($editMode) { + $dmap = array( + 'title' => null, + 'year' => null, + 'originallyAvailableAt' => 'release_date', + 'originalTitle' => 'original_name', + 'summary' => null, + ); + $litem->update(self::get_data_from_map($dmap)); + } + $litem->format(); + + $subtype = strtolower(get_class($litem)); if ($subtype == 'tvshow_episode') { - Plex_XML_Data::addEpisode($r, $video, true); + Plex_XML_Data::addEpisode($r, $litem, true); } elseif ($subtype == 'movie') { - Plex_XML_Data::addMovie($r, $video, true); + Plex_XML_Data::addMovie($r, $litem, true); } } elseif (Plex_XML_Data::isPlaylist($key)) { - $playlist = new Playlist($id); - $playlist->format(); + $litem = new Playlist($id); + $litem->format(); if ($editMode) { $dmap = array( 'title' => 'name', ); - $playlist->update(self::get_data_from_map($dmap)); + $litem->update(self::get_data_from_map($dmap)); } - Plex_XML_Data::addPlaylist($r, $playlist); + Plex_XML_Data::addPlaylist($r, $litem); } + } else { $subact = $params[1]; if ($subact == "children") { if (Plex_XML_Data::isArtist($key)) { - $artist = new Artist($id); - $artist->format(); - Plex_XML_Data::setArtistRoot($r, $artist); + $litem = new Artist($id); + $litem->format(); + Plex_XML_Data::setArtistRoot($r, $litem); } else if (Plex_XML_Data::isAlbum($key)) { - $album = new Album($id); - $album->format(); - Plex_XML_Data::setAlbumRoot($r, $album); + $litem = new Album($id); + $litem->format(); + Plex_XML_Data::setAlbumRoot($r, $litem); } else if (Plex_XML_Data::isTVShow($key)) { - $tvshow = new TVShow($id); - $tvshow->format(); - Plex_XML_Data::setTVShowRoot($r, $tvshow); + $litem = new TVShow($id); + $litem->format(); + Plex_XML_Data::setTVShowRoot($r, $litem); } else if (Plex_XML_Data::isTVShowSeason($key)) { - $season = new TVShow_Season($id); - $season->format(); - Plex_XML_Data::setTVShowSeasonRoot($r, $season); + $litem = new TVShow_Season($id); + $litem->format(); + Plex_XML_Data::setTVShowSeasonRoot($r, $litem); } - } elseif ($subaction == "posters") { - if ($editMode) { - // Upload art here + } elseif ($subact == "thumbs" || $subact == "posters" || $subact == "arts" || $subact == 'backgrounds') { + $kind = Plex_XML_Data::getPhotoKind($subact); + if ($createMode) { + // Upload art + $litem = Plex_XML_Data::createLibraryItem($key); + $uri = Plex_XML_Data::getMetadataUri($key) . '/' . Plex_XML_Data::getPhotoPlexKind($kind) . '/' . $key; + if (is_a($litem, 'video')) { + $type = 'video'; + } else { + $type = get_class($litem); + } + debug_event('aaaaaaaa', $type, 5); + $art = new Art($litem->id, $type, $kind); + $raw = file_get_contents("php://input"); + $art->insert($raw); + + header('Content-Type: text/html'); + echo $uri; + exit; } - // Get arts list here - } elseif ($subact == "thumb" || $subact == "art" || $subact == "background") { + Plex_XML_Data::addPhotos($r, $key, $kind); + } elseif ($subact == "thumb" || $subact == "poster" || $subact == "art" || $subact == "background") { if ($n == 3) { - // Ignore art id and type as we can only have 1 thumb + $kind = Plex_XML_Data::getPhotoKind($subact); + // Ignore art id as we can only have 1 thumb $art = null; if (Plex_XML_Data::isArtist($key)) { - $art = new Art($id, "artist"); + $art = new Art($id, "artist", $kind); } else if (Plex_XML_Data::isAlbum($key)) { - $art = new Art($id, "album"); + $art = new Art($id, "album", $kind); } else if (Plex_XML_Data::isTrack($key)) { - $art = new Art($id, "song"); + $art = new Art($id, "song", $kind); } else if (Plex_XML_Data::isTVShow($key)) { - $art = new Art($id, "tvshow"); + $art = new Art($id, "tvshow", $kind); } else if (Plex_XML_Data::isTVShowSeason($key)) { - $art = new Art($id, "tvshow_season"); + $art = new Art($id, "tvshow_season", $kind); } else if (Plex_XML_Data::isVideo($key)) { - $art = new Art($id, "video"); + $art = new Art($id, "video", $kind); } if ($art != null) { @@ -952,6 +1023,15 @@ class Plex_Api } } } + + if ($litem != null) { + $catalog_ids = $litem->get_catalogs(); + if (count($catalog_ids) > 0) { + $catalog = Catalog::create_from_id($catalog_ids[0]); + Plex_XML_Data::addCatalogIdentity($r, $catalog); + } + } + Plex_XML_Data::setContainerSize($r); self::apiOutputXml($r->asXML()); } @@ -1128,12 +1208,11 @@ class Plex_Api public static function system_scanners($params) { if (count($params) > 0) { - if ($params[0] == '8' || $params[0] == '9') { - $r = Plex_XML_Data::createSysContainer(); - Plex_XML_Data::setMusicScanners($r); - Plex_XML_Data::setContainerSize($r); - self::apiOutputXml($r->asXML()); - } + $type = $params[0]; + $r = Plex_XML_Data::createSysContainer(); + Plex_XML_Data::setScanners($r, $type); + Plex_XML_Data::setContainerSize($r); + self::apiOutputXml($r->asXML()); } else { self::createError(404); } @@ -1305,29 +1384,58 @@ class Plex_Api public static function playlists($params) { + $r = Plex_XML_Data::createContainer(); $n = count($params); - + + $createMode = ($_SERVER['REQUEST_METHOD'] == 'POST'); $editMode = ($_SERVER['REQUEST_METHOD'] == 'PUT'); $delMode = ($_SERVER['REQUEST_METHOD'] == 'DELETE'); - if ($editMode || $delMode) { + if ($createMode || $editMode || $delMode) { self::check_access(50); } - if ($n == 0 || ($n == 1 && $params[0] == "all")) { - $r = Plex_XML_Data::createContainer(); - Plex_XML_Data::setPlaylists($r); - Plex_XML_Data::setContainerSize($r); - self::apiOutputXml($r->asXML()); - } elseif ($n == 1) { - $plid = $params[0]; - if (Plex_XML_Data::isPlaylist($plid)) { - $playlist = new Playlist(Plex_XML_Data::getAmpacheId($plid)); - if ($playlist->id) { - $r = Plex_XML_Data::createContainer(); - Plex_XML_Data::addPlaylist($r, $playlist); - Plex_XML_Data::setContainerSize($r); - self::apiOutputXml($r->asXML()); + if ($n <= 1) { + $plid = 0; + if ($n == 0 && $createMode) { + // Create a new playlist + //$type = $_GET['type']; + $title = $_GET['title']; + //$smart = $_GET['smart']; + //$summary = $_GET['summary']; + $uri = $_GET['uri']; + + $plid = Playlist::create($title, 'public'); + $playlist = new Playlist($plid); + $key = Plex_XML_Data::getKeyFromFullUri($uri); + $id = Plex_XML_Data::getKeyFromMetadataUri($key); + if ($id) { + $item = Plex_XML_Data::createLibraryItem($id); + $medias = $item->get_medias(); + $playlist->add_medias($medias); } + $plid = Plex_XML_Data::getPlaylistId($plid); + } else { + if ($n == 1 && $params[0] != "all") { + $plid = $params[0]; + } + } + + if ($plid) { + if (Plex_XML_Data::isPlaylist($plid)) { + $playlist = new Playlist(Plex_XML_Data::getAmpacheId($plid)); + if ($playlist->id) { + if ($delMode) { + // Delete playlist + $playlist->delete(); + } else { + // Display playlist information + Plex_XML_Data::addPlaylist($r, $playlist); + } + } + } + } else { + // List all playlists + Plex_XML_Data::setPlaylists($r); } } elseif ($n >= 2) { $plid = $params[0]; @@ -1335,20 +1443,34 @@ class Plex_Api $playlist = new Playlist(Plex_XML_Data::getAmpacheId($plid)); if ($playlist->id) { if ($n == 2) { - $r = Plex_XML_Data::createContainer(); - Plex_XML_Data::setPlaylistItems($r, $playlist); - Plex_XML_Data::setContainerSize($r); - self::apiOutputXml($r->asXML()); + if ($editMode) { + // Add a new item to playlist + $uri = $_GET['uri']; + $key = Plex_XML_Data::getKeyFromFullUri($uri); + $id = Plex_XML_Data::getKeyFromMetadataUri($key); + if ($id) { + $item = Plex_XML_Data::createLibraryItem($id); + $medias = $item->get_medias(); + $playlist->add_medias($medias); + Plex_XML_Data::addPlaylist($r, $playlist); + } + } else { + Plex_XML_Data::setPlaylistItems($r, $playlist); + } } elseif ($n == 3) { $index = intval($params[2]); if ($delMode) { $playlist->delete_track_number($index); $playlist->regenerate_track_numbers(); + exit; } } } } } + + Plex_XML_Data::setContainerSize($r); + self::apiOutputXml($r->asXML()); } public static function playqueues($params) @@ -1372,21 +1494,25 @@ class Plex_Api Plex_XML_Data::setContainerSize($r); self::apiOutputXml($r->asXML()); } - + private static function get_data_from_map($dmap) { $data = array(); - + foreach ($dmap as $key=>$value) { if (isset($_GET[$key])) { if ($value == null) { $value = $key; } - + $data[$value] = $_GET[$key]; } } - + + if (isset($_GET['genre'])) { + $data['edit_tags'] = implode(',', $_GET['genre']); + } + return $data; } } diff --git a/lib/class/plex_xml_data.class.php b/lib/class/plex_xml_data.class.php index 64dd0c28..258810db 100644 --- a/lib/class/plex_xml_data.class.php +++ b/lib/class/plex_xml_data.class.php @@ -44,6 +44,8 @@ class Plex_XML_Data const PLEX_ARTIST = 8; const PLEX_ALBUM = 9; const PLEX_TVSHOW = 2; + const PLEX_SEASON = 3; + const PLEX_EPISODE = 4; const PLEX_MOVIE = 1; const PLEX_PLAYLIST = 15; @@ -173,6 +175,37 @@ class Plex_XML_Data return ($id >= Plex_XML_Data::AMPACHEID_PART); } + public static function createLibraryItem($id) + { + $item = null; + $oid = self::getAmpacheId($id); + if (self::isArtist($id)) { + $item = new Artist($oid); + } elseif (self::isAlbum($id)) { + $item = new Album($oid); + } elseif (self::isSong($id) || self::isTrack($id)) { + $item = new Song($oid); + } elseif (self::isTVShow($id)) { + $item = new TVShow($oid); + } elseif (self::isTVShowSeason($id)) { + $item = new TVShow_Season($oid); + } elseif (self::isVideo($id)) { + $item = Video::create_from_id($oid); + } elseif (self::isPlaylist($id)) { + $item = new Playlist($oid); + } + + if ($item != null) { + if ($item->id) { + $item->format(); + } else { + $item = null; + } + } + + return $item; + } + public static function getPlexVersion() { return "0.9.9.13.525-197d5ed"; @@ -296,6 +329,22 @@ class Plex_XML_Data return substr($uri, strlen($up)); } + public static function getKeyFromFullUri($uri) + { + $key = ''; + $puri = parse_url($uri); + if ($puri['scheme'] == 'library') { + // We ignore library uuid (= $puri['host']) + $ppath = explode('/', $puri['path']); + if (count($ppath) == 3) { + if ($ppath['1'] == 'item') { + $key = rawurldecode($ppath[2]); + } + } + } + return $key; + } + public static function getSectionUri($key) { return '/library/sections/' . $key; @@ -480,18 +529,18 @@ class Plex_XML_Data case 'movie': $dir->addAttribute('type', 'movie'); $dir->addAttribute('agent', 'com.plexapp.agents.imdb'); - $dir->addAttribute('scanner', 'Plex Movie Scanner'); + $dir->addAttribute('scanner', 'Ampache Movie Scanner'); break; case 'tvshow': $dir->addAttribute('type', 'show'); $dir->addAttribute('agent', 'com.plexapp.agents.thetvdb'); - $dir->addAttribute('scanner', 'Plex Series Scanner'); + $dir->addAttribute('scanner', 'Ampache Series Scanner'); break; case 'music': default: $dir->addAttribute('type', 'artist'); $dir->addAttribute('agent', 'com.plexapp.agents.none'); // com.plexapp.agents.lastfm - $dir->addAttribute('scanner', 'Plex Music Scanner'); + $dir->addAttribute('scanner', 'Ampache Music Scanner'); break; } $dir->addAttribute('language', 'en'); @@ -601,8 +650,7 @@ class Plex_XML_Data $xml->addAttribute('nocache', '1'); $xml->addAttribute('viewGroup', $viewGroup); $xml->addAttribute('viewMode', '65592'); - $xml->addAttribute('librarySectionID', $catalog->id); - $xml->addAttribute('librarySectionUUID', self::uuidFromSubKey($catalog->id)); + self::addCatalogIdentity($xml, $catalog); } public static function setSectionAll_Artists(SimpleXMLElement $xml, Catalog $catalog) @@ -615,6 +663,18 @@ class Plex_XML_Data } } + public static function setSectionAll_Albums(SimpleXMLElement $xml, Catalog $catalog) + { + self::setSectionAllAttributes($xml, $catalog, 'All Albums', 'album'); + + $albums_ids = Catalog::get_albums(0, 0, array($catalog->id)); + foreach ($albums_ids as $album_id) { + $album = new Album($album_id); + $album->format(); + self::addAlbum($xml, $album); + } + } + public static function setSectionAll_TVShows(SimpleXMLElement $xml, Catalog $catalog) { self::setSectionAllAttributes($xml, $catalog, 'All Shows', 'show'); @@ -626,6 +686,36 @@ class Plex_XML_Data } } + public static function setSectionAll_Seasons(SimpleXMLElement $xml, Catalog $catalog) + { + self::setSectionAllAttributes($xml, $catalog, 'All Seasons', 'season'); + + $shows = Catalog::get_tvshows(array($catalog->id)); + foreach ($shows as $show) { + $seasons = $show->get_seasons(); + foreach ($seasons as $season_id) { + $season = new TVShow_Season($season_id); + $season->format(); + self::addTVShowSeason($xml, $season); + } + } + } + + public static function setSectionAll_Episodes(SimpleXMLElement $xml, Catalog $catalog) + { + self::setSectionAllAttributes($xml, $catalog, 'All Episodes', 'episode'); + + $shows = Catalog::get_tvshows(array($catalog->id)); + foreach ($shows as $show) { + $episodes = $show->get_episodes(); + foreach ($episodes as $episode_id) { + $episode = new TVShow_Episode($episode_id); + $episode->format(); + self::addEpisode($xml, $episode); + } + } + } + public static function setSectionAll_Movies(SimpleXMLElement $xml, Catalog $catalog) { self::setSectionAllAttributes($xml, $catalog, 'All Movies', 'movie'); @@ -665,8 +755,7 @@ class Plex_XML_Data $xml->addAttribute('mixedParents', '1'); $xml->addAttribute('viewGroup', 'album'); $xml->addAttribute('viewMode', '65592'); - $xml->addAttribute('librarySectionID', $catalog->id); - $xml->addAttribute('librarySectionUUID', self::uuidFromSubKey($catalog->id)); + self::addCatalogIdentity($xml, $catalog); self::setSectionXContent($xml, $catalog); $data = array(); @@ -799,10 +888,9 @@ class Plex_XML_Data $tags = Tag::get_top_tags('album', $album->id); if (is_array($tags)) { - foreach ($tags as $tag_id=>$value) { - $tag = new Tag($tag_id); + foreach ($tags as $tag_id=>$tag) { $xgenre = $xdir->addChild('Genre'); - $xgenre->addAttribute('tag', $tag->name); + $xgenre->addAttribute('tag', $tag['name']); } } } @@ -811,8 +899,6 @@ class Plex_XML_Data { $id = self::getAlbumId($album->id); $xml->addAttribute('allowSync', '1'); - $xml->addAttribute('librarySectionID', $album->catalog_id); - $xml->addAttribute('librarySectionUUID', self::uuidFromkey($album->catalog_id)); $xml->addAttribute('type', 'album'); $xml->addAttribute('summary', ''); $xml->addAttribute('index', '1'); @@ -845,7 +931,9 @@ class Plex_XML_Data if ($rating_value > 0) { $xdir->addAttribute('rating', intval($rating_value * 2)); } - $xdir->addAttribute('year', $tvshow->year); + if ($tvshow->year) { + $xdir->addAttribute('year', $tvshow->year); + } //$xdir->addAttribute('duration', ''); //$xdir->addAttribute('originallyAvailableAt', ''); $xdir->addAttribute('leafCount', $tvshow->episodes); @@ -1024,12 +1112,22 @@ class Plex_XML_Data self::addSongMeta($xdir, $song); $time = $song->time * 1000; $xdir->addAttribute('title', $song->title); + $id = self::getAlbumId($song->id); $albumid = self::getAlbumId($song->album); + $artistid = self::getAlbumId($song->artist); $album = new Album($song->album); + $xdir->addAttribute('grandparentRatingKey', $artistid); $xdir->addAttribute('parentRatingKey', $albumid); + $xdir->addAttribute('grandparentKey', self::getMetadataUri($albumid)); $xdir->addAttribute('parentKey', self::getMetadataUri($albumid)); - $xdir->addAttribute('originalTitle', $album->f_name); + $xdir->addAttribute('grandparentTitle', $song->f_artist); + $xdir->addAttribute('parentTitle', $song->f_album); + $xdir->addAttribute('originalTitle', $song->f_artist); $xdir->addAttribute('summary', ''); + $xdir->addAttribute('art', self::getMetadataUri($id) . '/art/' . $id); + $xdir->addAttribute('grandparentThumb', self::getMetadataUri($artistid) . '/thumb/' . $artistid); + $xdir->addAttribute('parentThumb', self::getMetadataUri($albumid) . '/thumb/' . $albumid); + $xdir->addAttribute('thumb', self::getMetadataUri($albumid) . '/thumb/' . $albumid); // No song art, set album art $xdir->addAttribute('index', $song->track); $xdir->addAttribute('duration', $time); $xdir->addAttribute('type', 'track'); @@ -1078,10 +1176,13 @@ class Plex_XML_Data $xvid = self::addVideo($xml, $movie, $details); $xvid->addAttribute('type', 'movie'); $xvid->addAttribute('summary', $movie->summary); - if (isset($xml['year'])) { - $xml['year'] = $movie->year; - } else { - $xvid->addAttribute('year', $movie->year); + $xvid->addAttribute('originalTitle', $movie->original_name); + if ($movie->year) { + if (isset($xml['year'])) { + $xml['year'] = $movie->year; + } else { + $xvid->addAttribute('year', $movie->year); + } } return $xvid; } @@ -1119,7 +1220,10 @@ class Plex_XML_Data $xvid->addAttribute('key', self::getMetadataUri($id)); $xvid->addAttribute('title', $video->f_title); if ($video->release_date) { - $xvid->addAttribute('year', date('Y', $video->release_date)); + $year = date('Y', $video->release_date); + if ($year) { + $xvid->addAttribute('year', $year); + } $xvid->addAttribute('originallyAvailableAt', $video->f_release_date); } $rating = new Rating($video->id, "video"); @@ -1164,6 +1268,15 @@ class Plex_XML_Data */ + $tags = Tag::get_top_tags('video', $video->id); + if (is_array($tags)) { + foreach ($tags as $tag_id=>$tag) { + $xgenre = $xvid->addChild('Genre'); + $xgenre->addAttribute('id', $tag['id']); + $xgenre->addAttribute('tag', $tag['name']); + } + } + if ($details) { // Subtitles $subtitles = $video->get_subtitles(); @@ -1225,18 +1338,23 @@ class Plex_XML_Data self::addPlaylistsItems($xml, $items); } - private static function addPlaylistsItems(SimpleXMLElement $xml, $items, $attr = array()) + private static function addPlaylistsItems(SimpleXMLElement $xml, $items, $itemIDName = 'playlistItemID') { foreach ($items as $item) { + $xitem = null; if ($item['object_type'] == 'song') { - $song = new Song($item['object_id']); - $song->format(); - $xitem = self::addSong($xml, $song); - if (isset($item['track'])) { - $xitem->addAttribute('playlistItemID', $item['track']); - } - foreach ($attr as $key => $value) { - $xitem->addAttribute($key, $value); + $media = new Song($item['object_id']); + $media->format(); + $xitem = self::addSong($xml, $media); + } elseif ($item['object_type'] == 'video') { + $media = Video::create_from_id($item['object_id']); + $media->format(); + $xitem = self::addVideoExt($xml, $media); + } + + if ($xitem != null) { + if (isset($item['track_id'])) { + $xitem->addAttribute($itemIDName, $item['track_id']); } } } @@ -1244,108 +1362,23 @@ class Plex_XML_Data public static function setPlayQueue(SimpleXMLElement $xml, $type, $playlistID, $uri, $key, $shuffle) { - // We don't really support the queue and only have one item, always - $xml->addAttribute('playQueueID', '1'); - $xml->addAttribute('playQueueSelectedItemID', '1'); - $xml->addAttribute('playQueueSelectedItemOffset', '0'); - $xml->addAttribute('playQueueVersion', '1'); - $c = 0; - $GLOBALS['user']->playlist->clear(); $id = 0; if (!empty($key)) { $id = self::getKeyFromMetadataUri($key); } elseif (!empty($uri)) { - $puri = parse_url($uri); - if ($puri['scheme'] == 'library') { - // We ignore library uuid (= $puri['host']) - $ppath = explode('/', $puri['path']); - if (count($ppath) == 3) { - if ($ppath['1'] == 'item') { - $key = rawurldecode($ppath[2]); - $id = self::getKeyFromMetadataUri($key); - } - } - } + $key = self::getKeyFromFullUri($uri); + $id = self::getKeyFromMetadataUri($key); } $plmedias = array(); if ($id) { - if ($type == 'audio') { - if (self::isSong($id) || self::isTrack($id)) { - $media = new Song(self::getAmpacheId($id)); - if ($media->id) { - $media->format(); - $plmedias[] = array('object_type' => 'song', 'object_id' => $media->id); - $xitem = self::addSong($xml, $media); - $xitem->addAttribute('playQueueItemID', '1'); - $c++; - } - } elseif (self::isAlbum($id)) { - $album = new Album(self::getAmpacheId($id)); - if ($album->id) { - $song_ids = $album->get_songs(); - foreach ($song_ids as $song_id) { - $media = new Song($song_id); - $media->format(); - $plmedias[] = array('object_type' => 'song', 'object_id' => $media->id); - $xitem = self::addSong($xml, $media); - $xitem->addAttribute('playQueueItemID', '1'); - $c++; - } - } - } elseif (self::isArtist($id)) { - $artist = new Artist(self::getAmpacheId($id)); - if ($artist->id) { - $song_ids = $artist->get_songs(); - foreach ($song_ids as $song_id) { - $media = new Song($song_id); - $media->format(); - $plmedias[] = array('object_type' => 'song', 'object_id' => $media->id); - $xitem = self::addSong($xml, $media); - $xitem->addAttribute('playQueueItemID', '1'); - $c++; - } - } - } - } elseif ($type == 'video') { - if (self::isVideo($id)) { - $media = Video::create_from_id(self::getAmpacheId($id)); - if ($media->id) { - $media->format(); - $plmedias[] = array('object_type' => 'video', 'object_id' => $media->id); - $xitem = self::addVideoExt($xml, $media); - $xitem->addAttribute('playQueueItemID', '1'); - $c++; - } - } elseif (self::isTVShow($id)) { - $tvshow = new TVShow(self::getAmpacheId($id)); - if ($tvshow->id) { - $medias = $tvshow->get_medias(); - $plmedias = array_merge($plmedias, $items); - foreach ($medias as $mediad) { - $media = Video::create_from_id($mediad['object_id']); - $media->format(); - $xitem = self::addVideoExt($xml, $media); - $xitem->addAttribute('playQueueItemID', '1'); - $c++; - } - } - } elseif (self::isTVShowSeason($id)) { - $season = new TVShow_Season(self::getAmpacheId($id)); - if ($season->id) { - $medias = $season->get_medias(); - $plmedias = array_merge($plmedias, $items); - foreach ($medias as $mediad) { - $media = Video::create_from_id($mediad['object_id']); - $media->format(); - $xitem = self::addVideoExt($xml, $media); - $xitem->addAttribute('playQueueItemID', '1'); - $c++; - } - } + if ($type == 'audio' || $type == 'video') { + $item = self::createLibraryItem($id); + if ($item != null) { + $plmedias = $item->get_medias(); } } } else { @@ -1353,50 +1386,39 @@ class Plex_XML_Data if (self::isPlaylist($playlistID)) { $playlist = new Playlist(self::getAmpacheId($playlistID)); if ($shuffle) { - $items = $playlist->get_random_items(); + $plmedias = $playlist->get_random_items(); } else { - $items = $playlist->get_items(); + $plmedias = $playlist->get_items(); } - $plmedias = array_merge($plmedias, $items); - $c = count($items); - self::addPlaylistsItems($xml, $items, array('playQueueItemID' => '1')); } } - if (count($plmedias)) { - $GLOBALS['user']->playlist->add_medias($plmedias); - } - - $xml->addAttribute('playQueueTotalCount', $c); + $GLOBALS['user']->playlist->add_medias($plmedias); + self::setTmpPlayQueue($xml, 1); } public static function setTmpPlayQueue(SimpleXMLElement $xml, $playlistID) { + // We only support one queue at time if ($playlistID != 1) { debug_event('plex', 'Unsupported playlist, it should be 1.', 3); } else { $xml->addAttribute('playQueueID', '1'); - $xml->addAttribute('playQueueSelectedItemID', '1'); - $xml->addAttribute('playQueueSelectedItemOffset', '0'); $xml->addAttribute('playQueueVersion', '1'); - $c = 0; $items = $GLOBALS['user']->playlist->get_items(); - print_r($items); - foreach ($items as $key => $item) { - if ($item['object_type'] == 'song') { - $media = new Song($item['object_id']); - $media->format(); - $xitem = self::addSong($xml, $media); - $xitem->addAttribute('playQueueItemID', $key); - $c++; - } else { - $media = Video::create_from_id($item['object_id']); - $media->format(); - $xitem = self::addVideoExt($xml, $media); - $xitem->addAttribute('playQueueItemID', $key); - $c++; + $c = count($items); + if ($c > 0) { + self::addPlaylistsItems($xml, $items, 'playQueueItemID'); + + // TODO: This should be the real selected item. + // But we're missing this information in Ampache playlist + $currentIndex = 0; + $currentItem = $items[$currentIndex]; + if (isset($currentItem['track_id'])) { + $xml->addAttribute('playQueueSelectedItemID', $currentItem['track_id']); } + $xml->addAttribute('playQueueSelectedItemOffset', $currentIndex); } $xml->addAttribute('playQueueTotalCount', $c); @@ -1500,16 +1522,12 @@ class Plex_XML_Data public static function setSysMovieAgents(SimpleXMLElement $xml) { - self::addNoneAgent($xml, 'Personal Media'); - // We should check plug-in availability and allow configuration here - self::addAgent($xml, "The Movie Database", false, "com.plexapp.agents.themoviedb", true, "en,cs,da,de,el,es,fi,fr,he,hr,hu,it,lv,nl,no,pl,pt,ru,sk,sv,th,tr,vi,zh,ko"); + self::addNoneAgent($xml, 'Ampache Media Movies'); } public static function setSysTVShowAgents(SimpleXMLElement $xml) { - self::addNoneAgent($xml, 'Personal Media Shows'); - // We should check plug-in availability and allow configuration here - self::addAgent($xml, "TheTVDB", false, "com.plexapp.agents.thetvdb", true, "en,fr,zh,sv,no,da,fi,nl,de,it,es,pl,hu,el,tr,ru,he,ja,pt,cs,ko,sl"); + self::addNoneAgent($xml, 'Ampache Media Series'); } public static function setSysPhotoAgents(SimpleXMLElement $xml) @@ -1519,7 +1537,7 @@ class Plex_XML_Data public static function setSysMusicAgents($xml, $category = 'Artists') { - self::addNoneAgent($xml, 'Personal Media ' . $category); + self::addNoneAgent($xml, 'Ampache Media ' . $category); //self::addAgent($xml, 'Last.fm', '1', 'com.plexapp.agents.lastfm', 'true', 'en,sv,fr,es,de,pl,it,pt,ja,tr,ru,zh'); } @@ -1530,6 +1548,10 @@ class Plex_XML_Data return 'movie'; case Plex_XML_Data::PLEX_TVSHOW: return 'tvshow'; + case Plex_XML_Data::PLEX_SEASON: + return 'season'; + case Plex_XML_Data::PLEX_EPISODE: + return 'episode'; case Plex_XML_Data::PLEX_ARTIST: return 'artist'; case Plex_XML_Data::PLEX_ALBUM: @@ -1623,10 +1645,23 @@ class Plex_XML_Data $setting->addAttribute('group', $group); } - public static function setMusicScanners(SimpleXMLElement $xml) + public static function setScanners(SimpleXMLElement $xml, $type) { $scanner = $xml->addChild('Scanner'); - $scanner->addAttribute('name', 'Plex Music Scanner'); + switch ($type) { + case self::PLEX_ALBUM: + case self::PLEX_ARTIST: + $scanner->addAttribute('name', 'Ampache Music Scanner'); + break; + case self::PLEX_TVSHOW: + case self::PLEX_SEASON: + case self::PLEX_EPISODE: + $scanner->addAttribute('name', 'Ampache Series Scanner'); + break; + case self::PLEX_MOVIE: + $scanner->addAttribute('name', 'Ampache Movie Scanner'); + break; + } } public static function createAppStore() @@ -1724,4 +1759,59 @@ class Plex_XML_Data $dir->addAttribute('title', $title); $dir->addAttribute('path', $path); } + + public static function addCatalogIdentity(SimpleXMLElement $xml, Catalog $catalog) + { + $xml->addAttribute('librarySectionID', $catalog->id); + $xml->addAttribute('librarySectionTitle', $catalog->name); + $xml->addAttribute('librarySectionUUID', self::uuidFromkey($catalog->id)); + } + + public static function getPhotoKind($type) + { + switch ($type) { + case 'thumb': + case 'thumbs': + return 'preview'; + case 'art': + case 'arts': + return 'art'; + case 'background': + case 'backgrounds': + return 'background'; + case 'poster': + case 'posters': + default: + return 'default'; + } + } + + public static function getPhotoPlexKind($type) + { + switch ($type) { + case 'preview': + return 'thumb'; + case 'art': + return 'art'; + case 'background': + return 'background'; + case 'default': + default: + return 'poster'; + } + } + + public static function addPhotos(SimpleXMLElement $xml, $id, $kind = 'default') + { + self::addPhoto($xml, $id, $kind); + } + + public static function addPhoto(SimpleXMLElement $xml, $id, $kind = 'default') + { + $xart = $xml->addChild('Photo'); + $uri = self::getMetadataUri($id) . '/' . self::getPhotoPlexKind($kind) . '/' . $id; + $xart->addAttribute('key', $uri); + $xart->addAttribute('ratingKey', $uri); + $xart->addAttribute('thumb', $uri); + } } diff --git a/lib/class/song.class.php b/lib/class/song.class.php index 5769aa0f..f6c11ee4 100644 --- a/lib/class/song.class.php +++ b/lib/class/song.class.php @@ -1368,6 +1368,17 @@ class Song extends database_object implements media, library_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array($this->catalog); + } + /** * Get item's owner. * @return int|null diff --git a/lib/class/song_preview.class.php b/lib/class/song_preview.class.php index 25c491e7..99b8b2c7 100644 --- a/lib/class/song_preview.class.php +++ b/lib/class/song_preview.class.php @@ -248,6 +248,17 @@ class Song_Preview extends database_object implements media, playable_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array(); + } + /** * play_url * This function takes all the song information and correctly formats a diff --git a/lib/class/tag.class.php b/lib/class/tag.class.php index e5a97b5f..16be86c3 100644 --- a/lib/class/tag.class.php +++ b/lib/class/tag.class.php @@ -669,6 +669,17 @@ class Tag extends database_object implements library_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array(); + } + public function get_user_owner() { return null; diff --git a/lib/class/tmp_playlist.class.php b/lib/class/tmp_playlist.class.php index 856709fe..024ae320 100644 --- a/lib/class/tmp_playlist.class.php +++ b/lib/class/tmp_playlist.class.php @@ -146,11 +146,13 @@ class Tmp_Playlist extends database_object /* Define the array */ $items = array(); + $i = 1; while ($results = Dba::fetch_assoc($db_results)) { - $key = $results['id']; - $items[$key] = array( + $items[] = array( 'object_type' => $results['object_type'], - 'object_id' => $results['object_id'] + 'object_id' => $results['object_id'], + 'track_id' => $results['id'], + 'track' => $i++, ); } diff --git a/lib/class/tvshow.class.php b/lib/class/tvshow.class.php index 7e66f12b..eec28bb0 100644 --- a/lib/class/tvshow.class.php +++ b/lib/class/tvshow.class.php @@ -29,6 +29,7 @@ class TVShow extends database_object implements library_item public $summary; public $year; + public $catalog_id; public $tags; public $f_tags; public $episodes; @@ -118,7 +119,7 @@ class TVShow extends database_object implements library_item $sql .= "LEFT JOIN `video` ON `video`.`id` = `tvshow_episode`.`id` "; $sql .= "LEFT JOIN `catalog` ON `catalog`.`id` = `video`.`catalog` "; } - $sql .= "LEFT JOIN `tvshow_season` ON `tvshow_season`.`tvshow` = `tvshow_episode`.`season` "; + $sql .= "LEFT JOIN `tvshow_season` ON `tvshow_season`.`id` = `tvshow_episode`.`season` "; $sql .= "WHERE `tvshow_season`.`tvshow`='" . Dba::escape($this->id) . "' "; if (AmpConfig::get('catalog_disable')) { $sql .= "AND `catalog`.`enabled` = '1' "; @@ -145,8 +146,9 @@ class TVShow extends database_object implements library_item if (parent::is_cached('tvshow_extra', $this->id) ) { $row = parent::get_from_cache('tvshow_extra', $this->id); } else { - $sql = "SELECT COUNT(`tvshow_episode`.`id`) AS `episode_count` FROM `tvshow_season` " . + $sql = "SELECT COUNT(`tvshow_episode`.`id`) AS `episode_count`, `video`.`catalog` as `catalog_id` FROM `tvshow_season` " . "LEFT JOIN `tvshow_episode` ON `tvshow_episode`.`season` = `tvshow_season`.`id` " . + "LEFT JOIN `video` ON `video`.`id` = `tvshow_episode`.`id` " . "WHERE `tvshow_season`.`tvshow` = ?"; $db_results = Dba::read($sql, array($this->id)); $row = Dba::fetch_assoc($db_results); @@ -163,6 +165,7 @@ class TVShow extends database_object implements library_item /* Set Object Vars */ $this->episodes = $row['episode_count']; $this->seasons = $row['season_count']; + $this->catalog_id = $row['catalog_id']; return $row; @@ -229,6 +232,17 @@ class TVShow extends database_object implements library_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array($this->catalog_id); + } + public function get_user_owner() { return null; @@ -305,10 +319,13 @@ class TVShow extends database_object implements library_item { // Save our current ID $current_id = $this->id; + $name = $data['name'] ?: $this->name; + $year = $data['year'] ?: $this->year; + $summary = $data['summary'] ?: $this->summary; // Check if name is different than current name - if ($this->name != $data['name'] || $this->year != $data['year']) { - $tvshow_id = self::check($data['name'], $data['year'], true); + if ($this->name != $name || $this->year != $year) { + $tvshow_id = self::check($name, $year, true); // If it's changed we need to update if ($tvshow_id != $this->id && $tvshow_id != null) { @@ -321,18 +338,25 @@ class TVShow extends database_object implements library_item } // end if it changed } - $trimmed = Catalog::trim_prefix(trim($data['name'])); + $trimmed = Catalog::trim_prefix(trim($name)); $name = $trimmed['string']; $prefix = $trimmed['prefix']; $sql = 'UPDATE `tvshow` SET `name` = ?, `prefix` = ?, `year` = ?, `summary` = ? WHERE `id` = ?'; - Dba::write($sql, array($name, $prefix, $data['year'], $data['summary'], $current_id)); + Dba::write($sql, array($name, $prefix, $year, $summary, $current_id)); + + $this->name = $name; + $this->prefix = $prefix; + $this->year = $year; + $this->summary = $summary; $override_childs = false; if ($data['apply_childs'] == 'checked') { $override_childs = true; } - $this->update_tags($data['edit_tags'], $override_childs, $current_id); + if (isset($data['edit_tags'])) { + $this->update_tags($data['edit_tags'], $override_childs, $current_id); + } return $current_id; diff --git a/lib/class/tvshow_episode.class.php b/lib/class/tvshow_episode.class.php index f89731ca..c5a92cb5 100644 --- a/lib/class/tvshow_episode.class.php +++ b/lib/class/tvshow_episode.class.php @@ -122,10 +122,19 @@ class TVShow_Episode extends Video public function update(array $data) { parent::update($data); - $sql = "UPDATE `tvshow_episode` SET `original_name` = ?, `season` = ?, `episode_number` = ?, `summary` = ? WHERE `id` = ?"; - Dba::write($sql, array($data['original_name'], $data['tvshow_season'], $data['tvshow_episode'], $data['summary'], $this->id)); - Tag::update_tag_list($data['edit_tags'], 'episode', $this->id); + $original_name = $data['original_name'] ?: $this->original_name; + $tvshow_season = $data['tvshow_season'] ?: $this->season; + $tvshow_episode = $data['tvshow_episode'] ?: $this->episode_number; + $summary = $data['summary'] ?: $summary; + + $sql = "UPDATE `tvshow_episode` SET `original_name` = ?, `season` = ?, `episode_number` = ?, `summary` = ? WHERE `id` = ?"; + Dba::write($sql, array($original_name, $tvshow_season, $tvshow_episode, $summary, $this->id)); + + $this->original_name = $originale_name; + $this->tvshow_season = $tvshow_season; + $this->tvshow_episode = $tvshow_episode; + $this->summary = $summary; return $this->id; diff --git a/lib/class/tvshow_season.class.php b/lib/class/tvshow_season.class.php index 8dbe951d..28663e93 100644 --- a/lib/class/tvshow_season.class.php +++ b/lib/class/tvshow_season.class.php @@ -27,6 +27,7 @@ class TVShow_Season extends database_object implements library_item public $season_number; public $tvshow; + public $catalog_id; public $episodes; public $f_name; public $f_tvshow; @@ -107,7 +108,8 @@ class TVShow_Season extends database_object implements library_item if (parent::is_cached('tvshow_extra', $this->id) ) { $row = parent::get_from_cache('tvshow_extra', $this->id); } else { - $sql = "SELECT COUNT(`tvshow_episode`.`id`) AS `episode_count` FROM `tvshow_episode` " . + $sql = "SELECT COUNT(`tvshow_episode`.`id`) AS `episode_count`, `video`.`catalog` as `catalog_id` FROM `tvshow_episode` " . + "LEFT JOIN `video` ON `video`.`id` = `tvshow_episode`.`id` " . "WHERE `tvshow_episode`.`season` = ?"; $db_results = Dba::read($sql, array($this->id)); @@ -117,6 +119,7 @@ class TVShow_Season extends database_object implements library_item /* Set Object Vars */ $this->episodes = $row['episode_count']; + $this->catalog_id = $row['catalog_id']; return $row; @@ -190,6 +193,17 @@ class TVShow_Season extends database_object implements library_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array($this->catalog_id); + } + public function get_user_owner() { return null; diff --git a/lib/class/video.class.php b/lib/class/video.class.php index 4bdff89d..0747e16e 100644 --- a/lib/class/video.class.php +++ b/lib/class/video.class.php @@ -344,6 +344,17 @@ class Video extends database_object implements media, library_item return $medias; } + /** + * get_catalogs + * + * Get all catalog ids related to this item. + * @return int[] + */ + public function get_catalogs() + { + return array($this->catalog); + } + /** * Get item's owner. * @return int|null @@ -576,11 +587,23 @@ class Video extends database_object implements media, library_item */ public function update(array $data) { - $f_release_date = $data['release_date']; - $release_date = strtotime($f_release_date); + if (isset($data['release_date'])) { + $f_release_date = $data['release_date']; + $release_date = strtotime($f_release_date); + } else { + $release_date = $this->release_date; + } + $title = $data['title'] ?: $this->title; $sql = "UPDATE `video` SET `title` = ?, `release_date` = ? WHERE `id` = ?"; - Dba::write($sql, array($data['title'], $release_date, $this->id)); + Dba::write($sql, array($title, $release_date, $this->id)); + + if (isset($data['edit_tags'])) { + Tag::update_tag_list($data['edit_tags'], 'video', $this->id); + } + + $this->title = $title; + $this->release_date = $release_date; return $this->id;