Completed
Pull Request — 8.x-3.x (#525)
by Philipp
02:06
created

QueryRouteEnhancer::extractParams()   C

Complexity

Conditions 12
Paths 20

Size

Total Lines 40
Code Lines 17

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 12
eloc 17
nc 20
nop 1
dl 0
loc 40
rs 5.1612
c 0
b 0
f 0

How to fix   Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
namespace Drupal\graphql\Routing;
4
5
use Drupal\Component\Utility\NestedArray;
6
use Drupal\Core\Routing\Enhancer\RouteEnhancerInterface;
7
use Drupal\graphql\QueryProvider\QueryProviderInterface;
8
use Drupal\graphql\Utility\JsonHelper;
9
use GraphQL\Server\Helper;
10
use Symfony\Component\HttpFoundation\Request;
11
use Symfony\Component\Routing\Route;
12
13
class QueryRouteEnhancer implements RouteEnhancerInterface {
14
15
  /**
16
   * {@inheritdoc}
17
   */
18
  public function applies(Route $route) {
19
    return $route->hasDefault('_graphql');
20
  }
21
22
  /**
23
   * {@inheritdoc}
24
   */
25
  public function enhance(array $defaults, Request $request) {
26
    $helper = new Helper();
27
    $method = $request->getMethod();
28
    $body = $this->extractBody($request);
29
    $query = $this->extractQuery($request);
30
    $operations = $helper->parseRequestParams($method, $body, $query);
31
32
    // By default we assume a 'single' request. This is going to fail in the
33
    // graphql processor due to a missing query string but at least provides
34
    // the right format for the client to act upon.
35
    return $defaults + [
36
      '_controller' => $defaults['_graphql']['single'],
37
      'operations' => $operations,
38
    ];
39
  }
40
41
  /**
42
   * Extracts the query parameters from a request.
43
   *
44
   * @param \Symfony\Component\HttpFoundation\Request $request
45
   *   The http request object.
46
   *
47
   * @return array
48
   *   The normalized query parameters.
49
   */
50
  protected function extractQuery(Request $request) {
51
    return JsonHelper::decodeParams($request->query->all());
52
  }
53
54
  /**
55
   * Extracts the body parameters from a request.
56
   *
57
   * @param \Symfony\Component\HttpFoundation\Request $request
58
   *   The http request object.
59
   *
60
   * @return array
61
   *   The normalized body parameters.
62
   */
63
  protected function extractBody(Request $request) {
64
    $values = [];
65
66
    // The request body parameters might contain file upload mutations. We treat
67
    // them according to the graphql multipart request specification.
68
    //
69
    // @see https://github.com/jaydenseric/graphql-multipart-request-spec#server
70
    if ($body = JsonHelper::decodeParams($request->request->all())) {
71
      // Flatten the operations array if it exists.
72
      $operations = isset($body['operations']) && is_array($body['operations']) ? $body['operations'] : [];
73
      $values = array_merge($values, $body, $operations);
74
    }
75
76
    // Extract the request content.
77
    if ($content = $request->getContent()) {
78
      $values = array_merge($values, JsonHelper::decodeParams(json_decode($content, TRUE)));
79
    }
80
81
    return $values;
82
  }
83
84
  /**
85
   * TODO: Re-add this.
86
   *
87
   * Extract an associative array of query parameters from the request.
88
   *
89
   * If the given request does not have any POST body content it uses the GET
90
   * query parameters instead.
91
   *
92
   * @return array
93
   *   An associative array of query parameters.
94
   */
95
  protected function applyFiles(Request $request, $values) {
96
    // According to the graphql multipart request specification, uploaded files
97
    // are referenced to variable placeholders in a map. Here, we resolve this
98
    // map by assigning the uploaded files to the corresponding variables.
99
    if (!empty($values['map']) && is_array($values['map']) && $files = $request->files->all()) {
100
      foreach ($files as $key => $file) {
101
        if (!isset($values['map'][$key])) {
102
          continue;
103
        }
104
105
        $paths = (array) $values['map'][$key];
106
        foreach ($paths as $path) {
107
          $path = explode('.', $path);
108
109
          if (NestedArray::keyExists($values, $path)) {
110
            NestedArray::setValue($values, $path, $file);
111
          }
112
        }
113
      }
114
    }
115
116
    return $values;
117
  }
118
119
120
}
121