<commit_before><?php declare(strict_types=1);

/**
 * ownCloud - Music app
 *
 * This file is licensed under the Affero General Public License version 3 or
 * later. See the COPYING file.
 *
 * @author <NAME> <<EMAIL>>
 * @copyright <NAME> 2021
 */

namespace OCA\Music\Db;

use \OCP\AppFramework\Db\Entity;
use \OCA\Music\Utility\Util;

/**
 * @method string getUserId()
 * @method void setUserId(string $userId)
 * @method int getChannelId()
 * @method void setChannelId(int $id)
 * @method ?string getStreamUrl()
 * @method setStreamUrl(?string $url)
 * @method ?string getMimetype()
 * @method setMimetype(?string $mime)
 * @method ?int getSize()
 * @method void setSize(?int $size)
 * @method ?int getDuration()
 * @method void setDuration(?int $duration)
 * @method string getGuid()
 * @method void setGuid(string $guid)
 * @method string getGuidHash()
 * @method void setGuidHash(string $guidHash)
 * @method ?string getTitle()
 * @method void setTitle(?string $title)
 * @method ?int getEpisode()
 * @method void setEpisode(?int $episode)
 * @method ?int getSeason()
 * @method void setSeason(?int $season)
 * @method ?string getLinkUrl()
 * @method void setLinkUrl(?string $url)
 * @method ?string getPublished()
 * @method void setPublished(?string $timestamp)
 * @method ?string getKeywords()
 * @method void setKeywords(?string $keywords)
 * @method ?string getCopyright()
 * @method void setCopyright(?string $copyright)
 * @method ?string getAuthor()
 * @method void setAuthor(?string $author)
 * @method ?string getDescription()
 * @method void setDescription(?string $description)
 * @method ?string getStarred()
 * @method void setStarred(?string $timestamp)
 * @method ?string getCreated()
 * @method void setCreated(?string $timestamp)
 * @method ?string getUpdated()
 * @method void setUpdated(?string $timestamp)
 */
class PodcastEpisode extends Entity {
	public $userId;
	public $channelId;
	public $streamUrl;
	public $mimetype;
	public $size;
	public $duration;
	public $guid;
	public $guidHash;
	public $title;
	public $episode;
	public $season;
	public $linkUrl;
	public $published;
	public $keywords;
	public $copyright;
	public $author;
	public $description;
	public $starred;
	public $created;
	public $updated;

	public function __construct() {
		$this->addType('channelId', 'int');
		$this->addType('size', 'int');
		$this->addType('duration', 'int');
		$this->addType('episode', 'int');
	}

	public function toApi() : array {
		return [
			'id' => $this->getId(),
			'title' => $this->getTitle(),
			'ordinal' => $this->getEpisodeWithSeason(),
			'stream_url' => $this->getStreamUrl(),
			'mimetype' => $this->getMimetype()
		];
	}

	public function detailsToApi() : array {
		return [
			'id' => $this->getId(),
			'title' => $this->getTitle(),
			'episode' => $this->getEpisode(),
			'season' => $this->getSeason(),
			'description' => $this->getDescription(),
			'channel_id' => $this->getChannelId(),
			'link_url' => $this->getLinkUrl(),
			'stream_url' => $this->getStreamUrl(),
			'mimetype' => $this->getMimetype(),
			'author' => $this->getAuthor(),
			'copyright' => $this->getCopyright(),
			'duration' => $this->getDuration(),
			'size' => $this->getSize(),
			'bit_rate' => $this->getBitrate(),
			'guid' => $this->getGuid(),
			'keywords' => $this->getKeywords(),
			'published' => $this->getPublished(),
		];
	}

	public function toAmpacheApi() : array {
		return [
			'id' => (string)$this->getId(),
			'name' => $this->getTitle(),
			'title' => $this->getTitle(),
			'description' => $this->getDescription(),
			'author' => $this->getAuthor(),
			'author_full' => $this->getAuthor(),
			'website' => $this->getLinkUrl(),
			'pubdate' => Util::formatDateTimeUtcOffset($this->getPublished()),
			'state' => 'Completed',
			'filelength' => Util::formatTime($this->getDuration()),
			'filesize' => Util::formatFileSize($this->getSize(), 2) . 'B',
			'mime' => $this->getMimetype(),
			'url' => $this->getStreamUrl(),
			'flag' => empty($this->getStarred()) ? 0 : 1,
		];
	}

	public function toSubsonicApi() : array {
		$result = [
			'id' => 'podcast_episode-' . $this->getId(),
			'streamId' => 'podcast_episode-' . $this->getId(),
			'channelId' => 'podcast_channel-' . $this->getChannelId(),
			'title' => $this->getTitle(),
			'track' => $this->getEpisode(),
			'description' => $this->getDescription(),
			'publishDate' => Util::formatZuluDateTime($this->getPublished()),
			'status' => 'completed',
			'parent' => 'podcast_channel-' . $this->getChannelId(),
			'isDir' => false,
			'year' => $this->getYear(),
			'genre' => 'Podcast',
			'coverArt' => 'podcast_channel-' . $this->getChannelId(),
			'size' => $this->getSize(),
			'contentType' => $this->getMimetype(),
			'suffix' => $this->getSuffix(),
			'duration' => $this->getDuration(),
			'bitRate' => empty($this->getBitrate()) ? 0 : (int)\round($this->getBitrate()/1000), // convert bps to kbps
		];

		if (!empty($this->starred)) {
			$result['starred'] = Util::formatZuluDateTime($this->starred);
		}

		return $result;
	}

	public function getEpisodeWithSeason() : ?string {
		$result = (string)$this->getEpisode();
		// the season is considered only if there actually is an episode
		$season = $this->getSeason();
		if ($result !== null && $season !== null) {
			$result = "$season-$result";
		}
		return $result;
	}

	public function getYear() : ?int {
		$matches = null;
		if (\is_string($this->published) && \preg_match('/^(\d\d\d\d)-\d\d-\d\d.*/', $this->published, $matches) === 1) {
			return (int)$matches[1];
		} else {<commit_msg>Subsonic: Add a few more fields to the podcast episode responses<commit_after><?php declare(strict_types=1);

/**
 * ownCloud - Music app
 *
 * This file is licensed under the Affero General Public License version 3 or
 * later. See the COPYING file.
 *
 * @author <NAME> <<EMAIL>>
 * @copyright Pauli Järvinen 2021
 */

namespace OCA\Music\Db;

use \OCP\AppFramework\Db\Entity;
use \OCA\Music\Utility\Util;

/**
 * @method string getUserId()
 * @method void setUserId(string $userId)
 * @method int getChannelId()
 * @method void setChannelId(int $id)
 * @method ?string getStreamUrl()
 * @method setStreamUrl(?string $url)
 * @method ?string getMimetype()
 * @method setMimetype(?string $mime)
 * @method ?int getSize()
 * @method void setSize(?int $size)
 * @method ?int getDuration()
 * @method void setDuration(?int $duration)
 * @method string getGuid()
 * @method void setGuid(string $guid)
 * @method string getGuidHash()
 * @method void setGuidHash(string $guidHash)
 * @method ?string getTitle()
 * @method void setTitle(?string $title)
 * @method ?int getEpisode()
 * @method void setEpisode(?int $episode)
 * @method ?int getSeason()
 * @method void setSeason(?int $season)
 * @method ?string getLinkUrl()
 * @method void setLinkUrl(?string $url)
 * @method ?string getPublished()
 * @method void setPublished(?string $timestamp)
 * @method ?string getKeywords()
 * @method void setKeywords(?string $keywords)
 * @method ?string getCopyright()
 * @method void setCopyright(?string $copyright)
 * @method ?string getAuthor()
 * @method void setAuthor(?string $author)
 * @method ?string getDescription()
 * @method void setDescription(?string $description)
 * @method ?string getStarred()
 * @method void setStarred(?string $timestamp)
 * @method ?string getCreated()
 * @method void setCreated(?string $timestamp)
 * @method ?string getUpdated()
 * @method void setUpdated(?string $timestamp)
 */
class PodcastEpisode extends Entity {
	public $userId;
	public $channelId;
	public $streamUrl;
	public $mimetype;
	public $size;
	public $duration;
	public $guid;
	public $guidHash;
	public $title;
	public $episode;
	public $season;
	public $linkUrl;
	public $published;
	public $keywords;
	public $copyright;
	public $author;
	public $description;
	public $starred;
	public $created;
	public $updated;

	public function __construct() {
		$this->addType('channelId', 'int');
		$this->addType('size', 'int');
		$this->addType('duration', 'int');
		$this->addType('episode', 'int');
	}

	public function toApi() : array {
		return [
			'id' => $this->getId(),
			'title' => $this->getTitle(),
			'ordinal' => $this->getEpisodeWithSeason(),
			'stream_url' => $this->getStreamUrl(),
			'mimetype' => $this->getMimetype()
		];
	}

	public function detailsToApi() : array {
		return [
			'id' => $this->getId(),
			'title' => $this->getTitle(),
			'episode' => $this->getEpisode(),
			'season' => $this->getSeason(),
			'description' => $this->getDescription(),
			'channel_id' => $this->getChannelId(),
			'link_url' => $this->getLinkUrl(),
			'stream_url' => $this->getStreamUrl(),
			'mimetype' => $this->getMimetype(),
			'author' => $this->getAuthor(),
			'copyright' => $this->getCopyright(),
			'duration' => $this->getDuration(),
			'size' => $this->getSize(),
			'bit_rate' => $this->getBitrate(),
			'guid' => $this->getGuid(),
			'keywords' => $this->getKeywords(),
			'published' => $this->getPublished(),
		];
	}

	public function toAmpacheApi() : array {
		return [
			'id' => (string)$this->getId(),
			'name' => $this->getTitle(),
			'title' => $this->getTitle(),
			'description' => $this->getDescription(),
			'author' => $this->getAuthor(),
			'author_full' => $this->getAuthor(),
			'website' => $this->getLinkUrl(),
			'pubdate' => Util::formatDateTimeUtcOffset($this->getPublished()),
			'state' => 'Completed',
			'filelength' => Util::formatTime($this->getDuration()),
			'filesize' => Util::formatFileSize($this->getSize(), 2) . 'B',
			'mime' => $this->getMimetype(),
			'url' => $this->getStreamUrl(),
			'flag' => empty($this->getStarred()) ? 0 : 1,
		];
	}

	public function toSubsonicApi() : array {
		$result = [
			'id' => 'podcast_episode-' . $this->getId(),
			'streamId' => 'podcast_episode-' . $this->getId(),
			'channelId' => 'podcast_channel-' . $this->getChannelId(),
			'title' => $this->getTitle(),
			'artist' => $this->getAuthor(),
			'track' => $this->getEpisode(),
			'description' => $this->getDescription(),
			'publishDate' => Util::formatZuluDateTime($this->getPublished()),
			'status' => 'completed',
			'parent' => 'podcast_channel-' . $this->getChannelId(),
			'isDir' => false,
			'year' => $this->getYear(),
			'genre' => 'Podcast',
			'coverArt' => 'podcast_channel-' . $this->getChannelId(),
			'size' => $this->getSize(),
			'contentType' => $this->getMimetype(),
			'suffix' => $this->getSuffix(),
			'duration' => $this->getDuration(),
			'bitRate' => empty($this->getBitrate()) ? 0 : (int)\round($this->getBitrate()/1000), // convert bps to kbps
			'type' => 'podcast',
			'created' => Util::formatZuluDateTime($this->getCreated())
		];

		if (!empty($this->starred)) {
			$result['starred'] = Util::formatZuluDateTime($this->starred);
		}

		return $result;
	}

	public function getEpisodeWithSeason() : ?string {
		$result = (string)$this->getEpisode();
		// the season is considered only if there actually is an episode
		$season = $this->getSeason();
		if ($result !== null && $season !== null) {
			$result = "$season-$result";
		}
		return $result;
	}

	public function getYear() : ?int {
		$matches = null;
		if (\is_string($this->published) && \preg_match('/^(\d\d\d\d)-\d\d-\d\d.*/', $this->published, $matches) === 1) {
			return (int)$matches[1];
		} else {
{'fraction_non_alphanumeric': 0.19906094968107724, 'fraction_numerical': 0.002834868887313962, 'mean_word_length': 4.51220703125, 'pattern_counts': {'":': 0, '<': 12, '<?xml version=': 0, '>': 245, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 16, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5077404', 'n_tokens_mistral': 4164, 'n_tokens_neox': 3780, 'n_words': 857}