1: <?php
2:
3: declare(strict_types=1);
4:
5: /**
6: * This file is part of the Nexus MCP SDK package.
7: *
8: * (c) 2026 John Paul E. Balandan, CPA <paulbalandan@gmail.com>
9: *
10: * For the full copyright and license information, please view
11: * the LICENSE file that was distributed with this source code.
12: */
13:
14: namespace Nexus\Mcp\Core\Schema\Prompt;
15:
16: use Nexus\Assert\Assert;
17: use Nexus\Mcp\Core\Schema\Arrayable;
18: use Nexus\Mcp\Core\Schema\BaseMetadata;
19:
20: /**
21: * Describes an argument that a prompt can accept.
22: *
23: * @implements Arrayable<array{
24: * name: non-empty-string,
25: * title?: non-empty-string,
26: * description?: non-empty-string,
27: * required?: bool,
28: * }>
29: *
30: * @see https://modelcontextprotocol.io/specification/2026-07-28/schema#promptargument
31: */
32: final readonly class PromptArgument extends BaseMetadata implements Arrayable
33: {
34: /**
35: * @param null|non-empty-string $description
36: */
37: public function __construct(
38: string $name,
39: ?string $title = null,
40: public ?string $description = null,
41: public ?bool $required = null,
42: ) {
43: parent::__construct(name: $name, title: $title);
44:
45: Assert::that($description)->nullOr()->isNonEmptyString('"arguments.description" must be a non-empty string or null.');
46: }
47:
48: #[\Override]
49: public static function fromArray(array $data): static
50: {
51: Assert::that($data)->hasOffset('name', '"arguments" is missing the required "name" key.');
52: $name = $data['name'];
53: Assert::that($name)->isNonEmptyString('"arguments.name" must be a non-empty string, {type} given.');
54:
55: $title = $data['title'] ?? null;
56: Assert::that($title)->nullOr()->isNonEmptyString('"arguments.title" must be a non-empty string or null, {type} given.');
57:
58: $description = $data['description'] ?? null;
59: Assert::that($description)->nullOr()->isNonEmptyString('"arguments.description" must be a non-empty string or null, {type} given.');
60:
61: $required = $data['required'] ?? null;
62: Assert::that($required)->nullOr()->isBool('"arguments.required" must be a bool or null, {type} given.');
63:
64: return new self(name: $name, title: $title, description: $description, required: $required);
65: }
66:
67: #[\Override]
68: public function toArray(): array
69: {
70: $data = ['name' => $this->name];
71:
72: if (null !== $this->title) {
73: $data['title'] = $this->title;
74: }
75:
76: if (null !== $this->description) {
77: $data['description'] = $this->description;
78: }
79:
80: if (null !== $this->required) {
81: $data['required'] = $this->required;
82: }
83:
84: return $data;
85: }
86:
87: #[\Override]
88: public function jsonSerialize(): array
89: {
90: return $this->toArray();
91: }
92: }
93: