DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Over 2 million developers have joined DZone.
Log In / Join
Refcards Trend Reports Events Over 2 million developers have joined DZone. Join Today! Thanks for visiting DZone today,
Edit Profile Manage Email Subscriptions Moderation Admin Console How to Post to DZone Article Submission Guidelines
View Profile
Sign Out
Refcards
Trend Reports
Events
Zones
Culture and Methodologies Agile Career Development Methodologies Team Management
Data Engineering AI/ML Big Data Data Databases IoT
Software Design and Architecture Cloud Architecture Containers Integration Microservices Performance Security
Coding Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks
Partner Zones AWS Cloud
by AWS Developer Relations
Culture and Methodologies
Agile Career Development Methodologies Team Management
Data Engineering
AI/ML Big Data Data Databases IoT
Software Design and Architecture
Cloud Architecture Containers Integration Microservices Performance Security
Coding
Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance
Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks
Partner Zones
AWS Cloud
by AWS Developer Relations
Building Scalable Real-Time Apps with AstraDB and Vaadin
Register Now

Trending

  • Designing a New Framework for Ephemeral Resources
  • gRPC Basics
  • What Is Retesting?
  • Meet This Year's Top Committers
  1. DZone
  2. Coding
  3. Frameworks
  4. Subdomain Linking in a Zend Framework 2 Web Application

Subdomain Linking in a Zend Framework 2 Web Application

Nikola Poša user avatar by
Nikola Poša
·
Apr. 12, 14 · Interview
Like (0)
Save
Tweet
Share
6.78K Views

Join the DZone community and get the full member experience.

Join For Free

Recently, at work, I had a requirement for serving part of the ZF2-powered website from a different, non-www sub-domain. Problem was in fact that such requirement carries need of making all the other routes absolute, because when some link to a page on the default subdomain appears on a sub-domain page, it should be directed to the default (www) sub-domain, and not the current one. So here is the overview of a solution that I came up with in order to resolve this situation.

Zend Framework 2 introduces powerful routing mechanism, providing various strategies for defining application end-points. Among others, there's a Hostname route type, which allows matching of the request hostname.

In order to setup subdomain linking for the purpose of that separate site area/module, be it a Blog, its top route should be defined as a route of a hostname type:

'router' => array(
    'routes' => array(
        'blog' => array(
            'type' => 'hostname',
            'options' => array(
                'route' => 'blog.example.com',
                'defaults' => array(
                    'controller' => 'Application\Controller\BlogController',
                    'action' => 'index',
                ),
            ),
            'may_terminate' => true,
            'child_routes' => array(
                'post' => array(
                    'type' => 'segment',
                    'options' => array(
                        'route' => '/[:slug]',
                        'constraints' => array(
                            'slug' => '[a-zA-Z0-9_-]+'
                        ),
                        'defaults' => array(
                            'action' => 'view'
                        )
                    )
                )
            )
        )
    )
)

As a result, blog and it's posts will be accessible at the blog.example.com base URL. But some other links, like for example login/register links, should still point to the default domain, for example www.example.com/login, when rendered on some blog page. In order to achieve this, my idea was to dynamically override every non-hostname routes in the system in a way that they are prefixed with the default hostname route. In order to accomplish this, first, I defined abstract route, and named it "defaultDomain":

//...
'defaultDomain' => array(
    'type' => 'hostname',
    'options' => array(
        'route' => 'www.example.com',
    ),
),
//...

Then for the override part itself, I created a delegator, a wrapper around a factory for creating Router service, which intercepts routes configuration and inflects every non-hostname route into a chain route, consisting of a default domain route and the actual route:

public function getServiceConfig()
{
    return array(
        //...
        'delegators' => array(
            'Router' => array(
                function(ServiceLocatorInterface $sm, $name, $requestedName, $callback) {
                    if (!Console::isConsole()) {
                        $config = $sm->get('Config');
                        $routes = $config['router']['routes'];

                        $defaultDomain = $routes['defaultDomain'];
                        foreach ($routes as $name => $route) {
                            if ($route['type'] != 'hostname') {
                                $routes[$name] = array(
                                    'type' => 'chain',
                                    'options' => array(
                                        'routes' => array($defaultDomain, $route),
                                        'route_plugins' => $sm->get('RoutePluginManager')
                                    )
                                );
                            }
                        }
                        unset($routes['defaultDomain']);

                        //Save changes
                        $config['router']['routes'] = $routes;
                        $sm->setAllowOverride(true);
                        $sm->setService('Config', $config);
                        $sm->setAllowOverride(false);
                    }

                    return $callback();
                }
            ),
        ),
        //...
    );
}

In practice, I coded this a little bit differently, in a separate delegator factory class, but the point should be clear. By doing this, when, for example, user/login route is requested, it will always be assembled as an absolute URL: www.example.org/user/login on every page where it is requested, because it is now defined as a chain of the default domain route and the original route.

What I liked about this approach is that it is unobtrusive, meaning that if for ever reason that Blog module should be returned to the default subdomain, there will be no need for altering any other route except one for blog pages, because name/definition of that user/login route remained the same, and was not affected by the introduction of that root, base URL route.


Web application application Framework

Opinions expressed by DZone contributors are their own.

Trending

  • Designing a New Framework for Ephemeral Resources
  • gRPC Basics
  • What Is Retesting?
  • Meet This Year's Top Committers

Comments

Partner Resources

X

ABOUT US

  • About DZone
  • Send feedback
  • Careers
  • Sitemap

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 600 Park Offices Drive
  • Suite 300
  • Durham, NC 27709
  • support@dzone.com

Let's be friends: