1
<?php
2

3
namespace Nuwave\Lighthouse\Validation;
4

5
use GraphQL\Language\AST\FieldDefinitionNode;
6
use GraphQL\Language\AST\InputValueDefinitionNode;
7
use GraphQL\Language\AST\ObjectTypeDefinitionNode;
8
use Nuwave\Lighthouse\Exceptions\DefinitionException;
9
use Nuwave\Lighthouse\Schema\AST\DocumentAST;
10
use Nuwave\Lighthouse\Schema\Directives\BaseDirective;
11
use Nuwave\Lighthouse\Support\Contracts\ArgManipulator;
12
use Nuwave\Lighthouse\Support\Contracts\ArgumentValidation;
13

14
abstract class BaseRulesDirective extends BaseDirective implements ArgumentValidation, ArgManipulator
15
{
16 1
    public function rules(): array
17
    {
18 1
        $rules = $this->directiveArgValue('apply');
19

20
        // Custom rules may be referenced through their fully qualified class name.
21
        // The Laravel validator expects a class instance to be passed, so we
22
        // resolve any given rule where a corresponding class exists.
23 1
        foreach ($rules as $key => $rule) {
24 1
            if (class_exists($rule)) {
25 1
                $rules[$key] = app($rule);
26
            }
27
        }
28

29 1
        return $rules;
30
    }
31

32 1
    public function messages(): array
33
    {
34 1
        $messages = $this->directiveArgValue('messages');
35 1
        if ($messages === null) {
36 1
            return [];
37
        }
38

39 1
        if (isset($messages[0])) {
40
            /** @var array<string, string> $flattened */
41 1
            $flattened = [];
42

43
            /**
44
             * We know this holds true, because it has been validated before.
45
             *
46
             * @var array{rule: string, message: string} $messageMap
47
             */
48 1
            foreach ($messages as $messageMap) {
49 1
                $flattened[$messageMap['rule']] = $messageMap['message'];
50
            }
51

52 1
            return $flattened;
53
        }
54

55 1
        return $messages;
56
    }
57

58 1
    public function attribute(): ?string
59
    {
60 1
        return $this->directiveArgValue('attribute');
61
    }
62

63 1
    public function manipulateArgDefinition(
64
        DocumentAST &$documentAST,
65
        InputValueDefinitionNode &$argDefinition,
66
        FieldDefinitionNode &$parentField,
67
        ObjectTypeDefinitionNode &$parentType
68
    ) {
69 1
        $this->validateRulesArg();
70 1
        $this->validateMessageArg();
71
    }
72

73 1
    protected function validateRulesArg(): void
74
    {
75 1
        $rules = $this->directiveArgValue('apply');
76

77 1
        if (! is_array($rules)) {
78 1
            $this->invalidApplyArgument($rules);
79
        }
80

81 1
        if (count($rules) === 0) {
82 1
            $this->invalidApplyArgument($rules);
83
        }
84

85 1
        foreach ($rules as $rule) {
86 1
            if (! is_string($rule)) {
87 1
                $this->invalidApplyArgument($rules);
88
            }
89
        }
90
    }
91

92 1
    protected function validateMessageArg(): void
93
    {
94 1
        $messages = $this->directiveArgValue('messages');
95 1
        if ($messages === null) {
96 1
            return;
97
        }
98

99 1
        if (! is_array($messages)) {
100 1
            $this->invalidMessageArgument($messages);
101
        }
102

103 1
        if (isset($messages[0])) {
104 1
            foreach ($messages as $messageMap) {
105 1
                if (! is_array($messageMap)) {
106 1
                    $this->invalidMessageArgument($messages);
107
                }
108

109 1
                $rule = $messageMap['rule'] ?? null;
110 1
                if (! is_string($rule)) {
111 1
                    $this->invalidMessageArgument($messages);
112
                }
113

114 1
                $message = $messageMap['message'] ?? null;
115 1
                if (! is_string($message)) {
116 1
                    $this->invalidMessageArgument($messages);
117
                }
118
            }
119
        } else {
120 1
            foreach ($messages as $rule => $message) {
121 1
                if (! is_string($rule)) {
122 0
                    $this->invalidMessageArgument($messages);
123
                }
124

125 1
                if (! is_string($message)) {
126 1
                    $this->invalidMessageArgument($messages);
127
                }
128
            }
129
        }
130
    }
131

132
    /**
133
     * @param  mixed  $messages Whatever faulty value was given for messages
134
     * @throws DefinitionException
135
     */
136 1
    protected function invalidMessageArgument($messages): void
137
    {
138 1
        $encoded = \Safe\json_encode($messages);
139 1
        throw new DefinitionException(
140 1
            "The `messages` argument of @`{$this->name()}` on `{$this->nodeName()} must be a list of input values with the string keys `rule` and `message`, got: {$encoded}"
141
        );
142
    }
143

144
    /**
145
     * @param  mixed  $apply Any invalid value
146
     *
147
     * @throws \Nuwave\Lighthouse\Exceptions\DefinitionException
148
     */
149 1
    protected function invalidApplyArgument($apply): void
150
    {
151 1
        $encoded = \Safe\json_encode($apply);
152 1
        throw new DefinitionException(
153 1
            "The `apply` argument of @`{$this->name()}` on `{$this->nodeName()}` has to be a list of strings, got: {$encoded}"
154
        );
155
    }
156
}

Read our documentation on viewing source code .

Loading