Derivates API https://janezurevc.name/ en DrupalCon Denver 2011 - Media derivatives: take control over your files https://janezurevc.name/drupalcon-denver-2011-media-derivatives-take-control-over-your-files <span>DrupalCon Denver 2011 - Media derivatives: take control over your files</span> <span><span lang="" about="https://janezurevc.name/users/slashrsm" typeof="schema:Person" property="schema:name" datatype="" xml:lang="">slashrsm</span></span> <span>Mon, 07.11.2011 - 22:45</span> <div class="field field--name-body field--type-text-with-summary field--label-hidden field--item"><p><a href="https://drupal.org/project/media_derivatives">Derivatives API</a> is a Drupal project I developed during this year's Summer of Code. It is a framework, that tries to implement a simple, reliable and powerfull framework for asset derivation in Drupal. It can cover a lot of different use cases. We are in the times of emerging new technologies of HTML5, mobile publishing, responsive web, ... I believe that Derivatives API has it's piece in a puzzle of support of this new technologies on Drupal. </p> <p>In cooperation with my mentor, <a href="https://drupal.org/user/48877">Kevin Reynen</a>, I proposed<a href="https://denver2012.drupal.org/program/sessions/media-derivatives-take-control-over-your-files"> a session at DrupalCon Denver</a>, where we'd like to present this project to the wider public. Session will cover basic functionalities of the project, some possible use cases and it's extension with your own plugins. </p> <p>Would you like to hear about this project on DrupalCon? Please <a href="https://denver2012.drupal.org/program/sessions/media-derivatives-take-control-over-your-files">vote for our session</a>.</p> <p>Do you have any suggestions or questions? Feel free to comment here or on session proposal.</p> <p>Hope to see you in Denver!</p> </div> Mon, 07 Nov 2011 21:45:07 +0000 slashrsm 26 at https://janezurevc.name 5 day challenge (i'm in!:) https://janezurevc.name/5-day-challenge-im <span>5 day challenge (i'm in!:)</span> <span><span lang="" about="https://janezurevc.name/users/slashrsm" typeof="schema:Person" property="schema:name" datatype="" xml:lang="">slashrsm</span></span> <span>Sat, 17.09.2011 - 23:09</span> <div class="field field--name-body field--type-text-with-summary field--label-hidden field--item"><p>Today <a href="https://acquia.com/blog/5-days-5-challenges-drupal">Jakub Suchy proposed a really cool thing</a> on his blog. Idea is about spending 30 minutes each day in the next week to contribute something to Drupal. He proves, that only 63 people doing this, can do as much work as an individual could do in a month.</p> <p>Since I immediately loved this idea, I decided to join. Here is my plan for <a href="https://twitter.com/#!/search/realtime/d5dchallenge">#d5dChallenge</a>:</p> <ul><li><b>Day 1:</b> improve <a href="https://drupal.org/project/media_derivatives">Media derivatives API</a> views support,</li> <li><strong>Day 2:</strong> write some docs for Media derivatives API,</li> <li><b>Day 3:</b> work on YouTube uploader engine for Media derivatives API,</li> <li><strong>Day 4:</strong> spend some time in Media issue queue; find some issue to review or submit a simple patch; find some issues I could help with <a href="https://groups.drupal.org/node/173749">during Media code sprint</a>,</li> <li><strong>Day 5:</strong> do some research about Rules integration development and plan Rules integration for Media derivatives API.</li> </ul><p>What do you think about this list? You can also propose something else, if you think I should rather work on some other tasks during this week.</p> <p>Will you join too? I hope there will be even more than 63 of us!</p> </div> Sat, 17 Sep 2011 21:09:01 +0000 slashrsm 19 at https://janezurevc.name BoF about Media Derivatives API on DrupalCon Lonon https://janezurevc.name/bof-about-media-derivatives-api-drupalcon-lonon <span>BoF about Media Derivatives API on DrupalCon Lonon</span> <span><span lang="" about="https://janezurevc.name/users/slashrsm" typeof="schema:Person" property="schema:name" datatype="" xml:lang="">slashrsm</span></span> <span>Mon, 22.08.2011 - 11:56</span> <div class="field field--name-body field--type-text-with-summary field--label-hidden field--item"><p>There will be a <a href="https://london2011.drupal.org/bofsession/media-derivatives-api">BoF session</a> about <a href="https://drupal.org/project/media_derivatives">Media derivatives API</a> on <a href="https://london2011.drupal.org">DrupalCon London</a>. </p> <p>I will present the current state of this project and planned roadmap during this BoF. I will also explain how to use it and how to develop plugins for it.</p> <p>You are more than welcome also if you have any suggestions for improvements.</p> </div> Mon, 22 Aug 2011 09:56:59 +0000 slashrsm 18 at https://janezurevc.name Screencast: HTML5 <video> support with multiple files using Media Derivatives API https://janezurevc.name/screencast-html5-video-support-multiple-files-using-media-derivatives-api <span>Screencast: HTML5 <video> support with multiple files using Media Derivatives API</span> <span><span lang="" about="https://janezurevc.name/users/slashrsm" typeof="schema:Person" property="schema:name" datatype="" xml:lang="">slashrsm</span></span> <span>Tue, 02.08.2011 - 00:19</span> <div class="field field--name-body field--type-text-with-summary field--label-hidden field--item"><p>Have you seen <a href="https://janezurevc.name/screencast-derivatives-api-intro-gsoc-2011">my previous screencast</a> (Intro in Derivatives API)?</p> <p>In this screencast I show how to easily support HTML5 <video> tag on all major browsers using two derivatives of source video, created by Derivatives API. This is a sample feature. It's purpuse is to show how Media Derivatives API works and should not be used in production envirnonment.</p> <p> </p> <div class="video-wrapper"> <iframe allowfullscreen="" frameborder="0" height="410" src="https://www.youtube.com/embed/dSlSYG-9F7s" width="650"></iframe></div> <p> </p> </div> Mon, 01 Aug 2011 22:19:21 +0000 slashrsm 17 at https://janezurevc.name Screencast: Derivatives API intro (GSoC 2011) https://janezurevc.name/screencast-derivatives-api-intro-gsoc-2011 <span>Screencast: Derivatives API intro (GSoC 2011)</span> <span><span lang="" about="https://janezurevc.name/users/slashrsm" typeof="schema:Person" property="schema:name" datatype="" xml:lang="">slashrsm</span></span> <span>Tue, 02.08.2011 - 00:10</span> <div class="field field--name-body field--type-text-with-summary field--label-hidden field--item"><p>In this screencast I want to show you basic workflow with <a href="https://drupal.org/project/media_derivatives">Derivatives API</a>, my Summer of code 2011 project. Derivatives API works with <a href="https://drupal.org/project/media">Media</a> ecosystem and it's purpuse is to provide a solid and extensible framework for automated file derivations. </p> <p>You will also see how different plugins work and get an idea what should be possible to do with them.</p> <p>There is <a href="https://janezurevc.name/screencast-html5-video-support-multiple-files-using-media-derivatives-api">another screencast availible</a>, which shows how to support HTML5 <video> using Derivatives API.</p> <p> </p> <div class="video-wrapper"> <iframe allowfullscreen="" frameborder="0" height="410" src="https://www.youtube.com/embed/_71d7fXyUVA" width="650"></iframe></div> <p> </p> <p><strong>Resources</strong></p> <ul><li><a href="https://drupal.org/project/media_derivatives">Derivatives API module @ d.o.</a></li> <li><a href="https://drupal.org/sandbox/slashrsm/1221262">Core workspace I use</a></li> <li><a href="https://janezurevc.name/derivatives-api-midterm-status-update">Midterm status update blog post</a></li> </ul><p><strong>How to use core workspace?</strong></p> <pre> git clone --branch 7.x https://git.drupal.org/sandbox/slashrsm/1221262.git media cd media git submodule init git submodule update drush si --db-url=mysql://root:pass@localhost:port/dbname </pre><p>This will create a complete drupal installation with Media derivavtives and it's dependencies downloaded and enabled.</p> </div> Mon, 01 Aug 2011 22:10:35 +0000 slashrsm 16 at https://janezurevc.name Derivatives API: midterm status update https://janezurevc.name/derivatives-api-midterm-status-update <span>Derivatives API: midterm status update</span> <span><span lang="" about="https://janezurevc.name/users/slashrsm" typeof="schema:Person" property="schema:name" datatype="" xml:lang="">slashrsm</span></span> <span>Mon, 11.07.2011 - 20:57</span> <div class="field field--name-body field--type-text-with-summary field--label-hidden field--item"><p>This year's <a href="https://code.google.com/soc/">Summer of code</a> has come to it's midterm evaluation, and this could also be a great opportunity to write some words <a href="https://groups.drupal.org/node/145074">about my project</a>. As I've written before, I work on Derivatives API for <a href="https://drupal.org/project/media">Media</a> ecosystem in <a href="https://drupal.org">Drupal</a> 7. </p> <p>I've been committing quite a lot of code to my sandbox and API was getting it's rough form lately, so it should be the right time to share current state of the project and my thoughts about the roadmap with the community. I'd love to get some feedback about it, since this is my first serious API project. Feel free to comment this blog post, <a href="https://groups.drupal.org/node/161419">thread on groups.drupal.org</a> or to contact me directly, if you have any thoughts about the project, you would like to share with me.</p> <p>API is absolutely not ready to be used in any type of production environment, but it definitely needs testing. It would be great, if there are engine developers, that would be prepared to implement initial support for Derivatives API. This would help API to become stable enough in a much shorter period of time. API changes are still possible, but most of the basic API should stay at least similar to how it looks now (except <em>Schedulers</em> - see next part). </p> <h2>Basic structure</h2> <p><a class="colorbox" href="https://janezurevc.name/sites/default/files/derivatives-api.png"><br /><img src="https://janezurevc.name/sites/default/files/derivatives-api.png" data-entity-type="file" data-entity-uuid="c9bdbcb4-f266-43ab-8a00-b066fba04e08" /></a></p> <p>Basic API structure is shown on image. Most important parts of API are:</p> <ul><li><strong>Engines:</strong> responsible for physical creation of derivatives. Engines are implemented as own modules. API itself does not implement any engine functionalities, it only provides hooks for them.</li> <li><strong>Rules:</strong> their responsibility is to decide, if a given file should be derivated with a given preset at a given time. Few basic rules are implemented in API itself. Hooks are provided to allow custom modules to implement own custom rules.</li> <li><strong>Triggers:</strong> triggers are executed on events, when a file's derivative should be created. API implements two basic triggers, that are executed when a file is uploaded and when a file was added to a file/media/image field. Hooks are provided, that allow other modules to provide custom triggers.</li> <li><strong>Presets:</strong> presets are responsible for configuration, that is used to create a derivative of a given file. Presets are based on <a href="https://drupal.org/project/ctools">CTools</a> export API. There is currently no UI for preset management (a preset can be created in code, though), but it is planned to implement that in a short time (see <a href="#roadmap">Roadmap</a>).</li> <li><strong>Schedulers:</strong> scheduler's responsibility is to run derivation of a file at the right time. API currently implements two basic trigger, that are executed when a file is inserted and when a file is added to a field. No hooks, that would allow customization of this behavior, are currently provided. It is, however, planned to do this in next few days (see <a href="#roadmap">Roadmap</a>). This is the only part of basic API, where I plan to do significant API changes.</li> </ul><p>Derivative is saved in <em>file_managed</em> table if successfully created.</p> <p>You are more than welcome to take a look at the code and experiment with it. It can be found in <strike>project's sandbox</strike> <a href="https://drupal.org/project/media_derivatives">module at d.o.</a>. I will provide more detailed description of each part of API in next sections.</p> <h2>Engines</h2> <p>Engines are really simple. Module that wants to be an engine, should first implement a simple info hook, that returns an array containing info about engine's capabilities:</p> <pre> function hook_media_derivatives_engine_info() { return array( 'type' => 'video', 'stream_wrappers' => array('public://', 'private://'), 'mime_types' => array('video/mp4', 'audio/*'), ); }</pre><ul><li><strong>type:</strong> type of files, that can be derivated using this engine,</li> <li><strong style="margin-top: 0px; margin-right: 0px; margin-bottom: 0px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; vertical-align: baseline; border-style: initial; border-color: initial; ">stream_wrappers:</strong> array of stream schemas, that this engine know how to deal with (optional),</li> <li><strong style="margin-top: 0px; margin-right: 0px; margin-bottom: 0px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; vertical-align: baseline; ">mime_types:</strong> array of mime types, that this engine know how to deal with (optional), wildcard '*' can be used.</li> </ul><p>There is also <em>hook_media_derivatives_engine_info_alter()</em> available. Derivation callback should be implemented, when Drupal knows about the engine:</p> <pre> function hook_media_derivatives_create_derivative($file, $derivative) { // Create derivative of a $file. Configuration preset is saved in $derivative. return $new_file; } </pre><p>This function is expected to return derivative's URI or a full file object. API will build file object, if only URI is returned.</p> <h2>Rules</h2> <p>Module that wants to implement a derivatives rule, should implement info hook:</p> <pre> function hook_media_derivatives_rules_info() { $rules = array(); $rules['example_rule'] = array( 'name' => t('Example derivation rule'), 'description' => t('In-depth description of example rule'), 'callback' => 'mymodule_myrule_callback', ); return $rules; } </pre><p>There is also <em>hook_media_derivatives_rules_info_alter()</em> available. Hook should return array of rules implemented by this module, with each element's key being a rule's machine name and value an array with human readable name, description and name of callback function. API will call this function when a rule needs to be tested. Callback function is expected to return TRUE or FALSE. File will only be processed if if all active rules return TRUE. Source file and configuration preset will be passed to callback function. Here is a simple example of a rule callback function:</p> <pre> function media_derivatives_type_support($file, $preset) { return $file->type == $preset->rules_settings['type']; } </pre><h2>Triggers</h2> <p>Info hook should be implemented to inform system about a new trigger:</p> <pre> function hook_media_derivatives_triggers_info() { $triggers = array(); $triggers['file_insert'] = array( 'name' => t('File insert derivative trigger'), 'description' => t('Derivative trigger, that will be executed when a new file is saved.'), 'validation_callbacks' => array( '_media_derivatives_file_insert_validation' ), ); return $triggers; } </pre><p>There is, once again, <em>hook_media_derivatives_triggers_info_alter()</em> available. Info hook is mostly self-explanatory. Only part, that probably needs some more attention, are optional validation functions. Names of validation callbacks should be passed in that array. Callback functions are going to be called before a derivative will be created. Validation function should return TRUE if a file should really be derivated or FALSE, if a derivation process of a given file, triggered by this trigger, should be canceled. Validation callback will get file, configuration preset and context information as arguments. Example of validation callback:</p> <pre> function _media_derivatives_field_presave_validation($file, $preset, $context) { return in_array( $context['field'], $preset->triggers_settings['field_presave_allowed_fields'] ); } </pre><p>Module should call <em>media_derivatives_create_all_derivatives()</em> or <em>media_derivatives_create_derivative()</em>, when a trigger should be executed. First function will take a file and try to create derivatives for all active presets in the system, while second will take preset as an argument and create a derivative just for that preset.</p> <pre> // Some code ... media_derivatives_create_all_derivatives($file, $trigger, $context); // Or just for a single preset media_derivatives_create_derivative($file, $preset, $trigger, $context); </pre><ul><li><strong>$file:</strong> source file file object,</li> <li><strong>$trigger:</strong> trigger's machine name as passed to info hook,</li> <li><strong>$context:</strong> context information, that will be passed to the validation callback,</li> <li><strong>$preset:</strong> configuration preset, that is to be used for this derivation process.</li> </ul><h2>Presets</h2> <p>Presets hold configuration for derivation. There can be more active presets in a system at the same time. To create a preset from code, one should first implement CTools <em>hook_ctools_plugin_api()</em>. This example should work for 95% of use cases:</p> <pre> function hook_ctools_plugin_api($owner, $api) { if ($owner == 'media_derivatives' && $api == 'media_derivatives_presets') { return array('version' => 1); } } </pre><p><em>hook_media_derivatives_presets()</em> should be implemented to actually create one or more configuration presets. Function should return an array with preset objects as it's items. Here is an example:</p> <pre> function hook_media_derivatives_presets() { $export = array(); $preset = new stdClass; $preset->api_version = 1; $preset->machine_name = 'example_preset'; $preset->rules = array('file_type', 'mime_type', 'derivatives_of_derivatives'); $preset->rules_settings = array( 'type' => 'video', 'stream_wrappers' => array('public://', 'temporary://'), ); $preset->triggers = array('field_presave'); $preset->triggers_settings = array( 'field_presave_allowed_fields' => array('field_asdfasdf'), ); $preset->settings = array( 'engine' => 'example_engine', 'scheduled_type' => MEDIA_DERIVATIVE_RUN_IMMEDIATELY, 'recursive_delete' => TRUE, ); $export['ffmpeg_ex_preset'] = $preset; return $export; } </pre><p>Definition of preset object:</p> <ul><li><strong>api_version:</strong> presets api version (currently 1),</li> <li><strong>machine_name:</strong> preset's unique machine name,</li> <li><strong>rules:</strong> rules, that need to be tested, before a file is going to be derivation using this preset,</li> <li><strong>rules_settings:</strong> settings that rules expect for itself,</li> <li><strong>triggers:</strong> array of triggers, that this preset should react upon,</li> <li><strong>triggers_settings:</strong> settings that trigger validation callbacks expect for itself,</li> <li><strong>settings:</strong> global settings, expected by API itself <ul><li><strong>engine:</strong> machine name of engine that should be used with this preset,</li> <li><strong>scheduled_type:</strong> scheduling policy. Can be MEDIA_DERIVATIVE_RUN_IMMEDIATELY (default) if encoding should be run immediately or MEDIA_DERIVATIVE_SCHEDULE if it should be run sometime in the future,</li> <li><strong>scheduled_time:</strong> timestamp - when to run encoding if scheduled in future (required if scheduled_type was set to MEDIA_DERIVATIVE_SCHEDULE).</li> <li><strong>recursive_delete:</strong> delete derivative if source file was deleted (defaults to FALSE),</li> <li><strong>user:</strong> derivative owner selection policy. Possible values: MEDIA_DERIVATIVE_OWNER_FILE - derivative will have the same owner as original file (default), MEDIA_DERIVATIVE_OWNER_DERIVATIVE - user that triggered creation of derivative will also be it's owner, MEDIA_DERIVATIVE_OWNER_STATIC - owner can be statically chosen,</li> <li><strong>user_uid:</strong> owner uid if 'user' was set to MEDIA_DERIVATIVE_OWNER_STATIC.</li> </ul></li> </ul><h2 id="roadmap">Roadmap</h2> <p>Features that are planned to be implemented in near future:</p> <ul><li>schedulers,</li> <li>live encode status information retrieval, </li> <li>non-blocking batch encoding, </li> <li>ability to delete source, when a derivative was created, </li> <li>presets management UI, </li> <li>display derivatives list for a given file, </li> <li>unmanaged derivatives,</li> <li>features support, </li> <li>views support.</li> </ul></div> Mon, 11 Jul 2011 18:57:29 +0000 slashrsm 14 at https://janezurevc.name