transcoding -> videos

This commit is contained in:
shimon
2023-04-04 17:08:45 +03:00
parent 2b60b18a3c
commit c09f600e73
10 changed files with 60 additions and 31 deletions
+1 -1
View File
@@ -185,7 +185,7 @@ RUN chmod +x /usr/local/bin/doctor && \
chmod +x /usr/local/bin/worker-builds && \
chmod +x /usr/local/bin/worker-mails && \
chmod +x /usr/local/bin/worker-messaging && \
chmod +x /usr/local/bin/worker-transcoding && \
chmod +x /usr/local/bin/worker-videos && \
chmod +x /usr/local/bin/worker-webhooks
# Letsencrypt Permissions
+8 -9
View File
@@ -1,7 +1,7 @@
<?php
use Appwrite\Event\Delete;
use Appwrite\Event\Transcoding;
use Appwrite\Event\Video;
use Appwrite\OpenSSL\OpenSSL;
use Appwrite\Utopia\Database\Validator\CustomId;
use Appwrite\Utopia\Database\Validator\Queries\Files;
@@ -109,13 +109,13 @@ App::post('/v1/videos')
]));
});
(new Transcoding())
(new Video())
->setAction('preview')
->setProject($project)
->setVideo($video)
->trigger();
(new Transcoding())
(new Video())
->setAction('timeline')
->setProject($project)
->setVideo($video)
@@ -360,7 +360,7 @@ App::post('/v1/videos/:videoId/preview')
throw new Exception(Exception::VIDEO_SECOND_OUT_OF_RANGE);
}
(new Transcoding())
(new Video())
->setAction('preview')
->setProject($project)
->setVideo($video)
@@ -651,8 +651,7 @@ App::post('/v1/videos/:videoId/rendition')
throw new Exception(Exception::VIDEO_PROFILE_NOT_FOUND);
}
$transcoder = new Transcoding();
$transcoder
(new Video())
->setAction('encode')
->setProject($project)
->setVideo($video)
@@ -843,7 +842,7 @@ App::get('/v1/videos/:videoId/outputs/:output')
throw new Exception(Exception::VIDEO_RENDITION_NOT_FOUND);
}
$baseUrl = 'http://127.0.0.1/v1/videos/' . $videoId . '/outputs/' . $output;
$baseUrl = TMP_HOST . 'v1/videos/' . $videoId . '/outputs/' . $output;
$subtitles = Authorization::skip(fn() => $dbForProject->find('videos_subtitles', [
Query::equal('videoId', [$video->getId()]),
]));
@@ -1019,7 +1018,7 @@ App::get('/v1/videos/:videoId/outputs/:output/renditions/:renditionId/streams/:s
foreach ($segments as $segment) {
$_segments[] = [
'duration' => $segment->getAttribute('duration'),
'url' => 'http://127.0.0.1/v1/videos/' . $videoId . '/outputs/' . $output . '/renditions/' . $renditionId . '/segments/' . $segment->getId(),
'url' => TMP_HOST . 'v1/videos/' . $videoId . '/outputs/' . $output . '/renditions/' . $renditionId . '/segments/' . $segment->getId(),
];
}
@@ -1115,7 +1114,7 @@ App::get('/v1/videos/:videoId/outputs/:output/subtitles/:subtitleId')
foreach ($segments as $segment) {
$_segments[] = [
'duration' => $segment->getAttribute('duration'),
'url' => 'http://127.0.0.1/v1/videos/' . $videoId . '/outputs/' . $output . '/subtitles/' . $subtitleId . '/segments/' . $segment->getId(),
'url' => TMP_HOST . 'v1/videos/' . $videoId . '/outputs/' . $output . '/subtitles/' . $subtitleId . '/segments/' . $segment->getId(),
];
}
+1 -1
View File
@@ -176,7 +176,7 @@ const APP_AUTH_TYPE_KEY = 'Key';
const APP_AUTH_TYPE_ADMIN = 'Admin';
// Response related
const MAX_OUTPUT_CHUNK_SIZE = 2 * 1024 * 1024; // 2MB
const TMP_HOST = 'http://127.0.0.1/';
$register = new Registry();
App::setMode(App::getEnv('_APP_ENV', App::MODE_TYPE_PRODUCTION));
@@ -25,10 +25,10 @@ use Utopia\Storage\Device\Local;
require_once __DIR__ . '/../init.php';
Console::title('Transcoding V1 Worker');
Console::success(APP_NAME . ' transcoding worker v1 has started');
Console::title('Video V1 Worker');
Console::success(APP_NAME . ' video worker v1 has started');
class TranscodingV1 extends Worker
class VideosV1 extends Worker
{
/**
* Rendition Status
@@ -73,7 +73,7 @@ class TranscodingV1 extends Worker
public function getName(): string
{
return "Transcoding v1";
return "Video v1";
}
public function init(): void
@@ -255,7 +255,9 @@ class TranscodingV1 extends Worker
];
$result = shell_exec(implode(" ", $cmd));
/** Vtt creation**/
/**
* Vtt creation*
*/
if ($result !== false) {
$size = explode('x', $timeline['size']);
$counter = 0;
@@ -270,7 +272,7 @@ class TranscodingV1 extends Worker
'path' => $path,
]));
$url = 'http://127.0.0.1/v1/videos/' . $this->video->getId() . '/preview/' . $sprite->getId();
$url = TMP_HOST . 'v1/videos/' . $this->video->getId() . '/preview/' . $sprite->getId() . '/';
for ($col = 0; $col < $size[0]; $col++) {
for ($row = 0; $row < $size[1]; $row++) {
$data .= "\n" . gmdate("H:i:s", $counter * $interval) . " --> " . gmdate("H:i:s", ($counter + 1) * $interval) . "\n" . $url . "#xywh=" . ($row * $timeline['width']) . "," . ($col * $timeline['height']) . "," . $timeline['width'] . "," . $timeline['height'];
+1 -1
View File
@@ -7,4 +7,4 @@ else
REDIS_BACKEND="redis://${_APP_REDIS_USER}:${_APP_REDIS_PASS}@${_APP_REDIS_HOST}:${_APP_REDIS_PORT}"
fi
INTERVAL=0.1 QUEUE='v1-transcoding' APP_INCLUDE='/usr/src/code/app/workers/transcoding.php' php /usr/src/code/vendor/bin/resque -dopcache.preload=opcache.preload=/usr/src/code/app/preload.php
INTERVAL=0.1 QUEUE='v1-videos' APP_INCLUDE='/usr/src/code/app/workers/videos.php' php /usr/src/code/vendor/bin/resque -dopcache.preload=opcache.preload=/usr/src/code/app/preload.php
+3 -3
View File
@@ -228,10 +228,10 @@ services:
- _APP_LOGGING_PROVIDER
- _APP_LOGGING_CONFIG
appwrite-worker-transcoding:
entrypoint: worker-transcoding
appwrite-worker-videos:
entrypoint: worker-videos
<<: *x-logging
container_name: appwrite-worker-transcoding
container_name: appwrite-worker-videos
build:
context: .
networks:
+2 -2
View File
@@ -32,8 +32,8 @@ class Event
public const BUILDS_QUEUE_NAME = 'v1-builds';
public const BUILDS_CLASS_NAME = 'BuildsV1';
public const TRANSCODING_QUEUE_NAME = 'v1-transcoding';
public const TRANSCODING_CLASS_NAME = 'TranscodingV1';
public const VIDEO_QUEUE_NAME = 'v1-videos';
public const VIDEO_CLASS_NAME = 'VideosV1';
public const MESSAGING_QUEUE_NAME = 'v1-messaging';
public const MESSAGING_CLASS_NAME = 'MessagingV1';
@@ -5,7 +5,7 @@ namespace Appwrite\Event;
use Resque;
use Utopia\Database\Document;
class Transcoding extends Event
class Video extends Event
{
protected ?Document $video = null;
protected ?Document $profile = null;
@@ -15,7 +15,7 @@ class Transcoding extends Event
public function __construct()
{
parent::__construct(Event::TRANSCODING_QUEUE_NAME, Event::TRANSCODING_CLASS_NAME);
parent::__construct(Event::VIDEO_QUEUE_NAME, Event::VIDEO_CLASS_NAME);
}
/**
@@ -96,7 +96,7 @@ class VideosCustomClientTest extends Scope
'bucketId' => $this->getBucket()['$id'],
'fileId' => $this->getSubtitle()['$id'],
'name' => 'English',
'code' => 'eng',
'code' => 'Eng',
'default' => true,
]);
@@ -117,6 +117,7 @@ class VideosCustomClientTest extends Scope
$this->assertEquals(404, $response['headers']['status-code']);
$response = $this->client->call(Client::METHOD_POST, '/videos/' . $videoId . '/subtitles', [
'content-type' => 'application/json',
'x-appwrite-project' => $this->getProject()['$id'],
@@ -251,8 +252,8 @@ class VideosCustomClientTest extends Scope
$subsCount = 0;
$isVideo = false;
$isAudio = false;
$subs[] = ['id' => '2', 'lang' => 'eng',];
$subs[] = ['id' => '3', 'lang' => 'it',];
$subs[] = ['id' => '2', 'lang' => 'Eng',];
$subs[] = ['id' => '3', 'lang' => 'It',];
foreach ($xml->Period->AdaptationSet as $adaptation) {
if ((string)$adaptation['contentType'] === 'video') {
$isVideo = true;
@@ -253,6 +253,7 @@ class VideosCustomServerTest extends Scope
$this->assertNotEmpty($response['body']);
$this->assertNotEmpty($response['body']['$id']);
$this->assertEquals(92810, $response['body']['duration']);
/**
* timeline vtt
*/
@@ -263,7 +264,33 @@ class VideosCustomServerTest extends Scope
]);
$this->assertEquals(200, $response['headers']['status-code']);
$this->assertNotEmpty($response['body']);
$this->assertEquals(2956, strlen($response['body']));
preg_match_all('#\b/videos[^,\s()<>]+(?:\([\w\d]+\)|([^,[:punct:]\s]|/))#', $response['body'], $match);
$this->assertEquals(25, count($match[0]));
/**
* timeline preview image
*/
$response = $this->client->call(Client::METHOD_GET, '/v1' . $match[0][0], [
'content-type' => 'application/json',
'x-appwrite-project' => $this->getProject()['$id'],
'x-appwrite-key' => $this->getProject()['apiKey'],
]);
$this->assertEquals('image/jpeg', $response['headers']['content-type']);
$this->assertEquals('miss', $response['headers']['x-appwrite-cache']);
sleep(3);
/**
* timeline preview image (response from cache)
*/
$response = $this->client->call(Client::METHOD_GET, '/v1' . $match[0][0], [
'content-type' => 'application/json',
'x-appwrite-project' => $this->getProject()['$id'],
'x-appwrite-key' => $this->getProject()['apiKey'],
]);
$this->assertEquals('image/jpeg', $response['headers']['content-type']);
$this->assertEquals('hit', $response['headers']['x-appwrite-cache']);
$response = $this->client->call(Client::METHOD_GET, '/v1/videos/' . $videoId, [
'content-type' => 'application/json',
@@ -333,7 +360,7 @@ class VideosCustomServerTest extends Scope
'bucketId' => $this->getBucket()['$id'],
'fileId' => $this->getSubtitle()['$id'],
'name' => 'English',
'code' => 'Eng',
'code' => 'eng',
'default' => true,
]);
@@ -495,7 +522,7 @@ class VideosCustomServerTest extends Scope
'bucketId' => $this->getBucket()['$id'],
'fileId' => $this->getSubtitle()['$id'],
'name' => 'English',
'code' => 'Eng',
'code' => 'eng',
'default' => true,
]);