diff --git a/core/core.services.yml b/core/core.services.yml
index d0facb4..2f27bc3 100644
--- a/core/core.services.yml
+++ b/core/core.services.yml
@@ -19,7 +19,7 @@ services:
       - { name: cache.context}
   cache_context.theme:
     class: Drupal\Core\Cache\ThemeCacheContext
-    arguments: ['@request_stack', '@theme.negotiator']
+    arguments: ['@current_route_match', '@request_stack', '@theme.negotiator']
     tags:
       - { name: cache.context}
   cache_context.timezone:
@@ -198,7 +198,7 @@ services:
       - { name: service_collector, tag: http_client_subscriber, call: attach }
   theme.negotiator:
     class: Drupal\Core\Theme\ThemeNegotiator
-    arguments: ['@access_check.theme', '@request_stack']
+    arguments: ['@access_check.theme']
     tags:
       - { name: service_collector, tag: theme_negotiator, call: addNegotiator }
   theme.negotiator.default:
@@ -272,6 +272,9 @@ services:
     class: Symfony\Component\HttpFoundation\RequestStack
     tags:
       - { name: persist }
+  current_route_match:
+     class: Drupal\Core\Routing\CurrentRouteMatch
+     arguments: ['@request_stack']
   event_dispatcher:
     class: Symfony\Component\EventDispatcher\ContainerAwareEventDispatcher
     arguments: ['@service_container']
diff --git a/core/includes/menu.inc b/core/includes/menu.inc
index 46de223..1bc34d6 100644
--- a/core/includes/menu.inc
+++ b/core/includes/menu.inc
@@ -10,7 +10,6 @@
 use Drupal\Core\Language\Language;
 use Drupal\Core\Render\Element;
 use Drupal\Core\Template\Attribute;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 
 /**
  * @defgroup menu Menu and routing system
@@ -481,7 +480,7 @@ function menu_local_tasks($level = 0) {
     $data['tabs'] = array();
     $data['actions'] = array();
 
-    $route_name = \Drupal::request()->attributes->get(RouteObjectInterface::ROUTE_NAME);
+    $route_name = \Drupal::routeMatch()->getRouteName();
     if (!empty($route_name)) {
       $manager = \Drupal::service('plugin.manager.menu.local_task');
       $local_tasks = $manager->getTasksBuild($route_name);
@@ -536,7 +535,7 @@ function menu_secondary_local_tasks() {
  */
 function menu_get_local_actions() {
   $links = menu_local_tasks();
-  $route_name = Drupal::request()->attributes->get(RouteObjectInterface::ROUTE_NAME);
+  $route_name = Drupal::routeMatch()->getRouteName();
   $manager = \Drupal::service('plugin.manager.menu.local_action');
   return $manager->getActionsForRoute($route_name) + $links['actions'];
 }
diff --git a/core/includes/theme.inc b/core/includes/theme.inc
index 2b06429..77dcb3c 100644
--- a/core/includes/theme.inc
+++ b/core/includes/theme.inc
@@ -105,8 +105,9 @@ function drupal_theme_initialize() {
   // @todo Let the theme.negotiator listen to the kernel request event.
   // Determine the active theme for the theme negotiator service. This includes
   // the default theme as well as really specific ones like the ajax base theme.
+  $route_match = \Drupal::routeMatch();
   $request = \Drupal::request();
-  $theme = \Drupal::service('theme.negotiator')->determineActiveTheme($request);
+  $theme = \Drupal::service('theme.negotiator')->determineActiveTheme($route_match, $request);
 
   // If no theme could be negotiated, or if the negotiated theme is not within
   // the list of enabled themes, fall back to the default theme output of core
@@ -2152,7 +2153,7 @@ function template_preprocess_page(&$variables) {
     );
   }
 
-  if ($node = \Drupal::request()->attributes->get('node')) {
+  if ($node = \Drupal::routeMatch()->getParameter('node')) {
     $variables['node'] = $node;
   }
 
diff --git a/core/lib/Drupal.php b/core/lib/Drupal.php
index 83fe15f..064e3ad 100644
--- a/core/lib/Drupal.php
+++ b/core/lib/Drupal.php
@@ -188,6 +188,16 @@ public static function request() {
   }
 
   /**
+   * Retrieves the currently active route match object.
+   *
+   * @return \Drupal\Core\Routing\RouteMatchInterface
+   *   The currently active route match object.
+   */
+  public static function routeMatch() {
+    return static::$container->get('current_route_match');
+  }
+
+  /**
    * Gets the current active user.
    *
    * @return \Drupal\Core\Session\AccountProxyInterface
diff --git a/core/lib/Drupal/Core/Cache/ThemeCacheContext.php b/core/lib/Drupal/Core/Cache/ThemeCacheContext.php
index a11671b..afded28 100644
--- a/core/lib/Drupal/Core/Cache/ThemeCacheContext.php
+++ b/core/lib/Drupal/Core/Cache/ThemeCacheContext.php
@@ -7,6 +7,7 @@
 
 namespace Drupal\Core\Cache;
 
+use Drupal\Core\Routing\RouteMatchInterface;
 use Symfony\Component\HttpFoundation\RequestStack;
 use Drupal\Core\Theme\ThemeNegotiatorInterface;
 
@@ -16,6 +17,13 @@
 class ThemeCacheContext implements CacheContextInterface {
 
   /**
+   * The current route match.
+   *
+   * @var \Drupal\Core\Routing\RouteMatch
+   */
+  protected $routeMatch;
+
+  /**
    * The request stack.
    *
    * @var \Symfony\Component\HttpFoundation\RequestStack
@@ -32,12 +40,15 @@ class ThemeCacheContext implements CacheContextInterface {
   /**
    * Constructs a new ThemeCacheContext service.
    *
+   * @param \Drupal\Core\Routing\RouteMatchInterface $route_match
+   *   The route match.
    * @param \Symfony\Component\HttpFoundation\RequestStack $request_stack
    *   The request stack.
    * @param \Drupal\Core\Theme\ThemeNegotiatorInterface $theme_negotiator
    *   The theme negotiator.
    */
-  public function __construct(RequestStack $request_stack, ThemeNegotiatorInterface $theme_negotiator) {
+  public function __construct(RouteMatchInterface $route_match, RequestStack $request_stack, ThemeNegotiatorInterface $theme_negotiator) {
+    $this->routeMatch = $route_match;
     $this->requestStack = $request_stack;
     $this->themeNegotiator = $theme_negotiator;
   }
@@ -54,7 +65,7 @@ public static function getLabel() {
    */
   public function getContext() {
     $request = $this->requestStack->getCurrentRequest();
-    return $this->themeNegotiator->determineActiveTheme($request) ?: 'stark';
+    return $this->themeNegotiator->determineActiveTheme($this->routeMatch, $request) ?: 'stark';
   }
 
 }
diff --git a/core/lib/Drupal/Core/Routing/CurrentRouteMatch.php b/core/lib/Drupal/Core/Routing/CurrentRouteMatch.php
new file mode 100644
index 0000000..5cde3b6
--- /dev/null
+++ b/core/lib/Drupal/Core/Routing/CurrentRouteMatch.php
@@ -0,0 +1,113 @@
+<?php
+
+/**
+ * @file
+ * Contains Drupal\Core\Routing\CurrentRouteMatch.
+ */
+
+namespace Drupal\Core\Routing;
+
+use Symfony\Cmf\Component\Routing\RouteObjectInterface;
+use Symfony\Component\HttpFoundation\Request;
+use Symfony\Component\HttpFoundation\RequestStack;
+
+/**
+ * Default object for current_route_match service.
+ */
+class CurrentRouteMatch implements RouteMatchInterface {
+
+  /**
+   * The related request stack.
+   *
+   * @var \Symfony\Component\HttpFoundation\RequestStack
+   */
+  protected $requestStack;
+
+  /**
+   * Internal cache of RouteMatch objects.
+   *
+   * @var \SplObjectStorage
+   */
+  protected $routeMatches;
+
+  public function __construct(RequestStack $request_stack) {
+    $this->requestStack = $request_stack;
+    $this->routeMatches = new \SplObjectStorage();
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRouteName() {
+    return $this->getRouteMatch($this->requestStack->getCurrentRequest())->getRouteName();
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRouteObject() {
+    return $this->getRouteMatch($this->requestStack->getCurrentRequest())->getRouteObject();
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getParameter($parameter_name) {
+    return $this->getRouteMatch($this->requestStack->getCurrentRequest())->getParameter($parameter_name);
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getParameters() {
+    return $this->getRouteMatch($this->requestStack->getCurrentRequest())->getParameters();
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRawParameter($parameter_name) {
+    return $this->getRouteMatch($this->requestStack->getCurrentRequest())->getRawParameter($parameter_name);
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRawParameters() {
+    return $this->getRouteMatch($this->requestStack->getCurrentRequest())->getRawParameters();
+  }
+
+  /**
+   * Loads a RouteMatch from a request variable.
+   *
+   * @param \Symfony\Component\HttpFoundation\Request $request
+   *   A Symfony request object.
+   *
+   * @return \Drupal\Core\Routing\RouteMatch
+   *   A Drupal RouteMatch representing the request.
+   */
+  protected function getRouteMatch(Request $request) {
+    if (!isset($this->routeMatches[$request])) {
+      if (!$this->isRouted($request)) {
+        return new NullRouteMatch();
+      }
+      $this->routeMatches[$request] = RouteMatch::createFromRequest($request);
+    }
+    return $this->routeMatches[$request];
+  }
+
+  /**
+   * Returns whether a route has been matched for the request.
+   *
+   * @param \Symfony\Component\HttpFoundation\Request $request
+   *   A Symfony request object.
+   *
+   * @return bool
+   *   TRUE if a route has been matched for the request. FALSE if called prior
+   *   to routing or for a request with no matching route (e.g., a 404 page).
+   */
+  protected function isRouted(Request $request) {
+    return (bool) $request->attributes->get(RouteObjectInterface::ROUTE_OBJECT);
+  }
+
+}
diff --git a/core/lib/Drupal/Core/Routing/NullRouteMatch.php b/core/lib/Drupal/Core/Routing/NullRouteMatch.php
new file mode 100644
index 0000000..3fd72ed
--- /dev/null
+++ b/core/lib/Drupal/Core/Routing/NullRouteMatch.php
@@ -0,0 +1,59 @@
+<?php
+
+/**
+ * @file
+ * Contains Drupal\Core\Routing\NullRouteMatch.
+ */
+
+namespace Drupal\Core\Routing;
+
+use Symfony\Component\HttpFoundation\ParameterBag;
+
+/**
+ * Stub implementation of RouteMatchInterface for when there's no matched route.
+ */
+class NullRouteMatch implements RouteMatchInterface {
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRouteName() {
+    return '';
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRouteObject() {
+    return NULL;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getParameter($parameter_name) {
+    return NULL;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getParameters() {
+    return new ParameterBag();
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRawParameter($parameter_name) {
+    return NULL;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRawParameters() {
+    return new ParameterBag();
+  }
+
+}
diff --git a/core/lib/Drupal/Core/Routing/RouteMatch.php b/core/lib/Drupal/Core/Routing/RouteMatch.php
new file mode 100644
index 0000000..a82a696
--- /dev/null
+++ b/core/lib/Drupal/Core/Routing/RouteMatch.php
@@ -0,0 +1,157 @@
+<?php
+
+/**
+ * @file
+ * Contains Drupal\Core\Routing\RouteMatch.
+ */
+
+namespace Drupal\Core\Routing;
+
+use Symfony\Cmf\Component\Routing\RouteObjectInterface;
+use Symfony\Component\HttpFoundation\ParameterBag;
+use Symfony\Component\HttpFoundation\Request;
+use Symfony\Component\Routing\Route;
+
+/**
+ * Default object representing the results of routing.
+ */
+class RouteMatch implements RouteMatchInterface {
+
+  /**
+   * The route name.
+   *
+   * @var string
+   */
+  protected $routeName;
+
+  /**
+   * The route.
+   *
+   * @var \Symfony\Component\Routing\Route
+   */
+  protected $route;
+
+  /**
+   * A key|value store of parameters.
+   *
+   * @var \Symfony\Component\HttpFoundation\ParameterBag
+   */
+  protected $parameters;
+
+  /**
+   * A key|value store of raw parameters.
+   *
+   * @var \Symfony\Component\HttpFoundation\ParameterBag
+   */
+  protected $rawParameters;
+
+  /**
+   * Constructs a RouteMatch object.
+   *
+   * @param string $route_name
+   *  The name of the route.
+   * @param \Symfony\Component\Routing\Route $route
+   *   The route.
+   * @param array $parameters
+   *   The parameters array.
+   * @param array $raw_parameters
+   *   The raw $parameters array.
+   */
+  public function __construct($route_name, Route $route, array $parameters = array(), array $raw_parameters = array()) {
+    $this->routeName = $route_name;
+    $this->route = $route;
+
+    // Pre-filter parameters.
+    $route_params = $this->getParameterNames();
+    $parameters = array_intersect_key($this->parameters, $route_params);
+    $raw_parameters = array_intersect_key($this->$raw_parameters, $route_params);
+    $this->parameters = new ParameterBag($parameters);
+    $this->rawParameters = new ParameterBag($raw_parameters);
+  }
+
+  /**
+   * Create a RouteMatch from a request.
+   *
+   * @param Request $request
+   *   Symfony Request object.
+   * @return static
+   */
+  public static function createFromRequest(Request $request) {
+
+    $raw_variables = array();
+    if ($raw = $request->attributes->get('_raw_variables')) {
+      $raw_variables = $raw->all();
+    }
+    return new static(
+      $request->attributes->get(RouteObjectInterface::ROUTE_NAME),
+      $request->attributes->get(RouteObjectInterface::ROUTE_OBJECT),
+      $request->attributes->all(),
+      $raw_variables);
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRouteName() {
+    return $this->routeName;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRouteObject() {
+    return $this->route;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getParameter($parameter_name) {
+    return $this->parameters->get($parameter_name);
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getParameters() {
+    return $this->parameters;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRawParameter($parameter_name) {
+    return $this->rawParameters->get($parameter_name);
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getRawParameters() {
+    return $this->rawParameters;
+  }
+
+  /**
+   * Returns the names of all parameters for the currently matched route.
+   *
+   * @return array
+   *   Route parameter names as both the keys and values.
+   */
+  protected function getParameterNames() {
+    $names = array();
+    if ($route = $this->getRouteObject()) {
+      // Variables defined in path and host patterns are route parameters.
+      $variables = $route->compile()->getVariables();
+      $names = array_combine($variables, $variables);
+      // Route defaults that do not start with a leading "_" are also
+      // parameters, even if they are not included in path or host patterns.
+      foreach ($route->getDefaults() as $name => $value) {
+        if (!isset($names[$name]) && substr($name, 0, 1) !== '_') {
+          $names[$name] = $name;
+        }
+      }
+    }
+    return $names;
+  }
+
+}
diff --git a/core/lib/Drupal/Core/Routing/RouteMatchInterface.php b/core/lib/Drupal/Core/Routing/RouteMatchInterface.php
new file mode 100644
index 0000000..e2fc534
--- /dev/null
+++ b/core/lib/Drupal/Core/Routing/RouteMatchInterface.php
@@ -0,0 +1,79 @@
+<?php
+
+/**
+ * @file
+ * Contains Drupal\Core\Routing\RouteMatchInterface.
+ */
+
+namespace Drupal\Core\Routing;
+
+/**
+ * Provides an interface for classes representing the result of routing.
+ *
+ * Routing is the process of selecting the best matching candidate from a
+ * collection of routes for an incoming request. The relevant properties of a
+ * request include the path as well as a list of raw parameter values derived
+ * from the URL. If an appropriate route is found, raw parameter values will be
+ * upcast automatically if possible.
+ *
+ * The route match object contains useful information about the selected route
+ * as well as the raw and upcast parameters derived from the incoming
+ * request.
+ */
+interface RouteMatchInterface {
+
+  /**
+   * Returns the route name.
+   *
+   * @return string
+   *   The route name.
+   */
+  public function getRouteName();
+
+  /**
+   * Returns the route object.
+   *
+   * @return \Symfony\Component\Routing\Route
+   *   The route object.
+   */
+  public function getRouteObject();
+
+  /**
+   * Returns the value of a named route parameter.
+   *
+   * @param string $parameter_name
+   *   The parameter name.
+   *
+   * @return mixed
+   *   The parameter value.
+   */
+  public function getParameter($parameter_name);
+
+  /**
+   * Returns the bag of all route parameters.
+   *
+   * @return \Symfony\Component\HttpFoundation\ParameterBag
+   *   The parameter bag.
+   */
+  public function getParameters();
+
+  /**
+   * Returns the raw value of a named route parameter.
+   *
+   * @param string $parameter_name
+   *   The parameter name.
+   *
+   * @return string
+   *   The parameter value.
+   */
+  public function getRawParameter($parameter_name);
+
+  /**
+   * Returns the bag of all raw route parameters.
+   *
+   * @return \Symfony\Component\HttpFoundation\ParameterBag
+   *   The parameter bag.
+   */
+  public function getRawParameters();
+
+}
diff --git a/core/lib/Drupal/Core/Theme/AjaxBasePageNegotiator.php b/core/lib/Drupal/Core/Theme/AjaxBasePageNegotiator.php
index d3a4bac..1be4cf4 100644
--- a/core/lib/Drupal/Core/Theme/AjaxBasePageNegotiator.php
+++ b/core/lib/Drupal/Core/Theme/AjaxBasePageNegotiator.php
@@ -9,7 +9,7 @@
 
 use Drupal\Core\Access\CsrfTokenGenerator;
 use Drupal\Core\Config\ConfigFactoryInterface;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
+use Drupal\Core\Routing\RouteMatchInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -61,9 +61,9 @@ public function __construct(CsrfTokenGenerator $token_generator, ConfigFactoryIn
   /**
    * {@inheritdoc}
    */
-  public function applies(Request $request) {
+  public function applies(RouteMatchInterface $route_match, Request $request) {
     // Check whether the route was configured to use the base page theme.
-    return ($route = $request->attributes->get(RouteObjectInterface::ROUTE_OBJECT))
+    return ($route = $route_match->getRouteObject())
       && $route->hasOption('_theme')
       && $route->getOption('_theme') == 'ajax_base_page';
   }
@@ -71,7 +71,7 @@ public function applies(Request $request) {
   /**
    * {@inheritdoc}
    */
-  public function determineActiveTheme(Request $request) {
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request) {
     if (($ajax_page_state = $request->request->get('ajax_page_state'))  && !empty($ajax_page_state['theme']) && !empty($ajax_page_state['theme_token'])) {
       $theme = $ajax_page_state['theme'];
       $token = $ajax_page_state['theme_token'];
diff --git a/core/lib/Drupal/Core/Theme/DefaultNegotiator.php b/core/lib/Drupal/Core/Theme/DefaultNegotiator.php
index 22b5863..ea4bd15 100644
--- a/core/lib/Drupal/Core/Theme/DefaultNegotiator.php
+++ b/core/lib/Drupal/Core/Theme/DefaultNegotiator.php
@@ -8,6 +8,7 @@
 namespace Drupal\Core\Theme;
 
 use Drupal\Core\Config\ConfigFactoryInterface;
+use Drupal\Core\Routing\RouteMatchInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -35,14 +36,14 @@ public function __construct(ConfigFactoryInterface $config_factory) {
   /**
    * {@inheritdoc}
    */
-  public function applies(Request $request) {
+  public function applies(RouteMatchInterface $route_match, Request $request) {
     return TRUE;
   }
 
   /**
    * {@inheritdoc}
    */
-  public function determineActiveTheme(Request $request) {
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request) {
     return $this->config->get('default');
   }
 
diff --git a/core/lib/Drupal/Core/Theme/ThemeNegotiator.php b/core/lib/Drupal/Core/Theme/ThemeNegotiator.php
index 054d6be..13692bd 100644
--- a/core/lib/Drupal/Core/Theme/ThemeNegotiator.php
+++ b/core/lib/Drupal/Core/Theme/ThemeNegotiator.php
@@ -7,8 +7,8 @@
 
 namespace Drupal\Core\Theme;
 
+use Drupal\Core\Routing\RouteMatchInterface;
 use Symfony\Component\HttpFoundation\Request;
-use Symfony\Component\HttpFoundation\RequestStack;
 
 /**
  * Provides a class which determines the active theme of the page.
@@ -38,13 +38,6 @@ class ThemeNegotiator implements ThemeNegotiatorInterface {
   protected $sortedNegotiators;
 
   /**
-   * The request stack.
-   *
-   * @var \Symfony\Component\HttpFoundation\RequestStack
-   */
-  protected $requestStack;
-
-  /**
    * The access checker for themes.
    *
    * @var \Drupal\Core\Theme\ThemeAccessCheck
@@ -57,9 +50,8 @@ class ThemeNegotiator implements ThemeNegotiatorInterface {
    * @param \Drupal\Core\Theme\ThemeAccessCheck $theme_access
    *   The access checker for themes.
    */
-  public function __construct(ThemeAccessCheck $theme_access, RequestStack $request_stack) {
+  public function __construct(ThemeAccessCheck $theme_access) {
     $this->themeAccess = $theme_access;
-    $this->requestStack = $request_stack;
   }
 
   /**
@@ -97,33 +89,19 @@ protected function getSortedNegotiators() {
   }
 
   /**
-   * Get the current active theme.
-   *
-   * @return string
-   *   The current active string.
-   */
-  public function getActiveTheme() {
-    $request = $this->requestStack->getCurrentRequest();
-    if (!$request->attributes->has('_theme_active')) {
-      $this->determineActiveTheme($request);
-    }
-    return $request->attributes->get('_theme_active');
-  }
-
-  /**
    * {@inheritdoc}
    */
-  public function applies(Request $request) {
+  public function applies(RouteMatchInterface $route_match, Request $request) {
     return TRUE;
   }
 
   /**
    * {@inheritdoc}
    */
-  public function determineActiveTheme(Request $request) {
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request) {
     foreach ($this->getSortedNegotiators() as $negotiator) {
-      if ($negotiator->applies($request)) {
-        $theme = $negotiator->determineActiveTheme($request);
+      if ($negotiator->applies($route_match, $request)) {
+        $theme = $negotiator->determineActiveTheme($route_match, $request);
         if ($theme !== NULL && $this->themeAccess->checkAccess($theme)) {
           $request->attributes->set('_theme_active', $theme);
           return $request->attributes->get('_theme_active');
diff --git a/core/lib/Drupal/Core/Theme/ThemeNegotiatorInterface.php b/core/lib/Drupal/Core/Theme/ThemeNegotiatorInterface.php
index e0631c2..6a0ecfc 100644
--- a/core/lib/Drupal/Core/Theme/ThemeNegotiatorInterface.php
+++ b/core/lib/Drupal/Core/Theme/ThemeNegotiatorInterface.php
@@ -7,6 +7,7 @@
 
 namespace Drupal\Core\Theme;
 
+use Drupal\Core\Routing\RouteMatchInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -30,6 +31,8 @@
   /**
    * Whether this theme negotiator should be used to set the theme.
    *
+   * @param \Drupal\Core\Routing\RouteMatchInterface $route_match
+   *   The current route match object.
    * @param \Symfony\Component\HttpFoundation\Request $request
    *   The current request object.
    *
@@ -37,17 +40,19 @@
    *   TRUE if this negotiator should be used or FALSE to let other negotiators
    *   decide.
    */
-  public function applies(Request $request);
+  public function applies(RouteMatchInterface $route_match, Request $request);
 
   /**
    * Determine the active theme for the request.
    *
+   * @param \Drupal\Core\Routing\RouteMatchInterface $route_match
+   *   The active route match of the site.
    * @param \Symfony\Component\HttpFoundation\Request $request
    *   The active request of the site.
    *
    * @return string|null
    *   Returns the active theme name, else return NULL.
    */
-  public function determineActiveTheme(Request $request);
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request);
 
 }
diff --git a/core/modules/block/block.module b/core/modules/block/block.module
index ceffa1f..7a4f199 100644
--- a/core/modules/block/block.module
+++ b/core/modules/block/block.module
@@ -8,7 +8,6 @@
 use Drupal\block\BlockInterface;
 use Drupal\language\Entity\Language;
 use Drupal\system\Entity\Menu;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -102,7 +101,7 @@ function block_page_build(&$page) {
 
   // Fetch a list of regions for the current theme.
   $all_regions = system_region_list($theme);
-  if (\Drupal::request()->attributes->get(RouteObjectInterface::ROUTE_NAME) != 'block.admin_demo') {
+  if (\Drupal::routeMatch()->getRouteName() != 'block.admin_demo') {
     // Load all region content assigned via blocks.
     foreach (array_keys($all_regions) as $region) {
       // Assign blocks to region.
diff --git a/core/modules/block/src/Theme/AdminDemoNegotiator.php b/core/modules/block/src/Theme/AdminDemoNegotiator.php
index d175b91..98fab9c 100644
--- a/core/modules/block/src/Theme/AdminDemoNegotiator.php
+++ b/core/modules/block/src/Theme/AdminDemoNegotiator.php
@@ -7,8 +7,8 @@
 
 namespace Drupal\block\Theme;
 
+use Drupal\Core\Routing\RouteMatchInterface;
 use Drupal\Core\Theme\ThemeNegotiatorInterface;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -19,17 +19,17 @@ class AdminDemoNegotiator implements ThemeNegotiatorInterface {
   /**
    * {@inheritdoc}
    */
-  public function applies(Request $request) {
-    return $request->attributes->get(RouteObjectInterface::ROUTE_NAME) == 'block.admin_demo';
+  public function applies(RouteMatchInterface $route_match, Request $request) {
+    return $route_match->getRouteName() == 'block.admin_demo';
   }
 
   /**
    * {@inheritdoc}
    */
-  public function determineActiveTheme(Request $request) {
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request) {
     // We return exactly what was passed in, to guarantee that the page will
     // always be displayed using the theme whose blocks are being configured.
-    return $request->attributes->get('theme');
+    return $route_match->getParameter('theme');
   }
 
 }
diff --git a/core/modules/comment/src/Routing/CommentBundleEnhancer.php b/core/modules/comment/src/Routing/CommentBundleEnhancer.php
index 783fcda..5b15e4b 100644
--- a/core/modules/comment/src/Routing/CommentBundleEnhancer.php
+++ b/core/modules/comment/src/Routing/CommentBundleEnhancer.php
@@ -10,7 +10,6 @@
 use Drupal\Core\Entity\EntityManagerInterface;
 use Symfony\Component\HttpFoundation\Request;
 use Symfony\Cmf\Component\Routing\Enhancer\RouteEnhancerInterface;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 
 /**
  * Constructs a route enhancer to extract values from comment bundles.
diff --git a/core/modules/forum/forum.module b/core/modules/forum/forum.module
index af041fc..941c112 100644
--- a/core/modules/forum/forum.module
+++ b/core/modules/forum/forum.module
@@ -110,8 +110,7 @@ function forum_menu_local_tasks(&$data, $route_name) {
 
   // Add action link to 'node/add/forum' on 'forum' sub-pages.
   if (in_array($route_name, array('forum.index', 'forum.page'))) {
-    $request = \Drupal::request();
-    $forum_term = $request->attributes->get('taxonomy_term');
+    $forum_term = \Drupal::routeMatch()->getParameter('taxonomy_term');
     $vid = \Drupal::config('forum.settings')->get('vocabulary');
     $links = array();
     // Loop through all bundles for forum taxonomy vocabulary field.
diff --git a/core/modules/node/node.module b/core/modules/node/node.module
index 6d1b467..a1c78ee 100644
--- a/core/modules/node/node.module
+++ b/core/modules/node/node.module
@@ -29,7 +29,6 @@
 use Drupal\Core\Template\Attribute;
 use Drupal\file\Entity\File;
 use Drupal\language\Entity\Language as LanguageEntity;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Drupal\block\Entity\Block;
 use Drupal\Core\Session\AccountInterface;
 
@@ -565,9 +564,9 @@ function node_revision_delete($revision_id) {
  *   The ID of the node if this is a full page view, otherwise FALSE.
  */
 function node_is_page(NodeInterface $node) {
-  $request = \Drupal::request();
-  if ($request->attributes->get(RouteObjectInterface::ROUTE_NAME) == 'node.view') {
-    $page_node = $request->attributes->get('node');
+  $route_match = \Drupal::routeMatch();
+  if ($route_match->getRouteName() == 'node.view') {
+    $page_node = $route_match->getParameter('node');
   }
   return (!empty($page_node) ? $page_node->id() == $node->id() : FALSE);
 }
@@ -577,7 +576,7 @@ function node_is_page(NodeInterface $node) {
  */
 function node_preprocess_html(&$variables) {
   // If on an individual node page, add the node type to body classes.
-  if (($node = \Drupal::request()->attributes->get('node')) && $node instanceof NodeInterface) {
+  if (($node = \Drupal::routeMatch()->getParameter('node')) && $node instanceof NodeInterface) {
     $variables['attributes']['class'][] = drupal_html_class('node--type-' . $node->getType());
   }
 }
@@ -984,16 +983,14 @@ function node_block_access(Block $block, $operation, AccountInterface $account,
 
     // For blocks with node types associated, if the node type does not match
     // the settings from this block, deny access to it.
-    $request = \Drupal::request();
-    if ($node = $request->attributes->get('node')) {
+    $route_match = \Drupal::routeMatch();
+    if ($node = $route_match->getParameter('node')) {
       // Page has node.
       return in_array($node->bundle(), $allowed_types);
     }
     // This is a node creation page.
-    // $request->attributes->has('node_type') would also match administration
-    // configuration pages, which the previous URI path options did not.
-    if ($request->attributes->get(RouteObjectInterface::ROUTE_NAME) == 'node.add') {
-      $node_type = $request->attributes->get('node_type');
+    if ($route_match->getRouteName() == 'node.add') {
+      $node_type = $route_match->getParameter('node_type');
       return in_array($node_type->id(), $allowed_types);
     }
 
diff --git a/core/modules/rdf/rdf.module b/core/modules/rdf/rdf.module
index dc97773..419e6f0 100644
--- a/core/modules/rdf/rdf.module
+++ b/core/modules/rdf/rdf.module
@@ -6,7 +6,6 @@
  */
 
 use Drupal\Core\Template\Attribute;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -352,7 +351,7 @@ function rdf_preprocess_user(&$variables) {
   }
   // If we are on the user account page, add the relationship between the
   // sioc:UserAccount and the foaf:Person who holds the account.
-  if (\Drupal::request()->attributes->get(RouteObjectInterface::ROUTE_NAME) == $uri->getRouteName()) {
+  if (\Drupal::routeMatch()->getRouteName() == $uri->getRouteName()) {
     // Adds the markup for username as language neutral literal, see
     // rdf_preprocess_username().
     $name_mapping = $mapping->getPreparedFieldMapping('name');
diff --git a/core/modules/shortcut/shortcut.module b/core/modules/shortcut/shortcut.module
index 0225e25..6b516d1 100644
--- a/core/modules/shortcut/shortcut.module
+++ b/core/modules/shortcut/shortcut.module
@@ -11,7 +11,6 @@
 use Drupal\Core\Url;
 use Drupal\shortcut\Entity\ShortcutSet;
 use Drupal\shortcut\ShortcutSetInterface;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -343,10 +342,8 @@ function shortcut_preprocess_page(&$variables) {
   // shortcuts and if the page's actual content is being shown (for example,
   // we do not want to display it on "access denied" or "page not found"
   // pages).
-  // Load the router item corresponding to the current page.
-  $request = \Drupal::request();
   $item = array();
-  if ($route = $request->attributes->get(RouteObjectInterface::ROUTE_NAME)) {
+  if (\Drupal::routeMatch()->getRouteObject()) {
     // @todo What should be done on a 404/403 page?
     $item['access'] = TRUE;
   }
diff --git a/core/modules/system/src/Controller/BatchController.php b/core/modules/system/src/Controller/BatchController.php
index 574872e..d14f987 100644
--- a/core/modules/system/src/Controller/BatchController.php
+++ b/core/modules/system/src/Controller/BatchController.php
@@ -11,7 +11,6 @@
 use Drupal\Core\DependencyInjection\ContainerInjectionInterface;
 use Drupal\Core\Page\DefaultHtmlFragmentRenderer;
 use Drupal\Core\Page\HtmlPage;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\DependencyInjection\ContainerInterface;
 use Symfony\Component\HttpFoundation\Request;
 use Symfony\Component\HttpFoundation\Response;
@@ -99,8 +98,7 @@ public function batchPage(Request $request) {
    */
   public function render(array $output, $status_code = 200) {
     if (!isset($output['#title'])) {
-      $request = \Drupal::request();
-      $output['#title'] = $this->titleResolver->getTitle($request, $request->attributes->get(RouteObjectInterface::ROUTE_OBJECT));
+      $output['#title'] = $this->titleResolver->getTitle(\Drupal::request(), \Drupal::routeMatch()->getRouteObject());
     }
     $page = new HtmlPage('', isset($output['#cache']) ? $output['#cache'] : array(), $output['#title']);
 
diff --git a/core/modules/system/src/Theme/BatchNegotiator.php b/core/modules/system/src/Theme/BatchNegotiator.php
index 7002504..9635158 100644
--- a/core/modules/system/src/Theme/BatchNegotiator.php
+++ b/core/modules/system/src/Theme/BatchNegotiator.php
@@ -8,8 +8,8 @@
 namespace Drupal\system\Theme;
 
 use Drupal\Core\Batch\BatchStorageInterface;
+use Drupal\Core\Routing\RouteMatchInterface;
 use Drupal\Core\Theme\ThemeNegotiatorInterface;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -37,14 +37,14 @@ public function __construct(BatchStorageInterface $batch_storage) {
   /**
    * {@inheritdoc}
    */
-  public function applies(Request $request) {
-    return $request->attributes->get(RouteObjectInterface::ROUTE_NAME) == 'system.batch_page';
+  public function applies(RouteMatchInterface $route_match, Request $request) {
+    return $route_match->getRouteName() == 'system.batch_page';
   }
 
   /**
    * {@inheritdoc}
    */
-  public function determineActiveTheme(Request $request) {
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request) {
     // Retrieve the current state of the batch.
     $batch = &batch_get();
     if (!$batch && $request->request->has('id')) {
diff --git a/core/modules/system/tests/modules/menu_test/menu_test.module b/core/modules/system/tests/modules/menu_test/menu_test.module
index f8aff5d..4ac2487 100644
--- a/core/modules/system/tests/modules/menu_test/menu_test.module
+++ b/core/modules/system/tests/modules/menu_test/menu_test.module
@@ -139,7 +139,7 @@ function menu_test_theme_page_callback($inherited = FALSE) {
   // Initialize the theme system so that $theme_key will be populated.
   drupal_theme_initialize();
   // Now we check what the theme negotiator service returns.
-  $active_theme = \Drupal::service('theme.negotiator')->getActiveTheme('getActiveTheme');
+  $active_theme = \Drupal::service('theme.negotiator')->determineActiveTheme(\Drupal::routeMatch(), \Drupal::request());
   $output = "Active theme: $active_theme. Actual theme: $theme_key.";
   if ($inherited) {
     $output .= ' Theme negotiation inheritance is being tested.';
diff --git a/core/modules/system/tests/modules/menu_test/src/Theme/TestThemeNegotiator.php b/core/modules/system/tests/modules/menu_test/src/Theme/TestThemeNegotiator.php
index 77954a3..ebde794 100644
--- a/core/modules/system/tests/modules/menu_test/src/Theme/TestThemeNegotiator.php
+++ b/core/modules/system/tests/modules/menu_test/src/Theme/TestThemeNegotiator.php
@@ -7,6 +7,7 @@
 
 namespace Drupal\menu_test\Theme;
 
+use Drupal\Core\Routing\RouteMatchInterface;
 use Drupal\Core\Theme\ThemeNegotiatorInterface;
 use Symfony\Component\HttpFoundation\Request;
 
@@ -21,15 +22,15 @@ class TestThemeNegotiator implements ThemeNegotiatorInterface {
   /**
    * {@inheritdoc}
    */
-  public function applies(Request $request) {
-    return $request->attributes->has('inherited');
+  public function applies(RouteMatchInterface $route_match, Request $request) {
+    return (bool) $route_match->getParameter('inherited');
   }
 
   /**
    * {@inheritdoc}
    */
-  public function determineActiveTheme(Request $request) {
-    $argument = $request->attributes->get('inherited');
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request) {
+    $argument = $route_match->getParameter('inherited');
     // Test using the variable administrative theme.
     if ($argument == 'use-admin-theme') {
       return \Drupal::config('system.theme')->get('admin');
diff --git a/core/modules/system/tests/modules/theme_test/src/Theme/CustomThemeNegotiator.php b/core/modules/system/tests/modules/theme_test/src/Theme/CustomThemeNegotiator.php
index 33b9bec..96d2c95 100644
--- a/core/modules/system/tests/modules/theme_test/src/Theme/CustomThemeNegotiator.php
+++ b/core/modules/system/tests/modules/theme_test/src/Theme/CustomThemeNegotiator.php
@@ -7,10 +7,9 @@
 
 namespace Drupal\theme_test\Theme;
 
+use Drupal\Core\Routing\RouteMatchInterface;
 use Drupal\Core\Theme\ThemeNegotiatorInterface;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
-use Symfony\Component\Routing\Route;
 
 /**
  * Just forces the 'test_theme' theme.
@@ -20,16 +19,16 @@ class CustomThemeNegotiator implements ThemeNegotiatorInterface {
   /**
    * {@inheritdoc}
    */
-  public function applies(Request $request) {
-    return (($route_object = $request->attributes->get(RouteObjectInterface::ROUTE_OBJECT)) && $route_object instanceof Route && $route_object->hasOption('_custom_theme'));
+  public function applies(RouteMatchInterface $route_match, Request $request) {
+    $route = $route_match->getRouteObject();
+    return ($route && $route->hasOption('_custom_theme'));
   }
 
   /**
    * {@inheritdoc}
    */
-  public function determineActiveTheme(Request $request) {
-    $route_object = $request->attributes->get(RouteObjectInterface::ROUTE_OBJECT);
-    return $route_object->getOption('_custom_theme');
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request) {
+    return $route_match->getRouteObject()->getOption('_custom_theme');
   }
 
 }
diff --git a/core/modules/system/tests/modules/theme_test/src/Theme/HighPriorityThemeNegotiator.php b/core/modules/system/tests/modules/theme_test/src/Theme/HighPriorityThemeNegotiator.php
index 91fc936..cebc4eb 100644
--- a/core/modules/system/tests/modules/theme_test/src/Theme/HighPriorityThemeNegotiator.php
+++ b/core/modules/system/tests/modules/theme_test/src/Theme/HighPriorityThemeNegotiator.php
@@ -7,8 +7,8 @@
 
 namespace Drupal\theme_test\Theme;
 
+use Drupal\Core\Routing\RouteMatchInterface;
 use Drupal\Core\Theme\ThemeNegotiatorInterface;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -16,19 +16,17 @@
  */
 class HighPriorityThemeNegotiator implements ThemeNegotiatorInterface {
 
-
-
   /**
    * {@inheritdoc}
    */
-  public function applies(Request $request) {
-    return (($route_name = $request->attributes->get(RouteObjectInterface::ROUTE_NAME)) && $route_name == 'theme_test.priority');
+  public function applies(RouteMatchInterface $route_match, Request $request) {
+    return ($route_match->getRouteName() == 'theme_test.priority');
   }
 
   /**
    * {@inheritdoc}
    */
-  public function determineActiveTheme(Request $request) {
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request) {
     return 'stark';
   }
 
diff --git a/core/modules/taxonomy/taxonomy.module b/core/modules/taxonomy/taxonomy.module
index fde291e..cf9a6ab 100644
--- a/core/modules/taxonomy/taxonomy.module
+++ b/core/modules/taxonomy/taxonomy.module
@@ -332,9 +332,7 @@ function template_preprocess_taxonomy_term(&$variables) {
  *   A taxonomy term entity.
  */
 function taxonomy_term_is_page(Term $term) {
-  $request = \Drupal::request();
-  if ($request->attributes->has('taxonomy_term')) {
-    $page_term = $request->attributes->get('taxonomy_term');
+  if ($page_term = \Drupal::routeMatch()->getParameter('taxonomy_term')) {
     return $page_term->id() == $term->id();
   }
   return FALSE;
diff --git a/core/modules/tour/tour.module b/core/modules/tour/tour.module
index ffe79c2..f6774fd 100644
--- a/core/modules/tour/tour.module
+++ b/core/modules/tour/tour.module
@@ -5,7 +5,6 @@
  * Main functions of the module.
  */
 use Drupal\Core\Cache\CacheBackendInterface;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -83,8 +82,8 @@ function tour_preprocess_page(&$variables) {
   }
 
   // Load all of the items and match on route name.
-  $request = \Drupal::request();
-  $route_name = $request->attributes->get(RouteObjectInterface::ROUTE_NAME);
+  $route_match = \Drupal::routeMatch();
+  $route_name = $route_match->getRouteName();
 
   $results = \Drupal::entityQuery('tour')
     ->condition('routes.*.route_name', $route_name)
@@ -92,7 +91,7 @@ function tour_preprocess_page(&$variables) {
   if (!empty($results) && $tours = entity_load_multiple('tour', array_keys($results))) {
     foreach ($tours as $id => $tour) {
       // Match on params.
-      if (!$tour->hasMatchingRoute($route_name, $request->attributes->get('_raw_variables')->all())) {
+      if (!$tour->hasMatchingRoute($route_name, $route_match->getRawParameters()->all())) {
         unset($tours[$id]);
       }
     }
diff --git a/core/modules/user/src/Theme/AdminNegotiator.php b/core/modules/user/src/Theme/AdminNegotiator.php
index ce6f04b..bc9660d 100644
--- a/core/modules/user/src/Theme/AdminNegotiator.php
+++ b/core/modules/user/src/Theme/AdminNegotiator.php
@@ -10,9 +10,9 @@
 use Drupal\Core\Config\ConfigFactoryInterface;
 use Drupal\Core\Entity\EntityManagerInterface;
 use Drupal\Core\Routing\AdminContext;
+use Drupal\Core\Routing\RouteMatchInterface;
 use Drupal\Core\Session\AccountInterface;
 use Drupal\Core\Theme\ThemeNegotiatorInterface;
-use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
 
 /**
@@ -68,14 +68,14 @@ public function __construct(AccountInterface $user, ConfigFactoryInterface $conf
   /**
    * {@inheritdoc}
    */
-  public function applies(Request $request) {
-    return ($this->entityManager->hasController('user_role', 'storage') && $this->user->hasPermission('view the administration theme') && $this->adminContext->isAdminRoute($request->attributes->get(RouteObjectInterface::ROUTE_OBJECT)));
+  public function applies(RouteMatchInterface $route_match, Request $request) {
+    return ($this->entityManager->hasController('user_role', 'storage') && $this->user->hasPermission('view the administration theme') && $this->adminContext->isAdminRoute($route_match->getRouteObject()));
   }
 
   /**
    * {@inheritdoc}
    */
-  public function determineActiveTheme(Request $request) {
+  public function determineActiveTheme(RouteMatchInterface $route_match, Request $request) {
     return $this->configFactory->get('system.theme')->get('admin');
   }
 
diff --git a/core/tests/Drupal/Tests/Core/Theme/ThemeNegotiatorTest.php b/core/tests/Drupal/Tests/Core/Theme/ThemeNegotiatorTest.php
index 89a1e46..df29b74 100644
--- a/core/tests/Drupal/Tests/Core/Theme/ThemeNegotiatorTest.php
+++ b/core/tests/Drupal/Tests/Core/Theme/ThemeNegotiatorTest.php
@@ -7,10 +7,12 @@
 
 namespace Drupal\Tests\Core\Theme;
 
+use Drupal\Core\Routing\RouteMatch;
 use Drupal\Core\Theme\ThemeNegotiator;
 use Drupal\Tests\UnitTestCase;
 use Symfony\Component\HttpFoundation\Request;
 use Symfony\Component\HttpFoundation\RequestStack;
+use Symfony\Component\Routing\Route;
 
 /**
  * Tests the theme negotiator.
@@ -54,8 +56,7 @@ protected function setUp() {
     $this->themeAccessCheck = $this->getMockBuilder('\Drupal\Core\Theme\ThemeAccessCheck')
       ->disableOriginalConstructor()
       ->getMock();
-    $this->requestStack = new RequestStack();
-    $this->themeNegotiator = new ThemeNegotiator($this->themeAccessCheck, $this->requestStack);
+    $this->themeNegotiator = new ThemeNegotiator($this->themeAccessCheck);
   }
 
   /**
@@ -78,11 +79,11 @@ public function testDetermineActiveTheme() {
       ->method('checkAccess')
       ->will($this->returnValue(TRUE));
 
+    $route_match = new RouteMatch('test_route', new Route('/test-route'), array(), array());
     $request = Request::create('/test-route');
-    $theme = $this->themeNegotiator->determineActiveTheme($request);
+    $theme = $this->themeNegotiator->determineActiveTheme($route_match, $request);
 
     $this->assertEquals('example_test', $theme);
-    $this->assertEquals('example_test', $request->attributes->get('_theme_active'));
   }
 
   /**
@@ -113,11 +114,11 @@ public function testDetermineActiveThemeWithPriority() {
       ->method('checkAccess')
       ->will($this->returnValue(TRUE));
 
+    $route_match = new RouteMatch('test_route', new Route('/test-route'), array(), array());
     $request = Request::create('/test-route');
-    $theme = $this->themeNegotiator->determineActiveTheme($request);
+    $theme = $this->themeNegotiator->determineActiveTheme($route_match, $request);
 
     $this->assertEquals('example_test', $theme);
-    $this->assertEquals('example_test', $request->attributes->get('_theme_active'));
   }
 
   /**
@@ -156,11 +157,11 @@ public function testDetermineActiveThemeWithAccessCheck() {
       ->with('example_test2')
       ->will($this->returnValue(TRUE));
 
+    $route_match = new RouteMatch('test_route', new Route('/test-route'), array(), array());
     $request = Request::create('/test-route');
-    $theme = $this->themeNegotiator->determineActiveTheme($request);
+    $theme = $this->themeNegotiator->determineActiveTheme($route_match, $request);
 
     $this->assertEquals('example_test2', $theme);
-    $this->assertEquals('example_test2', $request->attributes->get('_theme_active'));
   }
 
   /**
@@ -192,11 +193,11 @@ public function testDetermineActiveThemeWithNotApplyingNegotiator() {
       ->method('checkAccess')
       ->will($this->returnValue(TRUE));
 
+    $route_match = new RouteMatch('test_route', new Route('/test-route'), array(), array());
     $request = Request::create('/test-route');
-    $theme = $this->themeNegotiator->determineActiveTheme($request);
+    $theme = $this->themeNegotiator->determineActiveTheme($route_match, $request);
 
     $this->assertEquals('example_test2', $theme);
-    $this->assertEquals('example_test2', $request->attributes->get('_theme_active'));
   }
 
 }
