Hacking Movable Type Training - Day 1

10,724 views
9,881 views

Published on

A series of slides presented to developers wishing to learn how to build plugins using Movable Type.

Published in: Technology, Art & Photos
6 Comments
8 Likes
Statistics
Notes
No Downloads
Views
Total views
10,724
On SlideShare
0
From Embeds
0
Number of Embeds
3
Actions
Shares
0
Downloads
80
Comments
6
Likes
8
Embeds 0
No embeds

No notes for slide

Hacking Movable Type Training - Day 1

  1. Hacking
Movable
Type A
guide
for
developers Six
Apart
Ltd. Page

  2. Developing
for
Movable
Type
in
2
Days • Day
1:
The
Basics – Plugin
Structure – The
Registry – ConfiguraEon
DirecEves – Template
Tags – Objects – Callbacks • Day
2:
Building
User
Interfaces – Menus – New
ApplicaEon
Screens – Dialogs – LisEng
Screens 2 Page

  3. Course
Prerequisites • This
course
requires
that
you
have
access
to
a
 working
Movable
Type
installa:on. • This
course
also
assumes
that
you
are
familiar
 with
basic
system
administra:on
tasks,
such
 as
copying
and
ediEng
files. • Finally,
this
course
requires
knowledge
of
the
 Perl
programming
language. Page

  4. About
Hacking • What
makes
a
good
programmer? • Use
the
source
Luke. • Copy
and
paste
is
your
friend. Page

  5. Developing
for
Movable
Type
in
2
Days • Day
1:
The
Basics ➡ Plugin
Structure – The
Registry – ConfiguraEon
DirecEves – Template
Tags – Objects – Callbacks • Day
2:
Building
User
Interfaces – Menus – New
ApplicaEon
Screens – Dialogs – LisEng
Screens 5 Page

  6. Plugin
Structure • Your
config
file – plugins/MyPlugin/config.yaml • Your
library
files – plugins/MyPlugin/lib/* • Your
templates – plugins/MyPlugin/tmpl/* • Your
staEc
images,
javascript
and
CSS
files – mt-static/plugins/MyPlugin/* Page

  7. Plugin
Structure • Other
important
files
and
directories – MyPlugin-README.txt – MyPlugin-LICENSE.txt – plugins/MyPlugin/t/* – plugins/MyPlugin/extlib/* – plugins/MyPlugin/php/* Page

  8. Plugin
Packaging • Files
that
really
help
with
the
packaging
and
 distribuEon
of
an
enEre
plugin: – Makefile.PL – MANIFEST.SKIP Page

  9. Makefile.PL use ExtUtils::MakeMaker; WriteMakefile( NAME => quot;My Plugin's Display Namequot;, VERSION => '1.1', DISTNAME => 'MyPlugin', ); Page

  10. MANIFEST.SKIP # version control bCVS (^|/). # CPAN chain files ^MANIFEST ^Makefile ^META.yml$ ^blib/ ~$ # packages .zip$ .tar.gz$ Page

  11. CreaEng
a
Plugin
Zip
File These
simple
sequence
of
commands: > perl Makefile.PL > make manifest > make zipdist Will
produce
the
perfect
MT
Plugin
zip
file: • MyPlugin‐1.1.zip Page

  12. Developing
for
Movable
Type
in
2
Days • Day
1:
The
Basics – Plugin
Structure ➡ The
Registry – ConfiguraEon
DirecEves – Template
Tags – Objects – Callbacks • Day
2:
Building
User
Interfaces – Menus – New
ApplicaEon
Screens – Dialogs – LisEng
Screens 12 Page

  13. The
Movable
Type
Registry • Movable
Type
is
a
config‐driven
applicaEon. • The
“registry”
is
where
Movable
Type
stores
its
 configuraEon. • Each
plugin
provides
a
mini‐registry
file,
config.yaml,
 that
defines
its
feature
set. • The
config.yaml
file
is
then
merged
into
Movable
 Type’s
main
registry. • Every
plugin
therefore
is
50%
configuraEon
and
50%
 code. Page

  14. config.yaml name: Fluid App id: FluidApp author_link: http://www.majordojo.com/ author_name: Byrne Reese description: This plugin provides enhanced support for Fluid. version: 0.90 plugin_link: http://www.majordojo.com/projects/mt-fluid-app.php applications: cms: methods: fluid_update: $FluidApp::FluidApp::Plugin::cms_update callbacks: MT::App::CMS::template_source.header: $FluidApp::…::Plugin::xfrm Page

  15. Yikes What
is
all
that? Page

  16. A
YAML
Primer • YAML
==
“Yet
Another
Markup
Language” • XML
AlternaEve • Less
verbose • Human
readable
and
writable Page

  17. XML
vs.
YAML <?xml version=quot;1.0quot;> <address> <first_name>Byrne</first_name> <last_name>Reese</last_name> <email>byrne@majordojo.com</email> <company> <name>Six Apart, Ltd.</name> <street_address> 548 4th Street, San Francisco, CA 94107 </street_address> </company> </address> Page

  18. XML
vs.
YAML address: first_name: Byrne last_name: Reese email: byrne@majordojo.com company: name: Six Apart, Ltd. street_address: 548 4th Street, San Francisco, CA 94107 Page

  19. Your
First
Plugin Place
this
in:
plugins/Good4Nothing/config.yaml name: Good for Nothing Plugin for Movable Type id: Good4Nothing key: Good4Nothing author_link: http://www.yourwebsite.com/ author_name: Your Name Here description: This plugin is an example plugin. version: 1.0 Page

  20. Developing
for
Movable
Type
in
2
Days • Day
1:
The
Basics – Plugin
Structure – The
Registry ➡ Configura:on
Direc:ves – Template
Tags – Objects – Callbacks • Day
2:
Building
User
Interfaces – Menus – New
ApplicaEon
Screens – Dialogs – LisEng
Screens 20 Page

  21. Adding
a
Config
DirecEve • What
is
a
configuraEon
direcEve? • When
should
you
use
a
config
direcEve? • What
are
the
alternaEves? Page

  22. Adding
a
Config
DirecEve name: Good for Nothing Plugin for Movable Type id: Good4Nothing key: Good4Nothing author_link: http://www.yourwebsite.com/ author_name: Your Name Here description: This plugin is an example plugin. version: 1.0 config_settings: MyImageURL: default: http://path.com/images/foo.jpg Page

  23. Config
DirecEve
ProperEes • Registry
properEes: – path – handler – alias Page

  24. Developing
for
Movable
Type
in
2
Days • Day
1:
The
Basics – Plugin
Structure – The
Registry – ConfiguraEon
DirecEves ➡ Template
Tags – Objects – Callbacks • Day
2:
Building
User
Interfaces – Menus – New
ApplicaEon
Screens – Dialogs – LisEng
Screens 24 Page

  25. Adding
a
Template
Tag • What
is
a
template
tag? • Where
are
template
tags
used? • What
are
the
various
types
of
template
tags? Page

  26. Adding
a
Template
Tag
‐
config.yaml name: Good for Nothing Plugin for Movable Type id: Good4Nothing key: Good4Nothing author_link: http://www.yourwebsite.com/ author_name: Your Name Here description: This plugin is an example plugin. version: 1.0 config_settings: MyImageURL: default: http://path.com/images/foo.jpg tags: function: MyImageURL: $Good4Nothing::Good4Nothing::Plugin::tag Page

  27. Adding
a
Template
Tag
‐
Handler # Good for Nothing Plugin for Movable Type # Author: Your Name Here, your.email@address.com # Copyright (C) 2008 Your Name Here # This file is licensed under the Artistic License, # or the same terms as Perl itself. package Good4Nothing::Plugin; use strict; sub tag { my ($ctx) = @_; my $cfg = $ctx->{config}; return $cfg->MyImageURL; } 1; # Every module must return true Page

  28. More
about
Template
Tags • Types
of
Tags – funcEon – block – modifiers • CondiEonal
Tags • Loops • Template
Context Page

  29. More
about
Template
Tags tags: function: 'SaySomething': $Example::Example::Plugin::SaySomething 'SayWhatever': $Example::Example::Plugin::SayWhatever block: 'LoopTenTimes': $Example::Example::Plugin::LoopTenTimes 'IfOdd?': $Example::Example::Plugin::IfOdd Page

  30. More
about
Template
Tags # Example: <mt:SaySomething> sub SaySomething { my ($ctx, $args) = @_; return quot;Somethingquot;quot;; } # Example: <mt:SayWhatever say=”Hello”> sub SayWhatever { my ($ctx, $args) = @_; # What the person passed in through the # argument 'say' my $input = $args->{'say'}; return $input; } Page

  31. More
about
Template
Tags # Example: <mt:LoopTenTimes>...</mt:LoopTenTimes> sub LoopTenTimes { my ($ctx, $args, $cond) = @_; my $out = quot;quot;; my $builder = $ctx->stash('builder'); my $tokens = $ctx->stash('tokens'); for (my $i = 1; $i <= 10; $i++) { $ctx->stash(quot;current_loop_numberquot;,$i); $out .= quot;$i * quot; . $builder->build($ctx,$tokens,$cond); } return $out; } # Example: <mt:IfOdd>do this</mt:IfOdd> sub IfOdd { my ($ctx, $args, $cond) = @_; my $num = $ctx->stash('current_loop_number'); if ($num % 2 == 0) { return 0; } else { return 1; } } Page

  32. Adding
a
Tag
Modifier • What
is
a
tag
modifier? • Example
modifiers: – <mt:block capitalize=“1”>abc</block> – <mt:block ltrim=“1”> foo</mt:block> – <mt:block regex_replace=“/foo/gi”,”bar”> foo </mt:block> – <mt:block count_words=“1”>Hello World</mt:block> Page

  33. Adding
a
Template
Tag
‐
config.yaml name: Good for Nothing Plugin for Movable Type id: Good4Nothing key: Good4Nothing author_link: http://www.yourwebsite.com/ author_name: Your Name Here description: This plugin is an example plugin. version: 1.0 config_settings: MyImageURL: default: http://path.com/images/foo.jpg tags: modifier: lolcats: $Good4Nothing::Good4Nothing::Plugin::lolcats Page

  34. Adding
a
Modifier
‐
Handler # Good for Nothing Plugin for Movable Type # Author: Your Name Here, your.email@address.com # Copyright (C) 2008 Your Name Here # This file is licensed under the Artistic License, # or the same terms as Perl itself. package Good4Nothing::Plugin; use strict; sub lolcats { my ($str, $val, $ctx) = @_; return quot;CAN I HAZ “. uc($str); } 1; # Every module must return true Page

  35. Developing
for
Movable
Type
in
2
Days • Day
1:
The
Basics – Plugin
Structure – The
Registry – ConfiguraEon
DirecEves – Template
Tags ➡ Objects – Callbacks • Day
2:
Building
User
Interfaces – Menus – New
ApplicaEon
Screens – Dialogs – LisEng
Screens 35 Page

  36. Objects
and
Data
Persistence • An
overview
of
Movable
Type
Objects – MT::Entry – MT::Comment – Etc. • Before
and
afer
a
record
is
modified
in
the
 Movable
Type
database,
an
event
is
fired. • Plugins
can
register
callbacks
for
those
events. Page

  37. About
MT
Objects • Movable
Type’s
Data
AbstracEon
Layer – Data::ObjectDriver – MT::ObjectDriver – MT::Object • Memcached
Support • Event
PropagaEon • Gegers/Segers Page

  38. InteracEng
with
MT::Objects • MT::MyObject‐>new() • $obj‐>save() • MT::MyObject‐>load($terms,
$arguments) • MT::MyObject‐>load_iter($terms,
$arguments) • $obj‐>remove($terms,
$arguments) • MT::MyObject‐>remove_all • MT::MyObject‐>count($terms) • MT::MyObject‐>exists($terms) • $obj‐>clone() Page

  39. new()
and
save() my $foo = MT::Foo->new; $foo->first_name(’Byrne'); $foo->last_name(‘Reese’); $foo->save() or die quot;Saving foo failed: quot;, $foo->errstr; Page

  40. load() my @objects = MT::Foo->load( { title => quot;Hello Worldquot;, foo => quot;barquot;, }, { sort => 'created_on', direction => 'ascend', } ); foreach my $obj (@objects) { print $obj->baz(); # do something } Page

  41. load_iter() my $iter = MT::Foo->load_iter( { title => quot;Hello Worldquot;, foo => quot;barquot;, }, { sort => 'created_on', direction => 'ascend', } ); while (my $obj = $iter->()) { print $obj->baz(); # do something } Page

  42. load
and
load_iter
OpEons • sort • direcEon • limit • lastn • offset • start_val • range • range_incl • join
 • unique Page

  43. CreaEng
Your
Own
Object • Schema
definiEon • Registering
database
indexes • Record
audiEng • Primary
keys • Meta
Data Page

  44. MT::MyObject package Example::MyObject; use strict; use base qw( MT::Object ); __PACKAGE__->install_properties({ column_defs => { 'id' => 'integer not null auto_increment', 'blog_id' => 'integer', 'some_property' => 'string(100) not null', }, audit => 1, indexes => { id => 1, }, datasource => 'myplugin_myobject', primary_key => 'id', }); Page

  45. MT::Object
Database
Data
Types • string • integer • boolean • smallint • dateEme • blob • text • float Page

  46. Extending
ExisEng
Objects • Extending
exisEng
objects • schema_version
registry
property Page

  47. Extending
ExisEng
Objects name: Example Plugin for Movable Type id: Example key: Example description: This plugin is an example plugin version: 1.0 schema_version: 2 object_types: entry: is_featured: smallint Page

  48. Extending
ExisEng
Objects • Which
then
let’s
you
do
this: use MT::Entry; my $entry = MT::Entry->load($id); $entry->is_featured(1); $entry->save; Page

  49. Developing
for
Movable
Type
in
2
Days • Day
1:
The
Basics – Plugin
Structure – The
Registry – ConfiguraEon
DirecEves – Template
Tags – Objects ➡ Callbacks • Day
2:
Building
User
Interfaces – Menus – New
ApplicaEon
Screens – Dialogs – LisEng
Screens 49 Page

  50. Movable
Type
Callbacks • Nomenclature: – Event,
Callback,
Fire,
Listening • Event
Types – Object
Level – ApplicaEon
Level – TransformaEon Page

  51. Object‐Level
Callbacks • Events: – MT::ObjectName::pre_save – MT::ObjectName::post_save – MT::ObjectName::pre_load – MT::ObjectName::post_load – MT::ObjectName::pre_remove – MT::ObjectName::pre_remove_all – MT::ObjectName::post_remove_all Page

  52. Adding
a
Callback
‐
config.yaml name: Good for Nothing Plugin for Movable Type id: Good4Nothing key: Good4Nothing author_link: http://www.yourwebsite.com/ author_name: Your Name Here description: This plugin is an example plugin. version: 1.0 callbacks: MT::Entry::pre_save: $Example::Example::Plugin::pre_save Page

  53. Adding
a
Callback
‐
Handler package Example::Plugin; use strict; sub pre_save { my ($cb, $obj) = @_; # $cb - holds a reference to the callback object # $obj - holds a reference to the object about # to be saved # do your thing if ($error) { return $cb->error(“Error Message”); } } Page

  54. Exercise:
Add
a
Callback • Your
Mission:
Add
a
record
to
the
Movable
 Type
AcEvity
Log,
just
afer
an
entry
is
saved. • About
Logging: MT->log({ message => quot;DemoPlugin: an object was saved.quot;, class => 'system', level => MT::Log::INFO() }); }); Page

  55. End
Day
1 Byrne
Reese byrne@sixapart.com Page


×