SlideShare ist ein Scribd-Unternehmen logo
1 von 85
Downloaden Sie, um offline zu lesen
Hardcore URL
Routing for WordPress
Mike Schinkel
@mikeschinkel
about.me/mikeschinkel
1
WordCamp Atlanta - March 15th, 2014
To Cover
• URLs We Love
• How Do URLs Get Routed?
• How to see your Rewrite Rules
• Review the Rewrite API Functions & Hooks
• Ways to Add Rewrite Rules
• flush_rewrite_rules( ) & generate_rewrite_rules()
• Full-control Manual URL Routing
• Link Generation: Beyond Routing
• Other Stuff we Won't Cover
4
• /products/{product_name}/details/
• Post type => 'product'
• /products/{prod_cat}/{product_name}/
• Post type => 'product',*Taxonomy ('prod_cat')*term
• /{permalink_path}/json/
• A JSON version of your post
• /comments/{year}/{monthnum}/{day}/
• Archive of all comments not related to a specific post
• /api/{api_request}/
• “Virtual” URL for Custom code
URLs We Love
11
• /{automaker}/
• Post type => 'automaker'
• /{automaker}/{model}/
• Post type => 'automaker',*Post type => 'model'
• /{user_nicename}/
• Specified user
• Other?
• Taking requests....
More URLs We Love
12
• WP Matches URL Path to a Rewrite Pattern
•Rewrite Patterns are Regular Expressions
• Example URL Path:
• /2014/03/15/hello-world/
• Matching Regular Expression
• ([0-9]{4})/([0-9]{1,2})/([0-9]{1,2})/([^/]+)(/[0-9]+)?/?$
• Rewrite Pattern:
• index.php?year=$matches[1]&monthnum=$matches[2]&
day=$matches[3]&name=$matches[4]&page=$matches[5]
• Resultant Query String:
• index.php?year=2014&monthnum=03&day=15&name=hello-world&page=
How Do URLs Get Routed?
13
index.php in Rewrite Pattern?
#ABEGINAWordPress
<IfModuleAmod_rewrite.c>
RewriteEngineAOn
RewriteBaseA/
RewriteRuleA^index.php$A1A[L]
RewriteCondA%{REQUEST_FILENAME}A!1f
RewriteCondA%{REQUEST_FILENAME}A!1d
RewriteRuleA.A/index.phpA[L]
</IfModule>
#AENDAWordPress
See: .htaccess:*
* If on IIS then web.config which has a different format.
14
• Stored in $wp1>query_vars
• Processed by WP_Query() for The Loop
The Resultant Query String
//ANotAexactlyAthis,AbutAsimilar
$query_varsA=A'year=2014&monthnum=03&day=15&name=hello1world&page=';
$query=AnewAWP_Query(A$query_varsA);
$queryA=AnewAWP_Query(Aarray(
AA'year'AAAAA=>A2014,
AA'monthnum'A=>A3,
AA'day'AAAAAA=>A15,
AA'name'AAAAA=>A'hello1world',
AA'page'AAAAA=>A'',
));
• Essentially the same as this:
15
See your Rewrite Rules
<?php
/*
A*AFilename:A/rewrite1rules.php
A*AREMEMBERATOASETAYOURAPERMALINKS!ASettingsA>APermalinks
A*/
includeA__DIR__A.A'/wp1load.php';
$rewrite_rulesA=Aget_option(A'rewrite_rules'A);
header(A'Content1type:Atext/plain;'A);
print_r(A$rewrite_rulesA);
16
Rewrite Rules, in a Table!
<?php
/*
A*AFilename:A/rewrite1rules2.phpA
A*AREMEMBERATOASETAYOURAPERMALINKS!ASettingsA>APermalinks
A*/
includeA__DIR__A.A'/wp1load.php';
$rewrite_rulesA=Aget_option(A'rewrite_rules'A);
?>
<html>
<head>
AA<title>RewriteARules</title>
AA<styleAtype="text/css">AthA{Atext1align:Aleft;A}A</style>
</head>
<body>
AA<table>
AAAA<?php
AAAAforeach(A$rewrite_rulesAasA$regexA=>A$patternA)A{
AAAAAAechoA"<tr><th>{$regex}</th><td>{$pattern}</td></tr>";
AAAA}A?>
AA</table>
</body>
</html>
17
Best Way to See Your Rulez
• Monkeyman Rewrite Analyzer
• http://wordpress.org/plugins/monkeyman-rewrite-analyzer/
18
The WordPress Rewrite API
•Rewrite API Functions
• Related Functions
•Rewrite API Hooks
• Related Hooks
19
The Rewrite API Functions
• register_post_type()* andAregister_taxonomy()*
• flush_rewrite_rules()
• add_rewrite_rule() and add_rewrite_tag()
• get_query_var()*
• register_activation_hook() andA
register_deactivation_hook()A
20
*Related functions
The Rewrite API Hooks
• 'parse_request'
• 'request'
• 'after_switch_theme'*
• 'template_redirect'*
• 'template_include'*
• 'redirect_canonical'*
• 'do_parse_request' A
• 'query_var'
21
*Related Hooks
Different Ways to Add Rules
• Adding Rewrite Rules Indirectly
• Adding Rewrite Tags & Rules
• Validating Rewritten URLs
• Adding EndPoints
• Adding Permastructs
• Adding External Rules
22
Adding Rules Indirectly
/products/{product_name}/
<?phpA//Afunctions.php
add_action(A'init',A'x_init'A);
functionAx_init()A{
AAregister_post_type(A'x_product',Aarray(
AAAA'public'A=>Atrue,
AAAA'label'A=>A__(A'Products',A'X'A),
AAAA'rewrite'A=>Aarray(
AAAAAA'with_front'A=>Afalse,
AAAAAA'slug'A=>A'products',
AAAA),
AA));
}
23
Always Remember to Flush!
flush_rewrite_rules(A$hard_or_softA)
add_action(A'init',A'x_init'A);
functionAx_init()A{
AA//ACallAregister_post_type()Ahere
AAifA(AWP_DEBUGA)A{
AAAifA(A!Afunction_exists(A'save_mod_rewrite_rules'A)A)A{
AAAAArequire_once(AABSPATHA.A'wp1admin/includes/file.php'A);
AAAAArequire_once(AABSPATHA.A'wp1admin/includes/misc.php'A);
AAA}
AAAflush_rewrite_rules(AtrueA);
AA}
}
• true (hard) - Writes changes to .htaccess/web.config
• false (soft) - Does not writes changes.
26
Flushing in a Plugin
<?php
/**
#*#Plugin#Name:#Hardcore#URLs
#*/
class#Hardcore_Urls#{
##static#function#on_load()#{
####add_action(#'init',#array(#__CLASS__,#'_init'#)#);
####register_activation_hook(#__FILE__,#array(#__CLASS__,#'_activate'#)#);
####register_deactivation_hook(#__FILE__,#array(#__CLASS__,#'_deactivate'#)#);
##}
##static#function#_init()#{
####//#Register#post#types,#taxonomies#here#
####//#Also#add#rewrite#rules,#tags,#permastructs,#etc.#here.
##}
##static#function#_activate()#{
####flush_rewrite_rules(#true#);
##}
##static#function#_deactivate()#{
####flush_rewrite_rules(#true#);
##}
}
Hardcore_Urls::on_load();
27
Flushing in a Theme
<?phpA//Afunctions.php
classAHardcore_Urls_ThemeA{
AAstaticAfunctionAon_load()A{
AAAAadd_action(A'init',Aarray(A__CLASS__,A'_init'A)A);
AAAAadd_action(A'after_switch_theme',A'_after_switch_theme'A);
AA}
AAstaticAfunctionA_init()A{
AAAA//ARegisterApostAtypes,AtaxonomiesAhereA
AAAA//AAlsoAaddArewriteArules,Atags,Apermastructs,Aetc.Ahere.
AA}
AAstaticAfunctionA_after_switch_theme()A{
AAAAflush_rewrite_rules(AtrueA);
AA}
}
Hardcore_Urls_Theme::on_load();
28
Adding Tags and Rewrite Rules
/products/{product_name}/details/
register_post_type(A'x_product',Aarray(
AA'public'A=>Atrue,
AA'label'A=>A__(A'Products',A'X'A),
AA'query_var'A=>A'x_product',
AA'rewrite'A=>Aarray(
AAAA'with_front'A=>Afalse,
AAAA'slug'A=>A'products',
AA),
));
add_rewrite_tag(A'%x_product_details%',A'details'A);
add_rewrite_rule(
AA'products/([^/]+)/details/?$',
AA'index.php?x_product=$matches[1]&'A.
AAAAAAAAAAAA'x_product_details=true',
AA'top'
);
29
Using in a Theme
<?phpAget_header();A?>
AA<divAid="primary"Aclass="content1area">
AAAA<divAid="content"Aclass="site1content"Arole="main">
AAAAAA<?php
AAAAAAAAifA(Aget_query_var(A'x_product_details'A)A)A{
AAAAAAAAAAechoA'<h2>THISAISAAAPRODUCTADETAILSAPAGE</h2>';
AAAAAAAA}
AAAAAA?>
AAAAAA<?php
AAAAAAAAwhileA(Ahave_posts()A)A:Athe_post();
AAAAAAAAAAget_template_part(A'content',Aget_post_format()A);
AAAAAAAAAAifA(Acomments_open()A||Aget_comments_number()A)A{
AAAAAAAAAAAAcomments_template();
AAAAAAAAAA}
AAAAAAAAendwhile;
AAAAAA?>
AAAA</div>
AA</div>
<?phpAget_footer();
Example:Asingle1acw14_product.php
30
Add Taxonomy Term to Post Type Slug
/products/{prod_cat}/{product_name}/
register_post_type(A'x_product',Aarray(
AA'public'A=>Atrue,
AA'label'A=>A__(A'Products',A'X'A),
AA'rewrite'A=>Aarray(
AAAA'with_front'A=>Afalse,
AAAA'slug'A=>A'products/[^/]+',
AA),
));
/products/valid1cat/{product_name}/
/products/foo1bar/{product_name}/
Except! No {prod_cat} Validation:
31
Validating {prod_cat}
add_action(#'init',#'x_init'#);
function#x_init()#{
##//#First#register#post#type#and#taxonomy#here
##add_rewrite_tag(#'%x_prod_cat%',#'([^/]+)'#);
##add_rewrite_rule(
####'products/([^/]+)/([^/]+)/?$',
####'index.php?x_prod_cat=$matches[1]&x_product=$matches[2]',
####'top'
##);
}
add_filter(#'parse_request',#'x_parse_request'#);
function#x_parse_request(#$wp#)#{
##if#(#!#empty(#$wp]>query_vars['x_prod_cat']#)#)#{
####$term_slug#=#$wp]>query_vars['x_prod_cat'];
####$query#=#new#WP_Query(#$wp]>query_vars#);
####if#(#!#has_term(#$term_slug,#'x_prod_cat',#$query]>post#)#)#{
######$wp]>query_vars#=#array(#
########'error'#####=>#404,#
########'post_type'#=>#true#
######);
######status_header(#404#);#
######nocache_headers();
####}
##}
}
/products/{prod_cat}/{product_name}/
32
More Rewrite Functions
• add_rewrite_endpoint()
• add_permastruct()
• WP_Rewrite ClassA
• $wp_rewrite1>add_external_rule()A
• generate_rewrite_rules() *
• save_mod_rewrite_rules() andA
iis7_save_url_rewrite_rules()
• get_sample_permalink() *
• redirect_guess_404_permalink()!!!
33
*Called internally byWordPress
!!! Bad Actor!
Adding an EndPoint
add_filter(A'request',A'x_request'A);
functionAx_request(A$query_varsA)A{
AAif(Aisset(A$query_vars['json']A)A)A{
AAAA$query_vars['json']A=Atrue;
AA}
AAreturnA$query_vars;
}
add_filter(A'template_redirect',A'x_template_redirect'A);
functionAx_template_redirect()A{
AAif(Aget_query_var(A'json'A)A)A{
AAAAglobalA$post;
AAAAheader(A'Content1type:Aapplication/json'A);
AAAAechoAjson_encode(A$postA);
AAAAexit;
AA}
}
/products/{product_name}/json/
34
Adding a Permastruct
add_action(A'init',A'x_init'A);
functionAx_init()A{
AA//ARegisterAotherAthingsAhere
AAadd_permastruct(A
AAAA'x_comments',A
AAAA'comments/%year%/%monthnum%/%day%',A
AAAAarray(
AAAAAA'with_front'AA=>Atrue,
AAAAAA'ep_mask'AAAAA=>AEP_NONE,
AAAAAA'paged'AAAAAAA=>Atrue,
AAAAAA'feed'AAAAAAAA=>Atrue,
AAAAAA'forcomments'A=>Afalse,
AAAAAA'walk_dirs'AAA=>Atrue,
AAAAAA'endpoints'AAA=>Atrue,
AAAA)
AA);
AA//AFlushArulesAifAWP_DEBUG
}
/comments/{year}/{monthnum}/{day}/
35
Recognizing a Permastruct
add_filter(A'parse_request',A'x_parse_request'A);
functionAx_parse_request(A$wpA)A{
AA$regexA=A'#^comments/?([019]{4}/?([019]{1,2}/?([019]{1,2}/?(.*))?)?)?$#';
AAifA(Apreg_match(A$regex,A$wp1>request,A$matchA)A)A{
AAAA$wp1>query_varsA+=Aarray(
AAAAAA'post_type'A=>Atrue,
AAAAAA'x_comments_permastruct'A=>Atrue
AAAA);
AA}
}
/comments/{year}/{monthnum}/{day}/
36
*WhyYes! That is a rather ugly regular expression!
Preparing a Special Template
add_filter(A'template_include',A'x_template_include'A);
functionAx_template_include(A$template_fileA)A{
AAglobalA$wp,A$wp_the_query;
AAif(Aget_query_var(A'x_comments_permastruct'A)A)A{
AAAA$wp_the_query1>queried_object_idA=Anull;
AAAA$wp_the_query1>queried_objectA=A$queryA=AnewAWP_Comment_Query;
AAAA$date_queryA=Aarray();
AAAAforeach(A$wp1>query_varsAasA$var_nameA=>A$var_valueA)A{
AAAAAAifA(Apreg_match(A'#^(year|monthnum|day)$#',A$var_nameA)A)A{
AAAAAAAA$date_query[]A=Aarray(A$var_nameA=>A$var_valueA);
AAAAAA}
AAAA}
AAAA$query1>commentsA=A$query1>query(Aarray(
AAAAAA'date_query'A=>A$date_query,
AAAA));
AAAAx_load_comments(Aget_stylesheet_directory()A.A'/comment.php'A);
AA}
AAreturnA$template_file;
}
/comments/{year}/{monthnum}/{day}/
37
Serving a Special Template
functionAx_load_comments(A$_template_fileA)A{
AAglobalA$post,A$wp_rewrite,A$wpdb,A$wp_version,A$wp,A$user_ID;
AAglobalA$comments,A$comment,A$wp_comment_query;
AA$wp_comment_queryA=Aget_queried_object();
AA$commentsA=A$wp_comment_query1>comments;
AA$commentA=Areset(A$commentsA);
AA$postA=Aget_post(A$comment1>comment_post_IDA);
AArequire(A$_template_fileA);
AAexit;
}
/comments/{year}/{monthnum}/{day}/
38
A Special Comment Template
<?php#//#comment.php#
get_header();#?>
<div#id="main]content"#class="main]content">
##<div#id="primary"#class="content]area">
####<div#id="content"#class="site]content"#role="main">
####<?php#if#(#count(#$comments#)#)#:
########echo#'<ul>';
########foreach(#$comments#as#$comment#):
##########$post#=#get_post(#$comment]>comment_post_ID#);
##########$url#=#get_comment_link(#$comment#);
##########$excerpt#=#get_comment_excerpt(#$comment#);
##########$date_time#=#get_comment_date()#.#'#'.#get_comment_time();
##########echo#"<li>About:#";#the_title();
##########echo#"<br>{$comment]>comment_author}#&lt;{$date_time}&gt;";
##########echo#"<br><a#href="{$url}">{$excerpt}</a><hr>";
########endforeach;
########echo#'</ul>';
######else:
########get_template_part(#'content',#'none'#);
######endif;#?>
####</div><!]]##content#]]>
##</div><!]]##primary#]]>
##<?php#get_sidebar(#'content'#);#?>
</div><!]]##main]content#]]><?php#
get_sidebar();
get_footer();
/comments/{year}/{monthnum}/{day}/
39
Rules Generated by Permastruct
/comments/{year}/{monthnum}/{day}/
40
comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/feed/(feed|rdf|rss|rss2|atom)/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&feed=$matches[4]&withcomments=1
comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/(feed|rdf|rss|rss2|atom)/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&feed=$matches[4]&withcomments=1
comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/page/?([0]9]{1,})/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&paged=$matches[4]
comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/comment]page]([0]9]{1,})/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&cpage=$matches[4]
comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/json(/(.*))?/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&json=$matches[5]
comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]
comments/([0]9]{4})/([0]9]{1,2})/feed/(feed|rdf|rss|rss2|atom)/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&feed=$matches[3]&withcomments=1
comments/([0]9]{4})/([0]9]{1,2})/(feed|rdf|rss|rss2|atom)/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&feed=$matches[3]&withcomments=1
comments/([0]9]{4})/([0]9]{1,2})/page/?([0]9]{1,})/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&paged=$matches[3]
comments/([0]9]{4})/([0]9]{1,2})/comment]page]([0]9]{1,})/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&cpage=$matches[3]
comments/([0]9]{4})/([0]9]{1,2})/json(/(.*))?/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]&json=$matches[4]
comments/([0]9]{4})/([0]9]{1,2})/?$
=>#index.php?year=$matches[1]&monthnum=$matches[2]
comments/([0]9]{4})/feed/(feed|rdf|rss|rss2|atom)/?$
=>#index.php?year=$matches[1]&feed=$matches[2]&withcomments=1
comments/([0]9]{4})/(feed|rdf|rss|rss2|atom)/?$
=>#index.php?year=$matches[1]&feed=$matches[2]&withcomments=1
comments/([0]9]{4})/page/?([0]9]{1,})/?$
=>#index.php?year=$matches[1]&paged=$matches[2]
comments/([0]9]{4})/comment]page]([0]9]{1,})/?$
=>#index.php?year=$matches[1]&cpage=$matches[2]
comments/([0]9]{4})/json(/(.*))?/?$
=>#index.php?year=$matches[1]&json=$matches[3]
comments/([0]9]{4})/?$
=>#index.php?year=$matches[1]
This was for all*true*&
A'ep_mask'A=>AEP_ALL
Adding an External Rule
/api/{whatevah}/
41
RewriteRuleA^api/?.*$A/wp1content/themes/wp38/api.phpA[QSA,L]
Adds the following to .htaccess:
add_action(A'init',A'x_init'A);
functionAx_init()A{
AAglobalA$wp_rewrite;
AA$local_pathA=Asubstr(A__DIR__A.A'/api.php',Astrlen(AABSPATHA)A);
AA$wp_rewrite1>add_external_rule(A'api/?.*$',A$local_pathA);
}
Recognizing the External Rule
/api/{whatevah}/
42
<?php
/*AFilename:Aapi.php
A*AThisAisAonlyAifAyouAneedAWordPressAloaded.
A*ATheA"/../../.."AassumesAinAaApluginAdirectory.
A*/
require(A__DIR__A.A'/../../../wp1load.php'A);
$url_pathA=A$_SERVER['REQUEST_URI'];
$requestA=Apreg_replace(A'#^/api/(.*)$#',A'$1',A
$url_pathA);
echoA"YourAAPIArequestAwas:A{$request}";
The generate_rewrite_rules() Function
43
• This is where it gets really ugly.
• This can turn your brain to mush.
• You might even switch to Drupal!
• Not really. Who'd want Drupal
if they can haz WordPress?!?
• But I digress...
44
Hooks Used During Rule Generation
45
• 'delete_option_rewrite_rules'
• 'pre_get_option_rewrite_rules'
• 'default_option_rewrite_rules'
• 'post_rewrite_rules'
• 'date_rewrite_rules'
• 'root_rewrite_rules'
• 'comments_rewrite_rules'
• 'search_rewrite_rules'
• 'author_rewrite_rules'
• 'page_rewrite_rules'
• "{$permastructname}_rewrite_rules"
• 'tag_rewrite_rules'
• 'generate_rewrite_rules'
• 'rewrite_rules_array'
For 'post_rewrite_rules'
46
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/attachment/([^/]+)/?$]#=>#index.php?attachment=$matches[1]
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/attachment/([^/]+)/trackback/?$]#=>#index.php?attachment=$matches[1]&tb=1
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/attachment/([^/]+)/feed/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?attachment=$matches[1]&feed=$matches[2]
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/attachment/([^/]+)/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?attachment=$matches[1]&feed=$matches[2]
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/attachment/([^/]+)/comment]page]([0]9]{1,})/?$]#=>#index.php?attachment=$matches[1]&cpage=$matches[2]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/([^/]+)/trackback/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&name=$matches[4]&tb=1
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/([^/]+)/feed/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&name=$matches[4]&feed=$matches[5]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/([^/]+)/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&name=$matches[4]&feed=$matches[5]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/([^/]+)/page/?([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&name=$matches[4]&paged=$matches[5]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/([^/]+)/comment]page]([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&name=$matches[4]&cpage=$matches[5]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/([^/]+)/json(/(.*))?/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&name=$matches[4]&json=$matches[6]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/([^/]+)(/[0]9]+)?/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&name=$matches[4]&page=$matches[5]
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/([^/]+)/?$]#=>#index.php?attachment=$matches[1]
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/([^/]+)/trackback/?$]#=>#index.php?attachment=$matches[1]&tb=1
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/([^/]+)/feed/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?attachment=$matches[1]&feed=$matches[2]
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/([^/]+)/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?attachment=$matches[1]&feed=$matches[2]
##[[0]9]{4}/[0]9]{1,2}/[0]9]{1,2}/[^/]+/([^/]+)/comment]page]([0]9]{1,})/?$]#=>#index.php?attachment=$matches[1]&cpage=$matches[2]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/feed/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&feed=$matches[4]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&feed=$matches[4]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/page/?([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&paged=$matches[4]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/comment]page]([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&cpage=$matches[4]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/json(/(.*))?/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&json=$matches[5]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]
##[([0]9]{4})/([0]9]{1,2})/feed/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&feed=$matches[3]
##[([0]9]{4})/([0]9]{1,2})/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&feed=$matches[3]
##[([0]9]{4})/([0]9]{1,2})/page/?([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&paged=$matches[3]
##[([0]9]{4})/([0]9]{1,2})/comment]page]([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&cpage=$matches[3]
##[([0]9]{4})/([0]9]{1,2})/json(/(.*))?/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&json=$matches[4]
##[([0]9]{4})/([0]9]{1,2})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]
##[([0]9]{4})/feed/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&feed=$matches[2]
##[([0]9]{4})/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&feed=$matches[2]
##[([0]9]{4})/page/?([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&paged=$matches[2]
##[([0]9]{4})/comment]page]([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&cpage=$matches[2]
##[([0]9]{4})/json(/(.*))?/?$]#=>#index.php?year=$matches[1]&json=$matches[3]
##[([0]9]{4})/?$]#=>#index.php?year=$matches[1]
For 'date_rewrite_rules'
47
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/feed/(feed|rdf|rss|rss2|atom)/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&feed=$matches[4]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/(feed|rdf|rss|rss2|atom)/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&feed=$matches[4]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/page/?([0]9]{1,})/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&paged=$matches[4]
##[([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]
##[([0]9]{4})/([0]9]{1,2})/feed/(feed|rdf|rss|rss2|atom)/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&feed=$matches[3]
##[([0]9]{4})/([0]9]{1,2})/(feed|rdf|rss|rss2|atom)/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&feed=$matches[3]
##[([0]9]{4})/([0]9]{1,2})/page/?([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&paged=$matches[3]
##[([0]9]{4})/([0]9]{1,2})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]
##[([0]9]{4})/feed/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&feed=$matches[2]
##[([0]9]{4})/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&feed=$matches[2]
##[([0]9]{4})/page/?([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&paged=$matches[2]
##[([0]9]{4})/?$]#=>#index.php?year=$matches[1]
For 'root_rewrite_rules'
48
AA[feed/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?&feed=$matches[1]
AA[(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?&feed=$matches[1]
AA[page/?([019]{1,})/?$]A=>Aindex.php?&paged=$matches[1]
For 'comments_rewrite_rules'
49
AA[comments/feed/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?&feed=$matches[1]&withcomments=1
AA[comments/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?&feed=$matches[1]&withcomments=1
For 'search_rewrite_rules'
50
AA[search/(.+)/feed/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?s=$matches[1]&feed=$matches[2]
AA[search/(.+)/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?s=$matches[1]&feed=$matches[2]
AA[search/(.+)/page/?([019]{1,})/?$]A=>Aindex.php?s=$matches[1]&paged=$matches[2]
AA[search/(.+)/?$]A=>Aindex.php?s=$matches[1]
For 'author_rewrite_rules'
51
AA[author/([^/]+)/feed/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?author_name=$matches[1]&feed=$matches[2]
AA[author/([^/]+)/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?author_name=$matches[1]&feed=$matches[2]
AA[author/([^/]+)/page/?([019]{1,})/?$]A=>Aindex.php?author_name=$matches[1]&paged=$matches[2]
AA[author/([^/]+)/?$]A=>Aindex.php?author_name=$matches[1]
For 'page_rewrite_rules'
52
AA[.?.+?/attachment/([^/]+)/?$]A=>Aindex.php?attachment=$matches[1]
AA[.?.+?/attachment/([^/]+)/trackback/?$]A=>Aindex.php?attachment=$matches[1]&tb=1
AA[.?.+?/attachment/([^/]+)/feed/(feed|rdf|rss|rss2|atom)/?$]A
=>Aindex.php?attachment=$matches[1]&feed=$matches[2]
AA[.?.+?/attachment/([^/]+)/(feed|rdf|rss|rss2|atom)/?$]A
=>Aindex.php?attachment=$matches[1]&feed=$matches[2]
AA[.?.+?/attachment/([^/]+)/comment1page1([019]{1,})/?$]A
=>Aindex.php?attachment=$matches[1]&cpage=$matches[2]
AA[(.?.+?)/trackback/?$]A=>Aindex.php?pagename=$matches[1]&tb=1
AA[(.?.+?)/feed/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?pagename=$matches[1]&feed=$matches[2]
AA[(.?.+?)/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?pagename=$matches[1]&feed=$matches[2]
AA[(.?.+?)/page/?([019]{1,})/?$]A=>Aindex.php?pagename=$matches[1]&paged=$matches[2]
AA[(.?.+?)/comment1page1([019]{1,})/?$]A=>Aindex.php?pagename=$matches[1]&cpage=$matches[2]
AA[(.?.+?)(/[019]+)?/?$]A=>Aindex.php?pagename=$matches[1]&page=$matches[2]
For 'category_rewrite_rules'
53
##[category/(.+?)/feed/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?category_name=$matches[1]&feed=$matches[2]
##[category/(.+?)/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?category_name=$matches[1]&feed=$matches[2]
##[category/(.+?)/page/?([0]9]{1,})/?$]#=>#index.php?category_name=$matches[1]&paged=$matches[2]
##[category/(.+?)/?$]#=>#index.php?category_name=$matches[1]
For 'post_tag_rewrite_rules'
54
AA[tag/([^/]+)/feed/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?tag=$matches[1]&feed=$matches[2]
AA[tag/([^/]+)/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?tag=$matches[1]&feed=$matches[2]
AA[tag/([^/]+)/page/?([019]{1,})/?$]A=>Aindex.php?tag=$matches[1]&paged=$matches[2]
AA[tag/([^/]+)/?$]A=>Aindex.php?tag=$matches[1]
For 'tag_rewrite_rules'
55
AA[tag/([^/]+)/feed/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?tag=$matches[1]&feed=$matches[2]
AA[tag/([^/]+)/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?tag=$matches[1]&feed=$matches[2]
AA[tag/([^/]+)/page/?([019]{1,})/?$]A=>Aindex.php?tag=$matches[1]&paged=$matches[2]
AA[tag/([^/]+)/?$]A=>Aindex.php?tag=$matches[1]
For 'post_format_rewrite_rules'
56
AA[type/([^/]+)/feed/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?post_format=$matches[1]&feed=$matches[2]
AA[type/([^/]+)/(feed|rdf|rss|rss2|atom)/?$]A=>Aindex.php?post_format=$matches[1]&feed=$matches[2]
AA[type/([^/]+)/page/?([019]{1,})/?$]A=>Aindex.php?post_format=$matches[1]&paged=$matches[2]
AA[type/([^/]+)/?$]A=>Aindex.php?post_format=$matches[1]
For 'x_comments_rewrite_rules'
57
##[comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/feed/(feed|rdf|rss|rss2|atom)/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&feed=$matches[4]&withcomments=1
##[comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/(feed|rdf|rss|rss2|atom)/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&feed=$matches[4]&withcomments=1
##[comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/page/?([0]9]{1,})/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&paged=$matches[4]
##[comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/comment]page]([0]9]{1,})/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&cpage=$matches[4]
##[comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/json(/(.*))?/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]&json=$matches[5]
##[comments/([0]9]{4})/([0]9]{1,2})/([0]9]{1,2})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&day=$matches[3]
##[comments/([0]9]{4})/([0]9]{1,2})/feed/(feed|rdf|rss|rss2|atom)/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&feed=$matches[3]&withcomments=1
##[comments/([0]9]{4})/([0]9]{1,2})/(feed|rdf|rss|rss2|atom)/?$]#
=>#index.php?year=$matches[1]&monthnum=$matches[2]&feed=$matches[3]&withcomments=1
##[comments/([0]9]{4})/([0]9]{1,2})/page/?([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&paged=$matches[3]
##[comments/([0]9]{4})/([0]9]{1,2})/comment]page]([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&cpage=$matches[3]
##[comments/([0]9]{4})/([0]9]{1,2})/json(/(.*))?/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]&json=$matches[4]
##[comments/([0]9]{4})/([0]9]{1,2})/?$]#=>#index.php?year=$matches[1]&monthnum=$matches[2]
##[comments/([0]9]{4})/feed/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&feed=$matches[2]&withcomments=1
##[comments/([0]9]{4})/(feed|rdf|rss|rss2|atom)/?$]#=>#index.php?year=$matches[1]&feed=$matches[2]&withcomments=1
##[comments/([0]9]{4})/page/?([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&paged=$matches[2]
##[comments/([0]9]{4})/comment]page]([0]9]{1,})/?$]#=>#index.php?year=$matches[1]&cpage=$matches[2]
##[comments/([0]9]{4})/json(/(.*))?/?$]#=>#index.php?year=$matches[1]&json=$matches[3]
##[comments/([0]9]{4})/?$]#=>#index.php?year=$matches[1]
Whew!
58
• I hope you never have to use any of that!
• But if you do, you are now equipped.
• (Assumed your brain didn't turn to mush.)
The*'do_parse_request'AHook
59
• This is the strong magic.
• Using 'do_parse_request' is like....
• ...getting the Glengarry Leads!!!
• Seriously! It's omni-powerful!
• But Theme/Plugin Devs beware...
• The magic might overpower you.
Context Specific URLs
60
• WordPress only supports Context Free URLs
• But we often want Context Sensitive URLs
• 'do_parse_request'Amakes it possible
• But, it's not without risk
• Plugins and Themes won't expect it
• And you can have one URL hide another
• With Great Power Comes Great Responsibility
Post Type Name in Root
/{product_name}/
61
add_filter(A'do_parse_request',A'x_do_parse_request',A10,A3A);
functionAx_do_parse_request(A$continue,A$wp,A$extra_query_varsA)A{
AAifA(A$continueA)A{
AAAA$url_pathA=Atrim(A$_SERVER['REQUEST_URI'],A'/'A);
AAAA$url_pathA=Asanitize_title_with_dashes(A$url_pathA);
AAAA$queryA=AnewAWP_Query(Aarray(
AAAAAA'name'AAAAAAAA=>A$url_path,
AAAAAA'post_type'AAA=>A'x_product',
AAAAAA'post_status'A=>A'publish',
AAAA));
AAAAifA(A1A==A$query1>found_postsA)A{
AAAAAA$wp1>query_varsA=Aarray(
AAAAAAAA'post_type'A=>A'x_product',
AAAAAAAA'x_product'A=>A$url_path,
AAAAAAAA'name'AAAAAA=>A$url_path,
AAAAAAAA'page'AAAAAA=>A'',
AAAAAA);
AAAAAA$continueA=Afalse;AA//AIMPORTANT
AAAA}
AA}
AAreturnA$continue;
}
Parent and Child Post Types
Part 1 of 3
/{product_name}/{model_name}/
62
add_filter(A'do_parse_request',A'x_do_parse_request',A10,A3A);
functionAx_do_parse_request(A$continue,A$wp,A$extra_query_varsA)A{
AAifA(A$continueA&&A!Ais_admin()A)A{
AAAA$url_pathA=Atrim(A$_SERVER['REQUEST_URI'],A'/'A);
AAAAifA(A!Aempty(A$url_pathA)A&&A'?'A!=A$url_path[0]A)A{
AAAAAA$url_path_partsA=Aarray_map(A'sanitize_title_with_dashes',Aexplode(A'/',A
$url_pathA)A);
AAAAAAswitch(Acount(A$url_path_partsA)A)A{
AAAAAAAAcaseA2:
AAAAAAAAAAifA(A$modelA=Ax_match_post_name(A'x_model',A$model_nameA=A$url_path_parts[1]A)A)A{
AAAAAAAAAAAAifA(A$productA=Ax_match_post_name(A'x_product',A$url_path_parts[0]A)A)A{
AAAAAAAAAAAAAAifA(A$model1>post_parentA==A$product1>IDA)A{
AAAAAAAAAAAAAAAAx_route_post_name(A$wp,A'x_model',A$model_nameA);
AAAAAAAAAAAAAAAA$continueA=Afalse;
AAAAAAAAAAAAAA}
AAAAAAAAAAAA}
AAAAAAAAAA}
AAAAAAAAAAbreak;
AAAAAAAAcaseA1:
AAAAAAAAAA$continueA=A!Ax_match_post_name(A'x_product',A$url_path_parts[0],A$wpA);
AAAAAAAAAAbreak;
AAAAAA}
AAAA}
AA}
AAreturnA$continue;
}
Parent and Child Post Types
Part 2 of 3
/{product_name}/{model_name}/
63
functionAx_route_post_name(A$post_type,A$post_name,A$wpA)A{
AA$wp1>query_varsA=Aarray(
AAAA'post_type'A=>A$post_type,
AAAA$post_typeAA=>A$post_name,
AAAA'name'AAAAAA=>A$post_name,
AAAA'page'AAAAAA=>A'',
AA);
}
functionAx_match_post_name(A$post_type,A$post_name,A$wpA=AfalseA)A{
AA$queryA=AnewAWP_Query(Aarray(
AAAA'name'AAAAAAAA=>A$post_name,
AAAA'post_type'AAA=>A$post_type,
AAAA'post_status'A=>A'publish',
AA));
AAifA(A(A$matchedA=A1A==A$query1>found_postsA)A&&A$wpA)A{
AAAAx_route_post_name(A$wp,A$post_type,A$post_nameA);
AA}
AAreturnA$matchedA?A$query1>postA:Afalse;
}
Parent and Child Post Types
Part 3 of 3
/{product_name}/{model_name}/
64
add_action(#'add_meta_boxes',#'x_add_meta_boxes'#);
function#x_add_meta_boxes(#$post_type#)#{
##if#(#'x_model'#==#$post_type#)#{
####add_meta_box(#'product_parent_box',#//#$id
######__(#'Parent#Product',#'X'#),######//#$title
######'x_model_parent_metabox',#########//#$callback
######'x_model',## #####################//#$post_type
######'side',###########################//#$context
######'low'## # #####################//#$priority
####);
##}
}
function#x_model_parent_metabox(#$post#)#{
##$post_type_object#=#get_post_type_object(#'x_product'#);
##$post_type_object]>hierarchical#=#true;
##wp_dropdown_pages(#array(
####'name'#=>#'parent_id',
####'post_type'#=>#'x_product',
####'selected'#=>#$post]>post_parent,
####'show_option_none'#=>#__(#'Select#a#Parent',#'X'#),
####'option_none_value'#=>#0,
##));
##$post_type_object]>hierarchical#=#false;
}
Stopping the "Helpful" Guesses
/{product_name}/{model_name}/A
=>
?post_type=x_model&p={post_id}
65
add_action(A'redirect_canonical',A'x_redirect_canonical',A10,A2A);
functionAx_redirect_canonical(A$redirect_url,A$requested_urlA)A{
AAlist(A$url,A$queryA)A=Aexplode(A'?',A"{$redirect_url}?"A);
AAifA(A$urlA==Ahome_url('/')A)A{
AAAAparse_str(A$query,A$paramsA);
AAAAifA(Aisset(A$params['post_type']A)A&&A'x_model'A==A$params['post_type']A)A{
AAAAAA//ADammit;Aredirect_guess_404_permalink()Ainterfered!ASetAitAback!!!
AAAAAA$redirect_urlA=A$requested_url;
AAAA}
AA}
AAreturnA$redirect_url;
}
Reveal the Query Vars
66
add_action(A'shutdown',A'x_shutdown'A);
functionAx_shutdown()A{
AAifA(A!Ais_admin()A)A{
AAAAglobalA$wp;
AAAAechoA'<pre><code><fontAsize="7">';
AAAAechoA'$wp1>query_vars:A';
AAAAprint_r(A$wp1>query_varsA);
AAAAechoA'</font></code></pre>';
AA}
}
Performance Optimization
67
• Cache Top N URLs in wp_options
•
In array; key=URL, value=$wp1>query_vars
• Periodically Recalculate Top N
• Even Better if using Memcache
• This is your Homework!
Warning:
May Be Incompatible
68
• Highly Custom Sites:
• A-OK
• Normal Websites or Blog:
• Plugins and themes might be incompatible
• Plugins or Themes for Distribution:
• Be very careful; this is non-standard routing
• Also...
• Very easy to create ambiguity in routing
The Dispatch Library
69
• Using URI Templates as Patterns
• Inspecting URLs by Segment
• Plan to do lots of caching
• Still PRE-ALPHA
• github.com/newclarity/dispatch
But Routing Ain't Enough
70
• Link Generation
• Allow Editing the Slug
• Changing the Permalink Sample
Generate the Link
71
add_filter(A'post_type_link',A'x_post_type_link',A10,A2A);
functionAx_post_type_link(A$post_link,A$postA)A{
AAswitchA(A$post1>post_typeA)A{
AAAAcaseA'x_product':
AAAAAA$post_linkA=Ahome_url(A"/{$post1>post_name}/"A);
AAAAAAbreak;
AAAAcaseA'x_model':
AAAAAA$product_linkA=Ax_post_type_link(Afalse,Aget_post(A$post1>post_parentA)A);
AAAAAA$post_linkA=A"{$product_link}{$post1>post_name}/";
AAAAAAbreak;
AA}
AAreturnA$post_link;
}
/{product_name}/{model_name}/
Make the Slug Editable
72
add_filter(A'post_type_link',A'x_post_type_link',A10,A3A);
functionAx_post_type_link(A$post_link,A$post,A$leavenameA=AfalseA)A{
AA$slugA=A$leavenameA?A"%{$post1>post_type}%"A:A$post1>post_name;
AAswitchA(A$post1>post_typeA)A{
AAAAcaseA'x_product':
AAAAAA$post_linkA=Ahome_url(A"/{$slug}/"A);
AAAAAAbreak;
AAAAcaseA'x_model':
AAAAAA$product_linkA=Ax_post_type_link(Afalse,Aget_post(A$post1>post_parentA)A);
AAAAAA$post_linkA=A"{$product_link}{$slug}/";
AAAAAAbreak;
AA}
AAreturnA$post_link;
}
/{product_name}/A{model_name}A/{model_name}
Changing the Sample Permalink
73
add_filter(A'post_type_link',A'x_post_type_link',A10,A3A);
functionAx_post_type_link(A$post_link,A$post,A$leavenameA=AfalseA)A{
AA$slugA=A$leavenameA?A"%{$post1>post_type}%"A:A$post1>post_name;
AAswitchA(A$post1>post_typeA)A{
AAAAcaseA'x_product':
AAAAAA$post_linkA=Ahome_url(A"/{$slug}/"A);
AAAAAAbreak;
AAAAcaseA'x_model':
AAAAAA$product_linkA=Ax_post_type_link(Afalse,Aget_post(A$post1>post_parentA)A);
AAAAAA$post_linkA=A"{$product_link}{$slug}/";
AAAAAAbreak;
AA}
AAifA(A$sampleA)A{
AAAA//ANO#CLUE#WHY#YOU'D#WANT#TO#DO#THIS...#BUT#YOU#CAN!
AAAA$post_linkA=A"11111>[A%{$post1>post_type}%A]<11111";
AA}
AAreturnA$post_link;
}
11111>[AAAAAAAAAAAAAA]<11111{model_name}
74
In Review
• How WordPress Routes URLs
• index.php and .htaccess
• That URLs ultimately create $argsAfor WP_Query()
• Rewrite Rules and how to see/test them.
• How and why to Flush Rules
• The Rewrite API Functions
• Especially add_rewrite_rule() and add_rewrite_tag()
• The Rewrite API Hooks
• Especially 'parse_request'and 'do_parse_request'
75
What We Learned Today
In Review (cont'd)
• About Endpoints, Permastructs and External Rules
• How abysmal generate_rewrite_rules() is
• All them crazii hooks when generating.
• The Strong Magic: do_parse_request
• Provides Context Sensitive URLs
• How to discover the query vars needed to route URLs
• Generating links, editing elugs and changing samples.
• And finally the logic flow for URL rewriting/routing.
76
What Else We Learned Today
About the 'x_' Prefix
See: http://nacin.com/2010/05/11/in-wordpress-prefix-everything/
24
I just used 'x_' (FOR THIS TALK, ONLY) because it was short!
25
And Stuff I Wrote for the Intro
77
• But I decided it didn't flow.
• Like how scenes gets left...
• on the cutting room floor.
• So I added to the DVD. ;-)
WordPress' URL Patterns
78
• Post & Page URL Patterns
• Archive URL Patterns
• Feed URL Patterns
• Other URL Patterns
Post & Page URL Patterns
Posts /{year}/{month}/{day}/{postname}/
Pages /{pagename}/
Hierarchical Pages /{rootname}/../{leafname}/
Custom Post Types /{post_type_slug}/{postname}/
Attachments
/{y}/{m}/{d}/attachment/{attachment}/
Attachments /{whatever}/attachment/{attachment}/Attachments
/{whatever}/{attachment}/
79
Archive URL Patterns
Tag Archive /tag/{tag}/
Category Archive /category/{category}/
Author Archive /author/{author_name}/
Search Results /search/{s}/AandA/s?={s}
Post Format Archive /type/{post_format}/
Custom Post Type Archive /{post_type_slug}/
Also Day, Month andYear Archives.
80
Feed URL Patterns
Feed* /feed/{feed|rdf|rss|rss2|atom}/
Category Feed* /category/{category}/feed/{feed_type}/
Tag Feed* /tag/{tag}/feed/{feed_type}/
Comment Feed* /comment/feed/{feed_type}/
Search Results Feed* /search/{s}/feed/{feed_type}/
Author Feed* /author/{author_name}/feed/{feed_type}/
**{feed_type}*=* Afeed,Arss,Ardf,Arss2,Aatom
Also Attachment, Post, Page, Day, Month andYear Feeds. (Why?)
81
Other URL Patterns
Robots /robots.txt
Register /{whatever}/wp1register.php
Comments /{post_url}/comment1page1{cpage}/
Trackback /{post_url}/trackback/{whatever}
And some... I’m*sure*I*forgot*about.
82
• The mapping of a URL Path of an HTTP
Request identifying the Resource on your
WordPress site for which you want an
HTTP Response to return a Representation.
• Whew! What a mouthful!
What is URL Routing?
83
• Because we want to control what
Representation is returned for a
given URL Path.
• So let’s define those terms...
Why Do We Care?
84
What is a URL Path?
• Example URL:
• http://example.com/2014/03/15/hello-world/
• The URL Path is:
• /2014/03/15/hello-world/
85
What is an HTTP Request?
It’s when you type a URL into your browser and press Enter!
86
What is a Resource?
• It’s the idea of the thing you want, the thing
located at the URL you type into your browser.
• Don’t worry, nerd types have argued over this
definition for years!
• A Representation is simply the HTML file,
image or other file you want when you enter a
URL.
87
What is an HTTP Response?
• It is what your WordPress website packages up
and sends back to your browser and is based
on the URL path you request.
88
It’s what gets downloaded when you
request a URL with your browser.
What is a Representation?
89
• So in review:
URL Routing is the mapping of a URL Path
of an HTTP Request identifying the Resource
on yourWordPress site for which you want an
HTTP Response to return a Representation.
See, That Wasn’t Hard!
90
Future Reading
• The Rewrite API:The Basics
• http://code.tutsplus.com/tutorials/the-rewrite-api-the-basics--wp-25474
• The Rewrite API: Post Types & Taxonomies
• http://code.tutsplus.com/articles/the-rewrite-api-post-types-taxonomies--wp-25488
• A (Mostly) Complete Guide to the WordPress Rewrite API
• http://o.pmg.co/a-mostly-complete-guide-to-the-wordpress-rewrite-api
• Some background on rewrite rules
• http://wordpress.stackexchange.com/a/5478/89
91
Me, in More Detail
• President, NewClarity LLC
• Boutique WordPress consulting firm with a small but expert team.
• Specialize in complex sites & vertical market products
• Offering: Back-end architecture, implementation, training, code reviews.
• 375+ Answers at WordPress Answers
• Was a founding moderator
• Have blogged at HardcoreWP.com
• Hope to find time again (doh!)
• Several "Libraries" for WordPress at github.com/newclarity
• Exo - "MVC that doesn't changeWordPress, it just makes it stronger."
• Sunrise - Code-based Forms and Fields
• Dispatch - Hardcore URL Routing forWordPress
• Contact us for more of the "Strong Magic"
• mike@newclarity.net
92
Thanks for Attending
93
May all your URLs be pretty
and may they all match
their intended patterns
Mike Schinkel
@mikeschinkel
mike@newclarity.net

Weitere ähnliche Inhalte

Was ist angesagt?

Rails 3 overview
Rails 3 overviewRails 3 overview
Rails 3 overviewYehuda Katz
 
Hooked on WordPress: WordCamp Columbus
Hooked on WordPress: WordCamp ColumbusHooked on WordPress: WordCamp Columbus
Hooked on WordPress: WordCamp ColumbusShawn Hooper
 
Oracle APEX Performance
Oracle APEX PerformanceOracle APEX Performance
Oracle APEX PerformanceScott Wesley
 
Django - 次の一歩 gumiStudy#3
Django - 次の一歩 gumiStudy#3Django - 次の一歩 gumiStudy#3
Django - 次の一歩 gumiStudy#3makoto tsuyuki
 
Action View Form Helpers - 1, Season 2
Action View Form Helpers - 1, Season 2Action View Form Helpers - 1, Season 2
Action View Form Helpers - 1, Season 2RORLAB
 
Rails 3 Beautiful Code
Rails 3 Beautiful CodeRails 3 Beautiful Code
Rails 3 Beautiful CodeGreggPollack
 
Introduction to CodeIgniter (RefreshAugusta, 20 May 2009)
Introduction to CodeIgniter (RefreshAugusta, 20 May 2009)Introduction to CodeIgniter (RefreshAugusta, 20 May 2009)
Introduction to CodeIgniter (RefreshAugusta, 20 May 2009)Michael Wales
 
Powershell to the People #suguk
Powershell to the People #sugukPowershell to the People #suguk
Powershell to the People #sugukChris McKinley
 
The effective use of Django ORM
The effective use of Django ORMThe effective use of Django ORM
The effective use of Django ORMYaroslav Muravskyi
 
Maintainable JavaScript 2012
Maintainable JavaScript 2012Maintainable JavaScript 2012
Maintainable JavaScript 2012Nicholas Zakas
 
Zend Framework 1.9 Setup & Using Zend_Tool
Zend Framework 1.9 Setup & Using Zend_ToolZend Framework 1.9 Setup & Using Zend_Tool
Zend Framework 1.9 Setup & Using Zend_ToolGordon Forsythe
 
シックス・アパート・フレームワーク
シックス・アパート・フレームワークシックス・アパート・フレームワーク
シックス・アパート・フレームワークTakatsugu Shigeta
 
Rails for Beginners - Le Wagon
Rails for Beginners - Le WagonRails for Beginners - Le Wagon
Rails for Beginners - Le WagonAlex Benoit
 
Routing 1, Season 1
Routing 1, Season 1Routing 1, Season 1
Routing 1, Season 1RORLAB
 
Satellite Apps around the Cloud: Integrating your infrastructure with JIRA St...
Satellite Apps around the Cloud: Integrating your infrastructure with JIRA St...Satellite Apps around the Cloud: Integrating your infrastructure with JIRA St...
Satellite Apps around the Cloud: Integrating your infrastructure with JIRA St...Atlassian
 
Bootstrat REST APIs with Laravel 5
Bootstrat REST APIs with Laravel 5Bootstrat REST APIs with Laravel 5
Bootstrat REST APIs with Laravel 5Elena Kolevska
 

Was ist angesagt? (20)

Django Heresies
Django HeresiesDjango Heresies
Django Heresies
 
Rails 3 overview
Rails 3 overviewRails 3 overview
Rails 3 overview
 
Hooked on WordPress: WordCamp Columbus
Hooked on WordPress: WordCamp ColumbusHooked on WordPress: WordCamp Columbus
Hooked on WordPress: WordCamp Columbus
 
Oracle APEX Performance
Oracle APEX PerformanceOracle APEX Performance
Oracle APEX Performance
 
I Love codeigniter, You?
I Love codeigniter, You?I Love codeigniter, You?
I Love codeigniter, You?
 
Django - 次の一歩 gumiStudy#3
Django - 次の一歩 gumiStudy#3Django - 次の一歩 gumiStudy#3
Django - 次の一歩 gumiStudy#3
 
ApacheCon 2005
ApacheCon 2005ApacheCon 2005
ApacheCon 2005
 
Action View Form Helpers - 1, Season 2
Action View Form Helpers - 1, Season 2Action View Form Helpers - 1, Season 2
Action View Form Helpers - 1, Season 2
 
Rails 3 Beautiful Code
Rails 3 Beautiful CodeRails 3 Beautiful Code
Rails 3 Beautiful Code
 
Introduction to CodeIgniter (RefreshAugusta, 20 May 2009)
Introduction to CodeIgniter (RefreshAugusta, 20 May 2009)Introduction to CodeIgniter (RefreshAugusta, 20 May 2009)
Introduction to CodeIgniter (RefreshAugusta, 20 May 2009)
 
Powershell to the People #suguk
Powershell to the People #sugukPowershell to the People #suguk
Powershell to the People #suguk
 
The effective use of Django ORM
The effective use of Django ORMThe effective use of Django ORM
The effective use of Django ORM
 
Silex Cheat Sheet
Silex Cheat SheetSilex Cheat Sheet
Silex Cheat Sheet
 
Maintainable JavaScript 2012
Maintainable JavaScript 2012Maintainable JavaScript 2012
Maintainable JavaScript 2012
 
Zend Framework 1.9 Setup & Using Zend_Tool
Zend Framework 1.9 Setup & Using Zend_ToolZend Framework 1.9 Setup & Using Zend_Tool
Zend Framework 1.9 Setup & Using Zend_Tool
 
シックス・アパート・フレームワーク
シックス・アパート・フレームワークシックス・アパート・フレームワーク
シックス・アパート・フレームワーク
 
Rails for Beginners - Le Wagon
Rails for Beginners - Le WagonRails for Beginners - Le Wagon
Rails for Beginners - Le Wagon
 
Routing 1, Season 1
Routing 1, Season 1Routing 1, Season 1
Routing 1, Season 1
 
Satellite Apps around the Cloud: Integrating your infrastructure with JIRA St...
Satellite Apps around the Cloud: Integrating your infrastructure with JIRA St...Satellite Apps around the Cloud: Integrating your infrastructure with JIRA St...
Satellite Apps around the Cloud: Integrating your infrastructure with JIRA St...
 
Bootstrat REST APIs with Laravel 5
Bootstrat REST APIs with Laravel 5Bootstrat REST APIs with Laravel 5
Bootstrat REST APIs with Laravel 5
 

Ähnlich wie Hardcore URL Routing for WordPress - WordCamp Atlanta 2014

Resource Routing in ExpressionEngine
Resource Routing in ExpressionEngineResource Routing in ExpressionEngine
Resource Routing in ExpressionEngineMichaelRog
 
LAB PHP Consolidated.ppt
LAB PHP Consolidated.pptLAB PHP Consolidated.ppt
LAB PHP Consolidated.pptYasirAhmad80
 
Mule soft RAML API Designing
Mule soft RAML API DesigningMule soft RAML API Designing
Mule soft RAML API DesigningRaja Reddy
 
Ruby on Rails + AngularJS + Twitter Bootstrap
Ruby on Rails + AngularJS + Twitter BootstrapRuby on Rails + AngularJS + Twitter Bootstrap
Ruby on Rails + AngularJS + Twitter BootstrapMarcio Marinho
 
Oracle APEX URLs Untangled & SEOptimized
Oracle APEX URLs Untangled & SEOptimizedOracle APEX URLs Untangled & SEOptimized
Oracle APEX URLs Untangled & SEOptimizedChristian Rokitta
 
Deploy Rails Application by Capistrano
Deploy Rails Application by CapistranoDeploy Rails Application by Capistrano
Deploy Rails Application by CapistranoTasawr Interactive
 
Lunacloud's Compute RESTful API - Programmer's Guide
Lunacloud's Compute RESTful API - Programmer's GuideLunacloud's Compute RESTful API - Programmer's Guide
Lunacloud's Compute RESTful API - Programmer's GuideLunacloud
 
Design API using RAML - basics
Design API using RAML - basicsDesign API using RAML - basics
Design API using RAML - basicskunal vishe
 
At Begin, URL Handling and REST
At Begin, URL Handling and RESTAt Begin, URL Handling and REST
At Begin, URL Handling and RESTBrian Loomis
 
Using Sinatra to Build REST APIs in Ruby
Using Sinatra to Build REST APIs in RubyUsing Sinatra to Build REST APIs in Ruby
Using Sinatra to Build REST APIs in RubyLaunchAny
 
Laravel - Website Development in Php Framework.
Laravel - Website Development in Php Framework.Laravel - Website Development in Php Framework.
Laravel - Website Development in Php Framework.SWAAM Tech
 
Super simple introduction to REST-APIs (2nd version)
Super simple introduction to REST-APIs (2nd version)Super simple introduction to REST-APIs (2nd version)
Super simple introduction to REST-APIs (2nd version)Patrick Savalle
 
Php i basic chapter 3 (syahir chaer's conflicted copy 2013-04-22)
Php i basic chapter 3 (syahir chaer's conflicted copy 2013-04-22)Php i basic chapter 3 (syahir chaer's conflicted copy 2013-04-22)
Php i basic chapter 3 (syahir chaer's conflicted copy 2013-04-22)Muhamad Al Imran
 
Php i basic chapter 3 (afifah rosli's conflicted copy 2013-04-23)
Php i basic chapter 3 (afifah rosli's conflicted copy 2013-04-23)Php i basic chapter 3 (afifah rosli's conflicted copy 2013-04-23)
Php i basic chapter 3 (afifah rosli's conflicted copy 2013-04-23)Muhamad Al Imran
 
Java colombo-deep-dive-into-jax-rs
Java colombo-deep-dive-into-jax-rsJava colombo-deep-dive-into-jax-rs
Java colombo-deep-dive-into-jax-rsSagara Gunathunga
 

Ähnlich wie Hardcore URL Routing for WordPress - WordCamp Atlanta 2014 (20)

Resource Routing in ExpressionEngine
Resource Routing in ExpressionEngineResource Routing in ExpressionEngine
Resource Routing in ExpressionEngine
 
LAB PHP Consolidated.ppt
LAB PHP Consolidated.pptLAB PHP Consolidated.ppt
LAB PHP Consolidated.ppt
 
Mule soft RAML API Designing
Mule soft RAML API DesigningMule soft RAML API Designing
Mule soft RAML API Designing
 
PHP Basic
PHP BasicPHP Basic
PHP Basic
 
Ruby on Rails + AngularJS + Twitter Bootstrap
Ruby on Rails + AngularJS + Twitter BootstrapRuby on Rails + AngularJS + Twitter Bootstrap
Ruby on Rails + AngularJS + Twitter Bootstrap
 
Oracle APEX URLs Untangled & SEOptimized
Oracle APEX URLs Untangled & SEOptimizedOracle APEX URLs Untangled & SEOptimized
Oracle APEX URLs Untangled & SEOptimized
 
Deploy Rails Application by Capistrano
Deploy Rails Application by CapistranoDeploy Rails Application by Capistrano
Deploy Rails Application by Capistrano
 
Lunacloud's Compute RESTful API - Programmer's Guide
Lunacloud's Compute RESTful API - Programmer's GuideLunacloud's Compute RESTful API - Programmer's Guide
Lunacloud's Compute RESTful API - Programmer's Guide
 
Design API using RAML - basics
Design API using RAML - basicsDesign API using RAML - basics
Design API using RAML - basics
 
At Begin, URL Handling and REST
At Begin, URL Handling and RESTAt Begin, URL Handling and REST
At Begin, URL Handling and REST
 
Using Sinatra to Build REST APIs in Ruby
Using Sinatra to Build REST APIs in RubyUsing Sinatra to Build REST APIs in Ruby
Using Sinatra to Build REST APIs in Ruby
 
Download It
Download ItDownload It
Download It
 
Laravel - Website Development in Php Framework.
Laravel - Website Development in Php Framework.Laravel - Website Development in Php Framework.
Laravel - Website Development in Php Framework.
 
Cqrs api v2
Cqrs api v2Cqrs api v2
Cqrs api v2
 
Super simple introduction to REST-APIs (2nd version)
Super simple introduction to REST-APIs (2nd version)Super simple introduction to REST-APIs (2nd version)
Super simple introduction to REST-APIs (2nd version)
 
Php i basic chapter 3 (syahir chaer's conflicted copy 2013-04-22)
Php i basic chapter 3 (syahir chaer's conflicted copy 2013-04-22)Php i basic chapter 3 (syahir chaer's conflicted copy 2013-04-22)
Php i basic chapter 3 (syahir chaer's conflicted copy 2013-04-22)
 
Php i basic chapter 3 (afifah rosli's conflicted copy 2013-04-23)
Php i basic chapter 3 (afifah rosli's conflicted copy 2013-04-23)Php i basic chapter 3 (afifah rosli's conflicted copy 2013-04-23)
Php i basic chapter 3 (afifah rosli's conflicted copy 2013-04-23)
 
Php i basic chapter 3
Php i basic chapter 3Php i basic chapter 3
Php i basic chapter 3
 
T5 Oli Aro
T5 Oli AroT5 Oli Aro
T5 Oli Aro
 
Java colombo-deep-dive-into-jax-rs
Java colombo-deep-dive-into-jax-rsJava colombo-deep-dive-into-jax-rs
Java colombo-deep-dive-into-jax-rs
 

Kürzlich hochgeladen

Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024The Digital Insurer
 
WhatsApp 9892124323 ✓Call Girls In Kalyan ( Mumbai ) secure service
WhatsApp 9892124323 ✓Call Girls In Kalyan ( Mumbai ) secure serviceWhatsApp 9892124323 ✓Call Girls In Kalyan ( Mumbai ) secure service
WhatsApp 9892124323 ✓Call Girls In Kalyan ( Mumbai ) secure servicePooja Nehwal
 
How to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected WorkerHow to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected WorkerThousandEyes
 
A Call to Action for Generative AI in 2024
A Call to Action for Generative AI in 2024A Call to Action for Generative AI in 2024
A Call to Action for Generative AI in 2024Results
 
08448380779 Call Girls In Greater Kailash - I Women Seeking Men
08448380779 Call Girls In Greater Kailash - I Women Seeking Men08448380779 Call Girls In Greater Kailash - I Women Seeking Men
08448380779 Call Girls In Greater Kailash - I Women Seeking MenDelhi Call girls
 
Exploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone ProcessorsExploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone Processorsdebabhi2
 
Developing An App To Navigate The Roads of Brazil
Developing An App To Navigate The Roads of BrazilDeveloping An App To Navigate The Roads of Brazil
Developing An App To Navigate The Roads of BrazilV3cube
 
[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdf[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdfhans926745
 
Breaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountBreaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountPuma Security, LLC
 
A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)Gabriella Davis
 
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc
 
2024: Domino Containers - The Next Step. News from the Domino Container commu...
2024: Domino Containers - The Next Step. News from the Domino Container commu...2024: Domino Containers - The Next Step. News from the Domino Container commu...
2024: Domino Containers - The Next Step. News from the Domino Container commu...Martijn de Jong
 
The 7 Things I Know About Cyber Security After 25 Years | April 2024
The 7 Things I Know About Cyber Security After 25 Years | April 2024The 7 Things I Know About Cyber Security After 25 Years | April 2024
The 7 Things I Know About Cyber Security After 25 Years | April 2024Rafal Los
 
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking MenDelhi Call girls
 
Unblocking The Main Thread Solving ANRs and Frozen Frames
Unblocking The Main Thread Solving ANRs and Frozen FramesUnblocking The Main Thread Solving ANRs and Frozen Frames
Unblocking The Main Thread Solving ANRs and Frozen FramesSinan KOZAK
 
IAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI SolutionsIAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI SolutionsEnterprise Knowledge
 
Top 5 Benefits OF Using Muvi Live Paywall For Live Streams
Top 5 Benefits OF Using Muvi Live Paywall For Live StreamsTop 5 Benefits OF Using Muvi Live Paywall For Live Streams
Top 5 Benefits OF Using Muvi Live Paywall For Live StreamsRoshan Dwivedi
 
Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024The Digital Insurer
 
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...Neo4j
 
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...apidays
 

Kürzlich hochgeladen (20)

Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024
 
WhatsApp 9892124323 ✓Call Girls In Kalyan ( Mumbai ) secure service
WhatsApp 9892124323 ✓Call Girls In Kalyan ( Mumbai ) secure serviceWhatsApp 9892124323 ✓Call Girls In Kalyan ( Mumbai ) secure service
WhatsApp 9892124323 ✓Call Girls In Kalyan ( Mumbai ) secure service
 
How to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected WorkerHow to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected Worker
 
A Call to Action for Generative AI in 2024
A Call to Action for Generative AI in 2024A Call to Action for Generative AI in 2024
A Call to Action for Generative AI in 2024
 
08448380779 Call Girls In Greater Kailash - I Women Seeking Men
08448380779 Call Girls In Greater Kailash - I Women Seeking Men08448380779 Call Girls In Greater Kailash - I Women Seeking Men
08448380779 Call Girls In Greater Kailash - I Women Seeking Men
 
Exploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone ProcessorsExploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone Processors
 
Developing An App To Navigate The Roads of Brazil
Developing An App To Navigate The Roads of BrazilDeveloping An App To Navigate The Roads of Brazil
Developing An App To Navigate The Roads of Brazil
 
[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdf[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdf
 
Breaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountBreaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path Mount
 
A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)
 
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
 
2024: Domino Containers - The Next Step. News from the Domino Container commu...
2024: Domino Containers - The Next Step. News from the Domino Container commu...2024: Domino Containers - The Next Step. News from the Domino Container commu...
2024: Domino Containers - The Next Step. News from the Domino Container commu...
 
The 7 Things I Know About Cyber Security After 25 Years | April 2024
The 7 Things I Know About Cyber Security After 25 Years | April 2024The 7 Things I Know About Cyber Security After 25 Years | April 2024
The 7 Things I Know About Cyber Security After 25 Years | April 2024
 
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
 
Unblocking The Main Thread Solving ANRs and Frozen Frames
Unblocking The Main Thread Solving ANRs and Frozen FramesUnblocking The Main Thread Solving ANRs and Frozen Frames
Unblocking The Main Thread Solving ANRs and Frozen Frames
 
IAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI SolutionsIAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI Solutions
 
Top 5 Benefits OF Using Muvi Live Paywall For Live Streams
Top 5 Benefits OF Using Muvi Live Paywall For Live StreamsTop 5 Benefits OF Using Muvi Live Paywall For Live Streams
Top 5 Benefits OF Using Muvi Live Paywall For Live Streams
 
Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024
 
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
 
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
 

Hardcore URL Routing for WordPress - WordCamp Atlanta 2014