SlideShare una empresa de Scribd logo
1 de 125
Descargar para leer sin conexión
Introducing Assetic
  Asset Management for PHP 5.3




         March 1, 2011
@kriswallsmith

•   Symfony Guru at

•   Symfony core team member

•   Doctrine contributor

•   10+ years experience with PHP and web development

•   Open source evangelist and international speaker
OpenSky connects you with innovators,
trendsetters and tastemakers.You choose
   the ones you like and each week they
  invite you to their private online sales.
OpenSky connects you with innovators,
trendsetters and tastemakers.You choose
   the ones you like and each week they
  invite you to their private online sales.
ShopOpenSky.com

•   PHP 5.3 + Symfony2

•   MongoDB + Doctrine MongoDB ODM

•   MySQL + Doctrine2 ORM

•   Less CSS

•   jQuery
Agenda


•   !(straw man)

•   Assetic

•   Twig, Symfony2 integration
If you haven’t optimized your
frontend, you haven’t optimized
A poorly optimized frontend
     can destroy UX
…and SEO


http://googlewebmastercentral.blogspot.com/2010/04/using-site-speed-in-web-search-ranking.html
Get your assets in line.
Asset Management
Lots of awesome tools:
Lots of awesome tools:
•   CoffeeScript              •   Packer

•   Compass Framework         •   SASS

•   CSSEmbed                  •   Sprockets

•   Google Closure Compiler   •   Stylus

•   JSMin                     •   YUI Compressor

•   LESS
The ones written in PHP…
The ones written in PHP…
This is a difficult problem
Assetic makes it easy
Enough talk
# /path/to/web/js/core.php

$core = new FileAsset('/path/to/jquery.js');
$core->load();

header('Content-Type: text/javascript');
echo $core->dump();
# /path/to/web/js/core.php

$core = new AssetCollection(array(
    new FileAsset('/path/to/jquery.js'),
    new GlobAsset('/path/to/js/core/*.js'),
));
$core->load();

header('Content-Type: text/javascript');
echo $core->dump();
# /path/to/web/js/core.php

$core = new AssetCollection(array(
    new FileAsset('/path/to/jquery.js'),
    new GlobAsset('/path/to/js/core/*.js'),
));
$core->load();many files into one == fewer HTTP requests
         Merge
header('Content-Type: text/javascript');
echo $core->dump();
# /path/to/web/js/core.php

$core = new AssetCollection(array(
    new FileAsset('/path/to/jquery.js'),
    new GlobAsset('/path/to/js/core/*.js'),
), array(
    new YuiCompressorJsFilter('/path/to/yui.jar'),
));
$core->load();

header('Content-Type: text/javascript');
echo $core->dump();
# /path/to/web/js/core.php

$core = new AssetCollection(array(
    new FileAsset('/path/to/jquery.js'),
    new GlobAsset('/path/to/js/core/*.js'),
), array(
    new YuiCompressorJsFilter('/path/to/yui.jar'),
));
$core->load();
   Compress the merged asset == less data over the wire

header('Content-Type: text/javascript');
echo $core->dump();
<script src="js/core.php"></script>
Assetic is
Assets & Filters
Inspired by Python’s webassets


        https://github.com/miracle2k/webassets
Assets have lazy, mutable content
Filters act on asset contents during
         “load” and “dump”
Assets can be gathered in
       collections
A collection is an asset
Asset
Filter
Asset
Filter
Filter
Asset
Load
   Filter
   Filter
   Asset
Filter
Filter
Asset




         Dump
Filter
Filter
Asset
Asset Collection
Filter              Filter
Filter              Filter
Asset               Asset
Asset Collection   Filter
                                 Filter
     Asset Collection            Asset
Filter              Filter
Filter              Filter
Asset               Asset
                                 Filter
                                 Filter
                                 Asset
# /path/to/web/css/styles.php

$styles = new AssetCollection(
    array(new FileAsset('/path/to/main.sass')),
    array(new SassFilter())
);

header('Content-Type: text/css');
echo $styles->dump();
# /path/to/web/css/styles.php

$styles = new AssetCollection(array(
    new AssetCollection(
        array(new FileAsset('/path/to/main.sass')),
        array(new SassFilter())
    ),
    new FileAsset('/path/to/more.css'),
));

header('Content-Type: text/css');
echo $styles->dump();
# /path/to/web/css/styles.php

$styles = new AssetCollection(array(
    new AssetCollection(
        array(new FileAsset('/path/to/main.sass')),
        array(new SassFilter())
    ),
    new FileAsset('/path/to/more.css'),
), array(
    new YuiCompressorCss('/path/to/yui.jar'),
));

header('Content-Type: text/css');
echo $styles->dump();
# /path/to/web/css/styles.php

$styles = new AssetCollection(array(
    new AssetCollection(
          array(new FileAsset('/path/to/main.sass')),
          array(new SassFilter())
    ),
    new FileAsset('/path/to/more.css'),
), array(
    new YuiCompressorCss('/path/to/yui.jar'),
));
     Lazy! The filesystem isn't touched until now
header('Content-Type: text/css');
echo $styles->dump();
Basic Asset Classes

•   AssetCollection

•   AssetReference

•   FileAsset

•   GlobAsset

•   StringAsset
Core Filter Classes
•   CallablesFilter                   •   SassScssFilter

•   CoffeeScriptFilter                •   SprocketsFilter

•   CssRewriteFilter                  •   StylusFilter

•   GoogleClosureCompilerApiFilter   •   YuiCssCompressorFilter

•   GoogleClosureCompilerJarFilter   •   YuiJsCompressorFilter

•   LessFilter                        •   More to come…

•   SassSassFilter
Asset Manager
$am = new AssetManager();
$am->set('jquery',
    new FileAsset('/path/to/jquery.js'));
$plugin = new AssetCollection(array(
    new AssetReference($am, 'jquery'),
    new FileAsset('/path/to/jquery.plugin.js'),
));
$core = new AssetCollection(array(
    $jquery,
    $plugin1,
    $plugin2,
));

header('text/javascript');
echo $core->dump();
jQuery will only be included once
       $core = new AssetCollection(array(
           $jquery,
           $plugin1,
           $plugin2,
       ));

       header('text/javascript');
       echo $core->dump();
Filter Manager
$yui = new YuiCompressorJs();
$yui->setNomunge(true);

$fm = new FilterManager();
$fm->set('yui_js', $yui);
$jquery = new FileAsset('/path/to/core.js');
$jquery->ensureFilter($fm->get('yui_js'));

$core = new AssetCollection(array(
    $jquery,
    new GlobAsset('/path/to/js/core/*.js'),
));
$core->ensureFilter($fm->get('yui_js'));
jQuery will only be compressed once

   $jquery = new FileAsset('/path/to/core.js');
   $jquery->ensureFilter($fm->get('yui_js'));

   $core = new AssetCollection(array(
       $jquery,
       new GlobAsset('/path/to/js/core/*.js'),
   ));
   $core->ensureFilter($fm->get('yui_js'));
Asset Factory
# /path/to/asset_factory.php

$fm = new FilterManager();
$fm->set('coffee', new CoffeeScriptFilter());
$fm->set('closure', new GoogleClosureCompilerApi());

$factory = new AssetFactory('/path/to/web');
$factory->setFilterManager($fm);
include '/path/to/asset_factory.php';

$asset = $factory->createAsset(
    array('js/src/*.coffee'),
    array('coffee', 'closure')
);

header('Content-Type: text/javascript');
echo $asset->dump();
Debug Mode
Debugging compressed
   Javascript sucks
Mark filters for omission
in debug mode using a “?”
// new AssetFactory('/path/to/web', true);

include '/path/to/asset_factory.php';

$asset = $factory->createAsset(
    array('js/src/*.coffee'),
    array('coffee', 'closure')
);

header('Content-Type: text/javascript');
echo $asset->dump();
// new AssetFactory('/path/to/web', true);

include '/path/to/asset_factory.php';

$asset = $factory->createAsset(
    array('js/src/*.coffee'),
    array('coffee', '?closure')
);

header('Content-Type: text/javascript');
echo $asset->dump();
// new AssetFactory('/path/to/web', false);

include '/path/to/asset_factory.php';

$asset = $factory->createAsset(
    array('js/src/*.coffee'),
    array('coffee', '?closure'),
    array('debug' => true)
);

header('Content-Type: text/javascript');
echo $asset->dump();
Factory Workers
Everything passes through the
       workers’ hands
$worker = new EnsureFilterWorker(
    '/.css$/',         // the output pattern
    $fm->get('yui_css') // the filter
);

$factory = new AssetFactory('/path/to/web');
$factory->addWorker($worker);

// compressed
$factory->createAsset('css/sass/*', 'sass', array(
    'output' => 'css/*.css',
));
Good: Basic Caching
# /path/to/web/css/styles.php

$styles = new AssetCollection(
    array(new FileAsset('/path/to/main.sass')),
    array(new SassFilter())
);

echo $styles->dump();
# /path/to/web/css/styles.php

$styles = new AssetCache(new AssetCollection(
    array(new FileAsset('/path/to/main.sass')),
    array(new SassFilter())
), new FilesystemCache('/path/to/cache'));

echo $styles->dump();
# /path/to/web/css/styles.php

$styles = new AssetCache(new AssetCollection(
    array(new FileAsset('/path/to/main.sass')),
    array(new SassFilter())
), new FilesystemCache('/path/to/cache'));
          Run the filters once and cache the content

echo $styles->dump();
Better: HTTP Caching
// $core = new AssetCache(...

$mtime = gmdate('D, d M y H:i:s',
    $core->getLastModified()).' GMT';

if ($mtime == $_SERVER['HTTP_IF_MODIFIED_SINCE']) {
    header('HTTP/1.0 304 Not Modified');
    exit();
}

header('Content-Type: text/javascript');
header('Last-Modified: '.$mtime);
echo $core->dump();
Best: Static Assets
# /path/to/scripts/dump_assets.php

$am = new AssetManager();
$am->set('foo', $foo);
// etc...

$writer = new AssetWriter('/path/to/web');
$writer->writeManagerAssets($am);
Best-est:
Content Distribution Network
new AssetWriter('s3://my-bucket')
new AssetWriter('s3://my-bucket')

                 A CloudFront S3 bucket
Not Lazy Enough?
Asset Formulae and the
 Lazy Asset Manager
$asset = $factory->createAsset(
    array('js/src/*.coffee'),
    array('coffee', '?closure'),
    array('output' => 'js/*.js')
);
$formula = array(
    array('js/src/*.coffee'),
    array('coffee', '?closure'),
    array('output' => 'js/*.js')
);
$am = new LazyAssetManager($factory);
$am->setFormula('core_js', $formula);

header('Content-Type: text/javascript');
echo $am->get('core_js')->dump();
This will make more sense
    in a few minutes…
Thought…
Assets are a part of the view layer
  and should be defined there.
<!-- header.php -->

<?php foreach (assetic_javascripts(
    array('js/core.js', 'js/more.js'),
    array('?yui_js')) as $url): ?>

<script src="<?php echo $url ?>"></script>

<?php endforeach; ?>
# config/assetic.php

require_once '/path/to/assetic/functions.php';
assetic_init($factory);
Issue…
Assets defined in the view layer
must actually exist somewhere
Option Bad...
Lazily dump assets to the
      web directory
Option Good…
Eagerly dump assets to the
      web directory
Formula Loaders
$loader = new FunctionCallsFormulaLoader();
$resource = new DirectoryResource(
    '/path/to/templates',
    '/.php$/'
);

$formulae = $loader->load($resource);
$am = new LazyAssetManager($factory);
$am->setLoader('php', $loader);
$am->addResource($resource, 'php');

$writer = new AssetWriter('/path/to/web');
$writer->writeManagerAssets($am);
$am = new LazyAssetManager($factory);
$am->setLoader('php', $loader);
$am->addResource($resource, 'php');
               Expensive every time
$writer = new AssetWriter('/path/to/web');
$writer->writeManagerAssets($am);
$cache = new ConfigCache('/path/to/cache');

$loader = new CachedFormulaLoader(
    $loader,
    $cache,
    $debug
);
Twig Integration
$twig->addExtension(new AsseticExtension($factory));
{% assetic 'js/*.coffee', filter='coffee' %}
<script src="{{ asset_url }}"></script>
{% endassetic %}
<script src="assets/92429d8"></script>
{% assetic 'js/*.coffee', filter='coffee' %}
<script src="{{ asset_url }}"></script>
{% endassetic %}
{% assetic 'js/*.coffee', filter='coffee',
   output='js/*.js' %}
<script src="{{ asset_url }}"></script>
{% endassetic %}
<script src="js/92429d8.js"></script>
{% assetic 'js/*.coffee', filter='coffee',
   output='js/*.js' %}
<script src="{{ asset_url }}"></script>
{% endassetic %}
{% assetic 'js/*.coffee', filter='coffee,?closure',
   output='js/*.js', name='core_js' %}
<script src="{{ asset_url }}"></script>
{% endassetic %}
AsseticBundle
  Symfony2 integration
{% assetic filter='scss,?yui_css', output='css/all.css',
   '@MainBundle/Resources/sass/main.scss',
   '@AnotherBundle/Resources/sass/more.scss' %}
<link href="{{ asset_url }}" rel="stylesheet" />
{% endassetic %}
<link href="css/all.css" rel="stylesheet" />
{% assetic filter='scss,?yui_css', output='css/all.css',
   '@MainBundle/Resources/sass/main.scss',
   '@AnotherBundle/Resources/sass/more.scss' %}
<link href="{{ asset_url }}" rel="stylesheet" />
{% endassetic %}
{% assetic filter='scss,?yui_css', output='css/all.css',
   '@MainBundle/Resources/sass/main.scss', debug=true,
   '@AnotherBundle/Resources/sass/more.scss' %}
<link href="{{ asset_url }}" rel="stylesheet" />
{% endassetic %}
<link href="css/all_part1.css" rel="stylesheet" />
<link href="css/all_part2.css" rel="stylesheet" />
Each "leaf" asset is referenced individually

<link href="css/all_part1.css" rel="stylesheet" />
<link href="css/all_part2.css" rel="stylesheet" />
Configuration
assetic:
    debug:            %kernel.debug%
    use_controller:   %kernel.debug%
    read_from:        %kernel.root_dir%/../web
    write_to:         s3://mybucket
{# when use_controller=true #}

<script src="{{ path('assetic_foo') }}"...
# routing_dev.yml
_assetic:
    resource: .
    type:     assetic
{# when use_controller=false #}

<script src="{{ asset('js/core.js') }}"></script>
{# when use_controller=false #}

<script src="{{ asset('js/core.js') }}"></script>

                 Lots for free
The Symfony2 Assets Helper


•   Multiple asset domains

•   Cache buster
framework:
    templating:
        assets_version: 1.2.3
        assets_base_urls:
            - http://assets1.domain.com
            - http://assets2.domain.com
            - http://assets3.domain.com
            - http://assets4.domain.com
{% assetic filter='scss,?yui_css', output='css/all.css',
   '@MainBundle/Resources/sass/main.scss',
   '@AnotherBundle/Resources/sass/more.scss' %}
<link href="{{ asset_url }}" rel="stylesheet" />
{% endassetic %}
<link href="http://assets3.domain.com/css/all.css?1.2.3" ...
assetic:dump
$ php app/console assetic:dump web/
$ php app/console assetic:dump s3://my-bucket
assetic:dump --watch
  Dump static assets in the background as you develop
Questions?
http://github.com/kriswallsmith/assetic

Más contenido relacionado

La actualidad más candente

SPL: The Missing Link in Development
SPL: The Missing Link in DevelopmentSPL: The Missing Link in Development
SPL: The Missing Link in Development
jsmith92
 
Dependency Injection IPC 201
Dependency Injection IPC 201Dependency Injection IPC 201
Dependency Injection IPC 201
Fabien Potencier
 
Speed up your developments with Symfony2
Speed up your developments with Symfony2Speed up your developments with Symfony2
Speed up your developments with Symfony2
Hugo Hamon
 
PHP 5.3 Overview
PHP 5.3 OverviewPHP 5.3 Overview
PHP 5.3 Overview
jsmith92
 
Dirty Secrets of the PHP SOAP Extension
Dirty Secrets of the PHP SOAP ExtensionDirty Secrets of the PHP SOAP Extension
Dirty Secrets of the PHP SOAP Extension
Adam Trachtenberg
 
symfony on action - WebTech 207
symfony on action - WebTech 207symfony on action - WebTech 207
symfony on action - WebTech 207
patter
 

La actualidad más candente (20)

Lithium: The Framework for People Who Hate Frameworks, Tokyo Edition
Lithium: The Framework for People Who Hate Frameworks, Tokyo EditionLithium: The Framework for People Who Hate Frameworks, Tokyo Edition
Lithium: The Framework for People Who Hate Frameworks, Tokyo Edition
 
Nubilus Perl
Nubilus PerlNubilus Perl
Nubilus Perl
 
Symfony2 - WebExpo 2010
Symfony2 - WebExpo 2010Symfony2 - WebExpo 2010
Symfony2 - WebExpo 2010
 
Perl Web Client
Perl Web ClientPerl Web Client
Perl Web Client
 
Silex meets SOAP & REST
Silex meets SOAP & RESTSilex meets SOAP & REST
Silex meets SOAP & REST
 
Keeping It Small with Slim
Keeping It Small with SlimKeeping It Small with Slim
Keeping It Small with Slim
 
Electrify your code with PHP Generators
Electrify your code with PHP GeneratorsElectrify your code with PHP Generators
Electrify your code with PHP Generators
 
The Origin of Lithium
The Origin of LithiumThe Origin of Lithium
The Origin of Lithium
 
SPL: The Missing Link in Development
SPL: The Missing Link in DevelopmentSPL: The Missing Link in Development
SPL: The Missing Link in Development
 
Design Patterns avec PHP 5.3, Symfony et Pimple
Design Patterns avec PHP 5.3, Symfony et PimpleDesign Patterns avec PHP 5.3, Symfony et Pimple
Design Patterns avec PHP 5.3, Symfony et Pimple
 
Dependency Injection IPC 201
Dependency Injection IPC 201Dependency Injection IPC 201
Dependency Injection IPC 201
 
Lithium: The Framework for People Who Hate Frameworks
Lithium: The Framework for People Who Hate FrameworksLithium: The Framework for People Who Hate Frameworks
Lithium: The Framework for People Who Hate Frameworks
 
Speed up your developments with Symfony2
Speed up your developments with Symfony2Speed up your developments with Symfony2
Speed up your developments with Symfony2
 
PHP 5.3 Overview
PHP 5.3 OverviewPHP 5.3 Overview
PHP 5.3 Overview
 
Looping the Loop with SPL Iterators
Looping the Loop with SPL IteratorsLooping the Loop with SPL Iterators
Looping the Loop with SPL Iterators
 
Introducing Assetic: Asset Management for PHP 5.3
Introducing Assetic: Asset Management for PHP 5.3Introducing Assetic: Asset Management for PHP 5.3
Introducing Assetic: Asset Management for PHP 5.3
 
Dirty Secrets of the PHP SOAP Extension
Dirty Secrets of the PHP SOAP ExtensionDirty Secrets of the PHP SOAP Extension
Dirty Secrets of the PHP SOAP Extension
 
Symfony War Stories
Symfony War StoriesSymfony War Stories
Symfony War Stories
 
symfony on action - WebTech 207
symfony on action - WebTech 207symfony on action - WebTech 207
symfony on action - WebTech 207
 
Perl5i
Perl5iPerl5i
Perl5i
 

Destacado

Destacado (13)

Assetic (Zendcon)
Assetic (Zendcon)Assetic (Zendcon)
Assetic (Zendcon)
 
How kris-writes-symfony-apps-london
How kris-writes-symfony-apps-londonHow kris-writes-symfony-apps-london
How kris-writes-symfony-apps-london
 
Drupal, meet Assetic
Drupal, meet AsseticDrupal, meet Assetic
Drupal, meet Assetic
 
Assetic (OSCON)
Assetic (OSCON)Assetic (OSCON)
Assetic (OSCON)
 
The View From Inside
The View From InsideThe View From Inside
The View From Inside
 
Assetic (Symfony Live Paris)
Assetic (Symfony Live Paris)Assetic (Symfony Live Paris)
Assetic (Symfony Live Paris)
 
How Kris Writes Symfony Apps
How Kris Writes Symfony AppsHow Kris Writes Symfony Apps
How Kris Writes Symfony Apps
 
Symfony 2
Symfony 2Symfony 2
Symfony 2
 
A Practical Introduction to Symfony2
A Practical Introduction to Symfony2A Practical Introduction to Symfony2
A Practical Introduction to Symfony2
 
How Kris Writes Symfony Apps
How Kris Writes Symfony AppsHow Kris Writes Symfony Apps
How Kris Writes Symfony Apps
 
Matters of State
Matters of StateMatters of State
Matters of State
 
Symfony in the Cloud
Symfony in the CloudSymfony in the Cloud
Symfony in the Cloud
 
Love and Loss: A Symfony Security Play
Love and Loss: A Symfony Security PlayLove and Loss: A Symfony Security Play
Love and Loss: A Symfony Security Play
 

Similar a Introducing Assetic (NYPHP)

Build Your Own CMS with Apache Sling
Build Your Own CMS with Apache SlingBuild Your Own CMS with Apache Sling
Build Your Own CMS with Apache Sling
Bob Paulin
 
Bcblackpool jquery tips
Bcblackpool jquery tipsBcblackpool jquery tips
Bcblackpool jquery tips
Jack Franklin
 
ZendCon2010 The Doctrine Project
ZendCon2010 The Doctrine ProjectZendCon2010 The Doctrine Project
ZendCon2010 The Doctrine Project
Jonathan Wage
 
10 Things Every Plugin Developer Should Know (WordCamp Atlanta 2013)
10 Things Every Plugin Developer Should Know (WordCamp Atlanta 2013)10 Things Every Plugin Developer Should Know (WordCamp Atlanta 2013)
10 Things Every Plugin Developer Should Know (WordCamp Atlanta 2013)
arcware
 
Laying the proper foundation for plugin and theme development
Laying the proper foundation for plugin and theme developmentLaying the proper foundation for plugin and theme development
Laying the proper foundation for plugin and theme development
Tammy Hart
 
Aura Project for PHP
Aura Project for PHPAura Project for PHP
Aura Project for PHP
Hari K T
 

Similar a Introducing Assetic (NYPHP) (20)

Understanding backbonejs
Understanding backbonejsUnderstanding backbonejs
Understanding backbonejs
 
jQuery Makes Writing JavaScript Fun Again (for HTML5 User Group)
jQuery Makes Writing JavaScript Fun Again (for HTML5 User Group)jQuery Makes Writing JavaScript Fun Again (for HTML5 User Group)
jQuery Makes Writing JavaScript Fun Again (for HTML5 User Group)
 
eZ Publish Cluster Unleashed
eZ Publish Cluster UnleashedeZ Publish Cluster Unleashed
eZ Publish Cluster Unleashed
 
Introduction to jQuery - Barcamp London 9
Introduction to jQuery - Barcamp London 9Introduction to jQuery - Barcamp London 9
Introduction to jQuery - Barcamp London 9
 
Intro to php
Intro to phpIntro to php
Intro to php
 
WordPress for developers - phpday 2011
WordPress for developers -  phpday 2011WordPress for developers -  phpday 2011
WordPress for developers - phpday 2011
 
Styling components with JavaScript
Styling components with JavaScriptStyling components with JavaScript
Styling components with JavaScript
 
Build Your Own CMS with Apache Sling
Build Your Own CMS with Apache SlingBuild Your Own CMS with Apache Sling
Build Your Own CMS with Apache Sling
 
The Way to Theme Enlightenment
The Way to Theme EnlightenmentThe Way to Theme Enlightenment
The Way to Theme Enlightenment
 
[Coscup 2012] JavascriptMVC
[Coscup 2012] JavascriptMVC[Coscup 2012] JavascriptMVC
[Coscup 2012] JavascriptMVC
 
How to make a WordPress theme
How to make a WordPress themeHow to make a WordPress theme
How to make a WordPress theme
 
The Way to Theme Enlightenment 2017
The Way to Theme Enlightenment 2017The Way to Theme Enlightenment 2017
The Way to Theme Enlightenment 2017
 
Bcblackpool jquery tips
Bcblackpool jquery tipsBcblackpool jquery tips
Bcblackpool jquery tips
 
ZendCon2010 The Doctrine Project
ZendCon2010 The Doctrine ProjectZendCon2010 The Doctrine Project
ZendCon2010 The Doctrine Project
 
jQuery Basic API
jQuery Basic APIjQuery Basic API
jQuery Basic API
 
Doctrine For Beginners
Doctrine For BeginnersDoctrine For Beginners
Doctrine For Beginners
 
Drupal & javascript
Drupal & javascriptDrupal & javascript
Drupal & javascript
 
10 Things Every Plugin Developer Should Know (WordCamp Atlanta 2013)
10 Things Every Plugin Developer Should Know (WordCamp Atlanta 2013)10 Things Every Plugin Developer Should Know (WordCamp Atlanta 2013)
10 Things Every Plugin Developer Should Know (WordCamp Atlanta 2013)
 
Laying the proper foundation for plugin and theme development
Laying the proper foundation for plugin and theme developmentLaying the proper foundation for plugin and theme development
Laying the proper foundation for plugin and theme development
 
Aura Project for PHP
Aura Project for PHPAura Project for PHP
Aura Project for PHP
 

Último

Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers:  A Deep Dive into Serverless Spatial Data and FMECloud Frontiers:  A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
Safe Software
 
Why Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire businessWhy Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire business
panagenda
 
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
?#DUbAI#??##{{(☎️+971_581248768%)**%*]'#abortion pills for sale in dubai@
 
Architecting Cloud Native Applications
Architecting Cloud Native ApplicationsArchitecting Cloud Native Applications
Architecting Cloud Native Applications
WSO2
 

Último (20)

Apidays New York 2024 - Passkeys: Developing APIs to enable passwordless auth...
Apidays New York 2024 - Passkeys: Developing APIs to enable passwordless auth...Apidays New York 2024 - Passkeys: Developing APIs to enable passwordless auth...
Apidays New York 2024 - Passkeys: Developing APIs to enable passwordless auth...
 
DBX First Quarter 2024 Investor Presentation
DBX First Quarter 2024 Investor PresentationDBX First Quarter 2024 Investor Presentation
DBX First Quarter 2024 Investor Presentation
 
Spring Boot vs Quarkus the ultimate battle - DevoxxUK
Spring Boot vs Quarkus the ultimate battle - DevoxxUKSpring Boot vs Quarkus the ultimate battle - DevoxxUK
Spring Boot vs Quarkus the ultimate battle - DevoxxUK
 
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers:  A Deep Dive into Serverless Spatial Data and FMECloud Frontiers:  A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
 
Biography Of Angeliki Cooney | Senior Vice President Life Sciences | Albany, ...
Biography Of Angeliki Cooney | Senior Vice President Life Sciences | Albany, ...Biography Of Angeliki Cooney | Senior Vice President Life Sciences | Albany, ...
Biography Of Angeliki Cooney | Senior Vice President Life Sciences | Albany, ...
 
Polkadot JAM Slides - Token2049 - By Dr. Gavin Wood
Polkadot JAM Slides - Token2049 - By Dr. Gavin WoodPolkadot JAM Slides - Token2049 - By Dr. Gavin Wood
Polkadot JAM Slides - Token2049 - By Dr. Gavin Wood
 
Boost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdfBoost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdf
 
Artificial Intelligence Chap.5 : Uncertainty
Artificial Intelligence Chap.5 : UncertaintyArtificial Intelligence Chap.5 : Uncertainty
Artificial Intelligence Chap.5 : Uncertainty
 
Exploring Multimodal Embeddings with Milvus
Exploring Multimodal Embeddings with MilvusExploring Multimodal Embeddings with Milvus
Exploring Multimodal Embeddings with Milvus
 
AXA XL - Insurer Innovation Award Americas 2024
AXA XL - Insurer Innovation Award Americas 2024AXA XL - Insurer Innovation Award Americas 2024
AXA XL - Insurer Innovation Award Americas 2024
 
MINDCTI Revenue Release Quarter One 2024
MINDCTI Revenue Release Quarter One 2024MINDCTI Revenue Release Quarter One 2024
MINDCTI Revenue Release Quarter One 2024
 
ICT role in 21st century education and its challenges
ICT role in 21st century education and its challengesICT role in 21st century education and its challenges
ICT role in 21st century education and its challenges
 
Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024
 
"I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ..."I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ...
 
Why Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire businessWhy Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire business
 
Strategies for Landing an Oracle DBA Job as a Fresher
Strategies for Landing an Oracle DBA Job as a FresherStrategies for Landing an Oracle DBA Job as a Fresher
Strategies for Landing an Oracle DBA Job as a Fresher
 
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
 
Cyberprint. Dark Pink Apt Group [EN].pdf
Cyberprint. Dark Pink Apt Group [EN].pdfCyberprint. Dark Pink Apt Group [EN].pdf
Cyberprint. Dark Pink Apt Group [EN].pdf
 
Architecting Cloud Native Applications
Architecting Cloud Native ApplicationsArchitecting Cloud Native Applications
Architecting Cloud Native Applications
 
presentation ICT roal in 21st century education
presentation ICT roal in 21st century educationpresentation ICT roal in 21st century education
presentation ICT roal in 21st century education
 

Introducing Assetic (NYPHP)