55use Binaryk \LaravelRestify \Contracts \RestifySearchable ;
66use Binaryk \LaravelRestify \Controllers \RestResponse ;
77use Binaryk \LaravelRestify \Eager \Related ;
8+ use Binaryk \LaravelRestify \Eager \RelatedCollection ;
89use Binaryk \LaravelRestify \Exceptions \InstanceOfException ;
910use Binaryk \LaravelRestify \Fields \BelongsToMany ;
1011use Binaryk \LaravelRestify \Fields \EagerField ;
@@ -162,6 +163,13 @@ abstract class Repository implements RestifySearchable, JsonSerializable
162163 */
163164 public $ extraFields = [];
164165
166+ /**
167+ * A collection of pivots for the nested relationships.
168+ *
169+ * @var PivotsCollection
170+ */
171+ private PivotsCollection $ pivots ;
172+
165173 public function __construct ()
166174 {
167175 $ this ->bootIfNotBooted ();
@@ -320,6 +328,20 @@ public function withExtraFields(array $fields): self
320328 return $ this ;
321329 }
322330
331+ public function withPivots (PivotsCollection $ pivots ): self
332+ {
333+ $ this ->pivots = $ pivots ;
334+
335+ return $ this ;
336+ }
337+
338+ public function getPivots (): ?PivotsCollection
339+ {
340+ return isset ($ this ->pivots )
341+ ? $ this ->pivots
342+ : null ;
343+ }
344+
323345 public function withResource ($ resource )
324346 {
325347 $ this ->resource = $ resource ;
@@ -406,7 +428,7 @@ public function resolveShowAttributes(RestifyRequest $request)
406428 ->forShow ($ request , $ this )
407429 ->filter (fn (Field $ field ) => $ field ->authorize ($ request ))
408430 ->when (
409- $ this ->eagerState ,
431+ $ this ->isEagerState () ,
410432 function ($ items ) {
411433 return $ items ->filter (fn (Field $ field ) => ! $ field instanceof EagerField);
412434 }
@@ -502,10 +524,29 @@ public function resolveShowMeta($request)
502524 ];
503525 }
504526
527+ public function resolveShowPivots (RestifyRequest $ request ): array
528+ {
529+ if (is_null ($ pivots = $ this ->getPivots ())) {
530+ return [];
531+ }
532+
533+ return $ pivots
534+ ->filter (fn (Field $ field ) => $ field ->authorize ($ request ))
535+ ->each (fn (Field $ field ) => $ field ->resolve ($ this ))
536+ ->map (fn (Field $ field ) => $ field ->serializeToValue ($ request ))
537+ ->mapWithKeys (fn ($ value ) => $ value )
538+ ->all ();
539+ }
540+
541+ public function resolveIndexPivots (RestifyRequest $ request ): array
542+ {
543+ return $ this ->resolveShowPivots ($ request );
544+ }
545+
505546 /**
506547 * Return a list with relationship for the current model.
507548 *
508- * @param $request
549+ * @param RestifyRequest $request
509550 * @return array
510551 */
511552 public function resolveRelationships ($ request ): array
@@ -515,6 +556,12 @@ public function resolveRelationships($request): array
515556 static ::collectRelated ()
516557 ->authorized ($ request )
517558 ->inRequest ($ request )
559+ ->when ($ request ->isShowRequest (), function (RelatedCollection $ collection ) use ($ request ) {
560+ return $ collection ->forShow ($ request , $ this );
561+ })
562+ ->when ($ request ->isForRepositoryRequest (), function (RelatedCollection $ collection ) use ($ request ) {
563+ return $ collection ->forIndex ($ request , $ this );
564+ })
518565 ->mapIntoRelated ($ request )
519566 ->each (function (Related $ related ) use ($ request , $ withs ) {
520567 $ relation = $ related ->getRelation ();
@@ -749,7 +796,7 @@ public function attach(RestifyRequest $request, $repositoryId, Collection $pivot
749796
750797 static ::fillFields ($ request , $ pivot , $ fields );
751798
752- $ eagerField ->authorizeToAttach ($ request, $ pivot );
799+ $ eagerField ->authorizeToAttach ($ request );
753800
754801 return $ pivot ;
755802 })->each ->save ();
@@ -763,16 +810,10 @@ public function attach(RestifyRequest $request, $repositoryId, Collection $pivot
763810 public function detach (RestifyRequest $ request , $ repositoryId , Collection $ pivots )
764811 {
765812 /** * @var BelongsToMany $eagerField */
766- $ eagerField = $ request ->newRepository ()
767- ->collectFields ($ request )
768- ->filterForManyToManyRelations ($ request )
813+ $ eagerField = $ request ->newRepository ()::collectRelated ()
814+ ->forManyToManyRelations ($ request )
769815 ->firstWhere ('attribute ' , $ request ->relatedRepository );
770816
771- if (is_null ($ eagerField )) {
772- $ class = class_basename ($ request ->repository ());
773- abort (400 , "Missing BelongsToMany or MorphToMany field for [ {$ request ->relatedRepository }]. This field should be in the [ {$ class }] class. " );
774- }
775-
776817 $ deleted = DB ::transaction (function () use ($ pivots , $ eagerField , $ request ) {
777818 return $ pivots
778819 ->map (fn ($ pivot ) => $ eagerField ->authorizeToDetach ($ request , $ pivot ) && $ pivot ->delete ());
@@ -913,6 +954,7 @@ public function serializeForShow(RestifyRequest $request): array
913954 'attributes ' => $ request ->isShowRequest () ? $ this ->resolveShowAttributes ($ request ) : $ this ->resolveIndexAttributes ($ request ),
914955 'relationships ' => $ this ->when (value ($ related = $ this ->resolveRelationships ($ request )), $ related ),
915956 'meta ' => $ this ->when (value ($ meta = $ request ->isShowRequest () ? $ this ->resolveShowMeta ($ request ) : $ this ->resolveIndexMeta ($ request )), $ meta ),
957+ 'pivots ' => $ this ->when (value ($ pivots = $ this ->resolveShowPivots ($ request )), $ pivots ),
916958 ]);
917959 }
918960
@@ -924,6 +966,7 @@ public function serializeForIndex(RestifyRequest $request): array
924966 'attributes ' => $ this ->when ((bool ) $ attrs = $ this ->resolveIndexAttributes ($ request ), $ attrs ),
925967 'relationships ' => $ this ->when (value ($ related = $ this ->resolveIndexRelationships ($ request )), $ related ),
926968 'meta ' => $ this ->when (value ($ meta = $ this ->resolveIndexMeta ($ request )), $ meta ),
969+ 'pivots ' => $ this ->when (value ($ pivots = $ this ->resolveIndexPivots ($ request )), $ pivots ),
927970 ]);
928971 }
929972
0 commit comments