 core/modules/rest/src/RequestHandler.php | 75 ++++++++++++++++++++++++++++----
 1 file changed, 67 insertions(+), 8 deletions(-)

diff --git a/core/modules/rest/src/RequestHandler.php b/core/modules/rest/src/RequestHandler.php
index e5437cc..54d9d87 100644
--- a/core/modules/rest/src/RequestHandler.php
+++ b/core/modules/rest/src/RequestHandler.php
@@ -2,6 +2,7 @@
 
 namespace Drupal\rest;
 
+use Drupal\Component\Utility\ArgumentsResolver;
 use Drupal\Core\Cache\CacheableResponseInterface;
 use Drupal\Core\DependencyInjection\ContainerInjectionInterface;
 use Drupal\Core\Entity\EntityStorageInterface;
@@ -119,17 +120,16 @@ public function handle(RouteMatchInterface $route_match, Request $request) {
 
     // Determine the request parameters that should be passed to the resource
     // plugin.
-    $route_parameters = $route_match->getParameters();
-    $parameters = [];
-    // Filter out all internal parameters starting with "_".
-    foreach ($route_parameters as $key => $parameter) {
-      if ($key{0} !== '_') {
-        $parameters[] = $parameter;
-      }
+    $argument_resolver = $this->getArgumentResolver($route_match, $unserialized, $request);
+    try {
+      $arguments = $argument_resolver->getArguments([$resource, $method]);
+    }
+    catch (\RuntimeException $exception) {
+      $arguments = $this->getLegacyParameters($route_match, $unserialized, $request);
     }
 
     // Invoke the operation on the resource plugin.
-    $response = call_user_func_array([$resource, $method], array_merge($parameters, [$unserialized, $request]));
+    $response = $response = call_user_func_array([$resource, $method], $arguments);
 
     if ($response instanceof CacheableResponseInterface) {
       // Add rest config's cache tags.
@@ -139,4 +139,63 @@ public function handle(RouteMatchInterface $route_match, Request $request) {
     return $response;
   }
 
+  /**
+   * Creates an argument resolver, which can pass along the REST parameters.
+   *
+   * @param \Drupal\Core\Routing\RouteMatchInterface $route_match
+   *   The route match
+   * @param mixed $unserialized
+   *   The unserialized data.
+   * @param \Symfony\Component\HttpFoundation\Request $request
+   *   The request.
+   *
+   * @return \Drupal\Component\Utility\ArgumentsResolver
+   */
+  protected function getArgumentResolver(RouteMatchInterface $route_match, $unserialized, Request $request) {
+    $route = $route_match->getRouteObject();
+
+    // Defaults for the parameters defined on the route object need to be added
+    // to the raw arguments.
+    $raw_route_arguments = $route_match->getRawParameters()->all() + $route->getDefaults();
+
+    $upcasted_route_arguments = $route_match->getParameters()->all();
+    $upcasted_route_arguments['entity'] = $unserialized;
+    $upcasted_route_arguments['data'] = $unserialized;
+    $upcasted_route_arguments['unserialized'] = $unserialized;
+
+    // Parameters which are not defined on the route object, but still are
+    // essential for access checking are passed as wildcards to the argument
+    // resolver.
+    $wildcard_arguments = [$route, $route_match];
+    if (isset($request)) {
+      $wildcard_arguments[] = $request;
+    }
+    $wildcard_arguments[] = $unserialized;
+
+    return new ArgumentsResolver($raw_route_arguments, $upcasted_route_arguments, $wildcard_arguments);
+  }
+
+  /**
+   * @param \Drupal\Core\Routing\RouteMatchInterface $route_match
+   *   The route match
+   * @param mixed $unserialized
+   *   The unserialized data.
+   * @param \Symfony\Component\HttpFoundation\Request $request
+   *   The request.
+   *
+   * @return array
+   */
+  protected function getLegacyParameters(RouteMatchInterface $route_match, $unserialized, Request $request) {
+    $route_parameters = $route_match->getParameters();
+    $parameters = [];
+    // Filter out all internal parameters starting with "_".
+    foreach ($route_parameters as $key => $parameter) {
+      if ($key{0} !== '_') {
+        $parameters[] = $parameter;
+      }
+    }
+
+    return array_merge($parameters, [$unserialized, $request]);
+  }
+
 }
