Adding a Secondary Root URL to WordPress Rewrites - php

I'm currently working on a project that has requirements of having multiple paths to the same contents. The project will have 4 different brands, for the sake of argument, we'll call those brand1, brand2, brand3, and brand4.
The desire is to generate rewrite rules for WordPress so that all of the following would work:
http://primaryurl.com/page-1 (Brand 1 is the base URL)
http://primaryurl.com/brand2/page-1
http://primaryurl.com/brand3/page-1
http://primaryurl.com/brand4/page-2
This would also be true of any custom post types that exists, posts, etc.
I've dug into WP_Rewrite a bit but haven't quite figured out how to solve this challenge and feel like I might just be missing something.
I believe this could be accomplished via a ton of add_rewrite_rule() calls but feel like there has to be a better way.
Thanks in advance for any advice on how to tackle this.

I wound up solving this with the following:
$brands = array( 'brand2','brand3','brand4' );
add_action( 'generate_rewrite_rules', function( $wp_rewrite ) {
global $brands;
$new_rewrite_rules = array();
foreach ($brands as $brand) {
foreach ($wp_rewrite->rules as $regex => $redirect) {
$new_rewrite_rules[$brand . '/' . $regex] = $redirect;
}
}
//All rewrite rules are expected to be set at this moment
$wp_rewrite->rules = array_merge($new_rewrite_rules, $wp_rewrite->rules);
} );

Related

How to allow/call multiple post types in wordpress

I am a newbie in coding. Can you help me this code that I got from jetpack.
function allow_my_post_types($allowed_post_types) {
$allowed_post_types[] = ‘wpdmpro’;
return $allowed_post_types;
}
add_filter( ‘rest_api_allowed_post_types’, ‘allow_my_post_types’ );
that code above was working perfectly. I allowed 'wpdmpro'
I want to call multiple post types. I want to include 'dwqa-question' and 'topic'. Please help me if I got wrong with the code that I just created because its not working after added those two post types.
function allow_my_post_types($allowed_post_types) {
$allowed_post_types[] = ‘wpdmpro’,’topic’,’dwqa-question’;
return $allowed_post_types;
}
add_filter( ‘rest_api_allowed_post_types’, ‘allow_my_post_types’ );
thank you so much for those who can help. I am just learning by myself. Thanks.
Try to add the values one by one to the array like this:
$allowed_post_types[] = ‘wpdmpro’;
$allowed_post_types[] = ’topic’;
$allowed_post_types[] = ’dwqa-question’;
Or you may find some useful solution here:
PHP Arrays
Try this
function allow_my_post_types($allowed_post_types) {
array_push($allowed_post_types,'wpdmpro','topic','dwqa-question');
return $allowed_post_types;
}
add_filter( ‘rest_api_allowed_post_types’, ‘allow_my_post_types’ );

Trying to highlight current menu item in Drupal 8 using hook_preprocess_menu

I have the below function to create active trail functionality. So if I were to have /blog as a "parent" and a post of /blog/mypost, when on mypost the blog link would show as highlighted. I don't want to have to make menu items for all the blog posts. The problem is when caching is turned on (not using settings.local.php and debug turned off) the getRequestUri isn't changing on some pages. It seems to be cached depending on the page. It works fine with page caching turned off but I'd like to get this working with caching. Is there a better way to check for the current path and apply the active class?
function mytheme_preprocess_menu(&$variables, $hook) {
if($variables['theme_hook_original'] == 'menu__main'){
$node = \Drupal::routeMatch()->getParameter('node');
if($node){
$current_path = \Drupal::request()->getRequestUri();
$items = $variables['items'];
foreach ($items as $key => $item) {
// If current path starts with a part of another path i.e. a parent, set active to li.
if (0 === strpos($current_path, $item['url']->toString())) {
// Add active link.
$variables['items'][$key]['attributes']['class'] .= ' menu-item--active-trail';
}
}
}
}
}
I've also tried putting this into a module to try and see if I can get the current path to then do the twig logic in the menu--main.twig.html template but I have the same problem.
function highlight_menu_sections_template_preprocess_default_variables_alter(&$variables) {
$variables['current_path'] = $_SERVER['REQUEST_URI'];
}
After a very long time trying all sorts of things, I found an excellent module which addresses exactly this problem. Install and go, not configuration, it just works:
https://www.drupal.org/project/menu_trail_by_path
Stable versions for D7 and D8.
I tried declaring an active path as part of a custom menu block, and even then my declared trail gets cached. Assuming it's related to the "There is no way to set the active link - override the service if you need more control." statement in this changelog, though why MenuTreeParameters->setActiveTrail() exists is anybody's guess.
For the curious (and for me when I search for this later!), here's my block's build() function:
public function build() {
$menu_tree = \Drupal::menuTree();
$parameters = new MenuTreeParameters();
$parameters->setRoot('menu_link_content:700c69e6-785b-4db7-be49-73188b47b5a3')->setMinDepth(1)->setMaxDepth(1)->onlyEnabledLinks();
// An array of routes and menu_link_content ids to set as active
$define_active_mlid = array(
'view.press_releases.page_1' => 385
);
$route_name = \Drupal::request()->get(RouteObjectInterface::ROUTE_NAME);
if (array_key_exists($route_name, $define_active_mlid)) {
$menu_link = \Drupal::entityTypeManager()->getStorage('menu_link_content')->loadByProperties(array('id' => $define_active_mlid[$route_name]));
$link = array_shift($menu_link);
$parameters->setActiveTrail(array('menu_link_content:' . $link->uuid()));
}
$footer_tree = $menu_tree->load('footer', $parameters);
$manipulators = array(
array('callable' => 'menu.default_tree_manipulators:checkAccess'),
array('callable' => 'menu.default_tree_manipulators:generateIndexAndSort'),
);
$tree = $menu_tree->transform($footer_tree, $manipulators);
$menu = $menu_tree->build($tree);
return array(
'menu' => $menu,
);
}
[adding a new answer since this is a completely different approach than my earlier one]
If a CSS-based solution is acceptable, this seems to work okay:
.page-node-type-press-release {
a[data-drupal-link-system-path="press-room/press-releases"] {
// active CSS styles here
}
}

Joomla router.php - custom urls

I have been spending quiet some time figuring out how this works - so thought lets ask the question here.
I do understand how to customize URL's in Joomla with the help of router.php - at least I thought so. It is simple to create something like this
domain.com/country/id
example:
domain.com/germany/12
However, you wouldn't know that the id stands for a city. So in this example lets assume the city with id 12 is Berlin.
So for my custom component (named: countries) I would like that the following is displayed:
for view=countries (1st level)
domain.com/country
i.e.:
domain.com/germany
for view=city (2nd level)
domain.com/country/city-id
i.e.:
domain.com/country/berlin-12
(or perhaps just: domain.com/country/berlin - but I think the ID is required for the custom component to work - and any related modules on the page that read the ID to know what to do)
What do I have so far:
function CountriesBuildRoute(&$query)
{
$segments = array();
//if(isset($query['view'])) {
// $segments[] = $query['view'];
// unset( $query['view'] );
//}
if (isset($query['task'])) {
$segments[] = implode('/',explode('.',$query['task']));
unset($query['task']);
}
if (isset($query['id'])) {
$segments[] = $query['id'];
unset($query['id']);
}
if (isset($query['name'])) {
$segments[] = $query['name'];
unset($query['name']);
}
unset( $query['view'] );
return $segments;
}
function CountriesParseRoute( $segments )
{
$vars = array();
$app =& JFactory::getApplication();
$menu =& $app->getMenu();
$item =& $menu->getActive();
// Count segments
$count = count( $segments );
//Handle View and Identifier
switch( $item->query['view'] )
{
case 'countries':
if($count == 1) {
$vars['view'] = 'city';
}
break;
case 'city':
$id = explode( ':', $segments[$count-2] );
$name = explode( ':', $segments[$count-1] );
$vars['id'] = $id[0].'-'.$name;
break;
}
return $vars;
}
The way I am calling city pages from view countries is the following:
<a href="<?php echo JRoute::_('index.php?option=com_countries&view=city&id=' . (int)$item->id) .'&name='. $item->city_name; ?>">
Would be amazing if someone can help ! Cheers
If you want to get ride of IDs from urls you will have to add every country menu item or create rooter that will search for item id within database (bad idea with big websites). This will also require setting your homepage to one of your component views. Its easiest way.
When you build router you need two functions. First that will return SEF url CountriesBuildRoute and second that will translate SEF url back to query CountriesParseRoute. It is harder then you actually think to write SEF at this level. I will not write you whole router but only point you to right direction.
In Joomla 1.5 it was easier to make smth you want. If you have time look in rooter from some Joomla 1.5 component like (com_weblinks). CountriesBuildRoute returns array that will build your URL. For example when you return $query array looking like this: array('country','berlin') url will look like you want: domain.com/country/berlin. But reversing that process (something you will do in CountriesParseRoute) gonna be harder. You will have to check if first segment is a country (if it is second should be city).
So in function CountriesBuildRoute check what view is passed and build $segments array directly like you want for your url or selected view to be. Remember that single element from that array will be single segment from URL.
In function CountriesParseRoute check if first array element is a country (db checking, cached countries list, there are many ways to do it) then you will have to do the same with second element from array(if it exists).
I always created BuildRoute first as I wanted. Then spend hours on making parse route as precise and effective as only could be. You can spend hours or even few days if you want to make good router.

I need chapter numbers in a WordPress Loop

I tried to solve something but struggling the whole morning.
I have my WordPress posts already in the state that they can have a parent post.
done by:
add_action('init', 'add_hierarchy_to_posts');
function add_hierarchy_to_posts() {
add_post_type_support( 'post', 'page-attributes' );
$obj = get_post_type_object( 'post' );
$obj->hierarchical =true;
remove_theme_support( 'post-formats' );
}
I need my post numerized in chapters so thats
1. Introduction
2. Subject is great
2.1 why great
2.2 why subject
2.2.1 better
2.2.2 worse
2.2.2.1 in best case
3. End
The problem is now, how to count subchapters.
The function is here so far, and it produces at least1.02.03.03.13.2
global $chapter,$subchapter,$subchapter1,$subchapter2,$depper;
function is_child_of($postID) {
global $post;
$ico=$post->post_parent;
return $ico;
}
function find_out_chapter_number($id){
global $chapter,$subchapter,$subchapter1,$subchapter2,$subchapter3,$depper;
if(is_child_of($id)==0){
$chapter++;
$subchapter=0;
}
else if(is_child_of($id)==$depper){
$subchapter++;
}
$depper=$id;
$ico=is_child_of($id);
//$id. " - ".$ico." - ".
return $chapter.".".$subchapter.".".$subchapter1.".".$subchapter2;
}
The $depper variable stores the post id before.
I need it deeper and I thought its maybe something with recursion but I don't know.
The function is called from the wordpress loop with$kapitel = find_out_chapter_number(get_the_ID()); and echoed before the_title();
Please try this plugin... this will help.
Page List plugin
if you still facing the same problem. please leave your comment. i will give you another solution.

CakePHP: Redirect in routes.php

OK, I dont know if I am taking the wrong approach or not but am stuck here...
We have developed our website and we have many controllers expecting ids and special variables, links already redirecting to the controllers passing what is expected.
The new requirement is to use friendlyUrls and the idea is that instead of having:
http://domain.com/search/advanced/term:head/city:/set:show-all/sort:basic-relevance
it now reads
http://domain.com/search/head
or passing options.
http://domain.com/search/in-edinburgh-scotland/by-rating/head
My idea was to, at the beginning of the Routes.php have a simple if such as:
$friendlyUrl = $_SERVER['REQUEST_URI'];
$friendlyUrl = split('/', $friendlyUrl);
foreach ($friendlyUrl as $key => $params) {
if(empty($params)){
unset($friendlyUrl[$key]);
}
if($params == 'search'){
Router::connect('/search/*', array('plugin'=>'Search','controller' => 'Search', 'action' => 'advancedSearch', 'term'=>'head));
}elseif ($params == 'employers') {
# code...
}elseif ($params == 'employer-reviews') {
# code...
}elseif ($params == 'jobs') {
# code...
}
}
That didn't work, then I tried adding something similar in my AppController and nothing.
All in all the the thing that has to do is:
Url be in the format of: /search/{term}
Actually be redirecting to: /search/advanced/{term}/city:{optional}/set:show-all/sort:basic-relevance
URL bar to keep reading: /search/{term}
Anyone has an idea?! Thank you
You definitely want to have a look at the routing page in the book
http://book.cakephp.org/2.0/en/development/routing.html
There are tons of options there to match url patterns to pass parameters to the controllers.
Router::connect(
'/search/:term',
array('controller' => 'search', 'action' => 'advanced'),
array(
'pass' => array( 'term')
)
);
You should probably set the defaults for city & set & sort in the actions function parameters definitions:
public function advanced($term, $city='optional', $sort = 'basic'){
// your codes
}
The great thing about doing it this way, is that your $this->Html->link's will reflect the routes in the paths they generate. (reverse routing)
The routes in cake are quite powerful, you should be able to get some decent friendly urls with them. One extra thing I've used is to use a behaviour - sluggable - to generate a searchable field from the content items title - for pages / content types in the cms.
good luck!

Categories