📜 ⬆️ ⬇️

WordPress and Zend FrameWork Integration

Yes, yes, it happens.
Suppose you work in a distributed team. The designer sits somewhere in a distant mysterious country, and all that can be obtained from it is templates made for WordPress. And you need to add to the site far from trivial functionality. Touch the core WordPress you can not, and the possibilities of plug-ins do not suit you at all (maybe you lack the standard set of hooks, or maybe you just don’t like this engine, anything can happen).
The first impulse is to take a suitable engine or framework (for example, ZF), transfer the design to it and work in peace. But here is a snag, you will make a new functionality and leave the project, but the designer and support will remain. And they are not able and do not want to be able to do anything at ZF.

If you are interested in how to get out in a similar situation, I invite you under the cat.


Concept such. All non-standard functionality performs ZF, and WP only displays the result, as well as for example the content of a separate page or post. So the designer can change the frame (header, footer, etc.) for any pages, the new frame will also apply to pages from ZF. The support will, as if nothing had happened, edit static pages and news, inserting where you need links to the functionality of ZF,
')
The first step is to force WP to ask content from ZF for requests of a certain type, for example / do / account / signup /
Of course, we use the plugin system. Only here there is no hook, which will make it possible not to pull the post from wordPressa, but to call the contents through some function. If someone finds it, then tell me, please :) Therefore, we will be treacherous to use the hook that is and is called before the content is prepared.

Fortunately, http requests are parsed by the WP_Query class and the page content is prepared by the same class. WP uses one global object of this class. Without any remorse, we replace this object with our fake instance of the heir to the class WP_Query. Feel what am I leading to? Correctly, the get_posts () function will be redefined.
Personally, I first call the standard method, it will fill all global objects with standard data, pull the default page out of the database for display, in general, it's good, it would be difficult for me without it.
Then I replace the content of the default page with the result coming from ZF.

define('ZF_MARKER', 'do');

add_action('parse_request', 'zf_query_controller');

function zf_query_controller() {
parse_str($_SERVER['QUERY_STRING'], $params);

if(isset($params[ZF_MARKER])) {

global $wp_the_query;
$q = new ZF_Query();
$q->copyFrom($wp_the_query);
$zf_uri = trim($params[ ZF_MARKER ], "/ ");
$q->req_uri_zf = empty($zf_uri)? '/' : '/' . $zf_uri . '/';
$wp_the_query = $q;
}
}

class ZF_Query extends WP_Query
{
public $req_uri_original = '';
public $req_uri_zf = '';

function copyFrom(WP_Query $wp_query) {
$vars = get_object_vars($wp_query);
foreach($vars as $name => $value) {
$this->$name = $value;
}
}

function &get_posts() {
parent::get_posts();

$post_zf = array(
"ID" => 1,
"post_author" => 1,
"post_date" => '',
"post_date_gmt" => '',
"post_content" => '',
"post_title" => '',
"post_excerpt" => "",
"post_status" => "publish",
"comment_status"=> "open",
"ping_status" => "open",
"post_password" => "",
"post_name" => "",
"to_ping" => "",
"pinged" => "",
"post_modified" => "",
"post_modified_gmt"=> "",
"post_content_filtered"=> "",
"post_parent" => 0,
"guid" => "",
"menu_order" => 1,
"post_type" => ZF_MARKER,
"post_mime_type"=> "",
"comment_count" => "0",
"ancestors" => array(),
"filter" => "",
);

$tmp = $_SERVER['REQUEST_URI'];
$_SERVER['REQUEST_URI'] = $this->req_uri_zf;
$post_zf['post_content'] = require_once ABSPATH . 'zf-app/public/index.php';
$_SERVER['REQUEST_URI'] = $tmp;

global $post;
$post = (object)$post_zf;
$this->posts = array($post);
$this->post = $post;
$this->post_count = count($this->posts);
$this->current_post = 0;

$this->is_single = 1;
$this->is_page = 0;
$this->is_404 = 0;
$this->is_archive = 0;
$this->is_home = 0;

// 2 , wordPress ( 3.x) , .
global $wp_filter;
unset($wp_filter['template_redirect']);

return $this->posts;
}
}


And of course the rule for .haccess is:
RewriteRule /?do/(.*) /index.php?do=$1 [L]

It is possible without it, then the URLs for the ZF functional will be of the form /? Do = account / signup /


Also, it is necessary to change the ZF, it should not withdraw its respons, but return it.

$controller->returnResponse(true);
$resp = $application->bootstrap()->getBootstrap()->run();
return $resp->getBody();


The returned HTML is needed without the <html> and <body> tags. So disable the layout or make it primitive, such as
<?php echo $this->layout()->content ?>


Here, in general, that's all.




PS: One more thing. if you need to teach WP how to handle content from ZF especially, then you can go to the Single.php template of the theme you are using and set it in the right place.
<?php the_post(); if (ZF_MARKER == $post->post_type) : ?>
<?php echo $post->post_content;?>
<?php else:?>
...
<?php endif; ?>


This was what the lines were for:
$this->is_single = 1;
$this->is_page = 0;
$this->is_404 = 0;
$this->is_archive = 0;
$this->is_home = 0;

Source: https://habr.com/ru/post/96782/


All Articles