Skip to content

Commit 009eda3

Browse files
committed
fix: no index in repository
1 parent d3ac977 commit 009eda3

21 files changed

+390
-243
lines changed

src/Eager/Related.php

Lines changed: 6 additions & 74 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@
77
use Binaryk\LaravelRestify\Http\Requests\RestifyRequest;
88
use Binaryk\LaravelRestify\MCP\Requests\McpRequest;
99
use Binaryk\LaravelRestify\Repositories\Repository;
10-
use Binaryk\LaravelRestify\Restify;
1110
use Binaryk\LaravelRestify\Traits\HasColumns;
1211
use Binaryk\LaravelRestify\Traits\Make;
1312
use Illuminate\Contracts\Database\Eloquent\Builder;
@@ -66,6 +65,7 @@ public function resolveField(Repository $repository): EagerField
6665
{
6766
return $this
6867
->field
68+
->forMcp($repository->isForMcp())
6969
->columns($this->getColumns())
7070
->resolve($repository);
7171
}
@@ -107,22 +107,22 @@ public function resolve(RestifyRequest $request, Repository $repository): self
107107
return $this;
108108
}
109109

110+
110111
switch ($paginator) {
111112
case $paginator instanceof Collection:
112-
$this->value = $this->serializeRelationshipData($request, $paginator);
113+
$this->value = $paginator;
113114

114115
break;
115116
case $paginator instanceof BelongsTo:
116-
$relatedModel = $paginator->first();
117-
$this->value = $relatedModel ? $this->serializeRelationshipData($request, $relatedModel) : null;
117+
$this->value = $paginator->first();
118118

119119
break;
120120
case $paginator instanceof Builder:
121-
$this->value = $this->serializeRelationshipData($request, $paginator->get());
121+
$this->value = $paginator->get();
122122

123123
break;
124124
default:
125-
$this->value = $this->serializeRelationshipData($request, $paginator);
125+
$this->value = $paginator;
126126
}
127127

128128
return $this;
@@ -135,74 +135,6 @@ public function resolveUsing(callable $resolver): self
135135
return $this;
136136
}
137137

138-
/**
139-
* Serialize relationship data using repository field collections for MCP requests.
140-
*/
141-
protected function serializeRelationshipData(RestifyRequest $request, $data)
142-
{
143-
// For non-MCP requests, return data as-is to maintain backward compatibility
144-
if (! $request instanceof McpRequest) {
145-
return $data;
146-
}
147-
148-
// Handle null data
149-
if (is_null($data)) {
150-
return null;
151-
}
152-
153-
// Handle single models
154-
if ($data instanceof \Illuminate\Database\Eloquent\Model) {
155-
return $this->serializeSingleModel($request, $data);
156-
}
157-
158-
// Handle collections
159-
if ($data instanceof Collection) {
160-
return $data->map(function ($model) use ($request) {
161-
return $model instanceof \Illuminate\Database\Eloquent\Model
162-
? $this->serializeSingleModel($request, $model)
163-
: $model;
164-
});
165-
}
166-
167-
return $data;
168-
}
169-
170-
/**
171-
* Serialize a single model using its repository's field collection for MCP requests.
172-
*/
173-
protected function serializeSingleModel(RestifyRequest $request, \Illuminate\Database\Eloquent\Model $model): array
174-
{
175-
// Try to find the repository for this model
176-
$repositoryClass = Restify::repositoryForModel($model);
177-
178-
if (! $repositoryClass) {
179-
// Fallback to model attributes if no repository found
180-
return $model->toArray();
181-
}
182-
183-
try {
184-
// Create repository instance with the model
185-
$repository = $repositoryClass::resolveWith($model);
186-
$repository->request = $request;
187-
188-
// Get the appropriate field collection for MCP index
189-
$fields = $repository->collectFields($request);
190-
191-
// Serialize using repository fields
192-
$result = [];
193-
foreach ($fields as $field) {
194-
$field->resolveForIndex($repository);
195-
$serialized = $field->serializeToValue($request);
196-
$result = array_merge($result, $serialized);
197-
}
198-
199-
return $result;
200-
} catch (\Exception $e) {
201-
// Fallback to model attributes if serialization fails
202-
return $model->toArray();
203-
}
204-
}
205-
206138
public function withRelatedQuery(RelatedQuery $relatedQuery): self
207139
{
208140
$this->relatedQuery = $relatedQuery;

src/Eager/RelatedCollection.php

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
use Binaryk\LaravelRestify\Fields\MorphToMany;
1212
use Binaryk\LaravelRestify\Filters\SortableFilter;
1313
use Binaryk\LaravelRestify\Http\Requests\RestifyRequest;
14+
use Binaryk\LaravelRestify\MCP\Concerns\HasMcpTools;
1415
use Binaryk\LaravelRestify\Repositories\Repository;
1516
use Illuminate\Support\Collection;
1617

@@ -97,6 +98,21 @@ public function forIndex(RestifyRequest $request, Repository $repository): self
9798
});
9899
}
99100

101+
public function forMcp(RestifyRequest $request, Repository $repository): self
102+
{
103+
return $this->filter(function (Related $related) {
104+
// If there's an EagerField, check its repository class
105+
if ($related->field && $related->field->repositoryClass) {
106+
return in_array(HasMcpTools::class, class_uses_recursive($related->field->repositoryClass), true);
107+
}
108+
109+
// For string relationships (without EagerField), we need to find the repository
110+
// This happens when relationships are defined as static::$related = ['user']
111+
// We'll allow these through and let the serialization handle the filtering
112+
return true;
113+
});
114+
}
115+
100116
public function inRequest(RestifyRequest $request, Repository $repository): self
101117
{
102118
return $this->filter(function (mixed $repositoryRelatedField, $repositoryRelatedKey) use (
@@ -129,6 +145,7 @@ public function inRequest(RestifyRequest $request, Repository $repository): self
129145
public function mapIntoRelated(RestifyRequest $request, Repository $repository): self
130146
{
131147
return $this->map(function ($value, $key) {
148+
ray($value)->green();
132149
return tap(
133150
Related::make($key, $value instanceof EagerField ? $value : null),
134151
function (Related $related) use ($value) {
@@ -167,7 +184,8 @@ public function forRequest(RestifyRequest $request, Repository $repository): sel
167184
->authorized($request)
168185
->inRequest($request, $repository)
169186
->when($request->isShowRequest(), fn (self $collection) => $collection->forShow($request, $repository))
170-
->when($request->isIndexRequest(), fn (self $collection) => $collection->forIndex($request, $repository));
187+
->when($request->isIndexRequest(), fn (self $collection) => $collection->forIndex($request, $repository))
188+
->when($repository->isForMcp(), fn (self $collection) => $collection->forIndex($request, $repository));
171189
}
172190

173191
public function unserialized(RestifyRequest $request, Repository $repository)

src/Fields/BelongsToMany.php

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
use Binaryk\LaravelRestify\Contracts\RestifySearchable;
66
use Binaryk\LaravelRestify\Fields\Concerns\Attachable;
77
use Binaryk\LaravelRestify\Http\Requests\RestifyRequest;
8+
use Binaryk\LaravelRestify\MCP\Requests\McpRequest;
89
use Binaryk\LaravelRestify\Repositories\PivotsCollection;
910
use Binaryk\LaravelRestify\Repositories\Repository;
1011
use Closure;
@@ -51,12 +52,19 @@ public function resolve($repository, $attribute = null)
5152

5253
$this->value = $paginator->map(function ($item) {
5354
try {
54-
return $this->repositoryClass::resolveWith($item)
55-
->allowToShow(app(Request::class))
55+
/**
56+
* @var Repository $repositoryFromClass
57+
*/
58+
$repositoryFromClass = $this->repositoryClass::resolveWith($item);
59+
60+
return $repositoryFromClass
61+
->allowToShow(
62+
$this->isForMcp() ? app(McpRequest::class) : app(RestifyRequest::class)
63+
)
5664
->withPivots(
5765
PivotsCollection::make($this->pivotFields)
58-
->map(fn (Field $field) => clone $field)
59-
->filter(fn (Field $field) => ! $field->isHidden(app(RestifyRequest::class)))
66+
->map(fn(Field $field) => clone $field)
67+
->filter(fn(Field $field) => ! $field->isHidden(app(RestifyRequest::class)))
6068
->resolveFromPivot($item->pivot)
6169
)
6270
->eager($this);

src/Fields/EagerField.php

Lines changed: 21 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,8 @@ class EagerField extends Field
3131

3232
private RelatedQuery $relatedQuery;
3333

34+
public bool $forMcp = false;
35+
3436
public function __construct($attribute, ?string $parentRepository = null)
3537
{
3638
parent::__construct(attribute: $attribute);
@@ -86,7 +88,7 @@ public function resolve($repository, $attribute = null)
8688
$serializableRepository = $this->repositoryClass::resolveWith($relatedModel);
8789

8890
$this->value = $serializableRepository
89-
->allowToShow($repository->request ?? app(Request::class))
91+
->allowToShow($this->isForMcp() ? app(McpRequest::class) : app(RestifyRequest::class))
9092
->columns()
9193
->eager($this);
9294
} catch (AuthorizationException) {
@@ -161,4 +163,22 @@ public function qualifySortable(RestifyRequest $request): ?string
161163

162164
return $table.'.attributes.'.$this->sortableColumn;
163165
}
166+
167+
public function forMcp(bool|callable $forMcp = false): self
168+
{
169+
if (is_callable($forMcp)) {
170+
$this->forMcp = $forMcp();
171+
172+
return $this;
173+
}
174+
175+
$this->forMcp = $forMcp;
176+
177+
return $this;
178+
}
179+
180+
public function isForMcp(): bool
181+
{
182+
return $this->forMcp;
183+
}
164184
}

src/MCP/Concerns/McpActionTool.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ public function actionTool(Action $action, array $arguments, McpActionRequest $a
6363

6464
public static function actionToolSchema(Action $action, ToolInputSchema $schema, McpActionRequest $mcpRequest): void
6565
{
66-
$modelName = class_basename(static::$model);
66+
$modelName = class_basename(static::guessModelClassName());
6767

6868
// Add action-specific validation rules
6969
$actionRules = $action->rules();

src/MCP/Concerns/McpDestroyTool.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ public function deleteTool(array $arguments, McpRequest $request): array
2525
public static function destroyToolSchema(ToolInputSchema $schema): void
2626
{
2727
$key = static::uriKey();
28-
$modelName = class_basename(static::$model);
28+
$modelName = class_basename(static::guessModelClassName());
2929

3030
$schema->string('id')
3131
->description("The ID of the $modelName to delete")

src/MCP/Concerns/McpGetterTool.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,7 +50,7 @@ public function getterTool(Getter $getter, array $arguments, McpGetterRequest $g
5050

5151
public static function getterToolSchema(Getter $getter, ToolInputSchema $schema, McpGetterRequest $mcpRequest): void
5252
{
53-
$modelName = class_basename(static::$model);
53+
$modelName = class_basename(static::guessModelClassName());
5454

5555
// Add getter-specific validation rules if the getter has a rules method
5656
if (method_exists($getter, 'rules')) {

src/MCP/Concerns/McpShowTool.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ public function showTool(array $arguments, McpRequest $request): array
3636

3737
public static function showToolSchema(ToolInputSchema $schema): void
3838
{
39-
$modelName = class_basename(static::$model);
39+
$modelName = class_basename(static::guessModelClassName());
4040

4141
$schema->string('id')
4242
->description("The ID of the $modelName to retrieve")

src/MCP/Concerns/McpStoreTool.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ public function storeTool(array $arguments, McpRequest $request): array
2121

2222
public static function storeToolSchema(ToolInputSchema $schema): void
2323
{
24-
$repository = static::resolveWith(app(static::$model));
24+
$repository = static::resolveWith(static::newModel());
2525

2626
$repository->collectFields($request = app(McpRequest::class))
2727
->forStore($request, $repository)

src/MCP/Concerns/McpUpdateTool.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ public function updateTool(array $arguments, McpRequest $request): array
2525
public static function updateToolSchema(ToolInputSchema $schema): void
2626
{
2727
$key = static::uriKey();
28-
$modelName = class_basename(static::$model);
28+
$modelName = class_basename(static::guessModelClassName());
2929

3030
$schema->string('id')
3131
->description("The ID of the $modelName to update")

0 commit comments

Comments
 (0)