19

I have custom eloquent api resource for user. For example when I use this resource

Code

$user = $request->user();
return new UserResource($user);

Then on response I get:

{
    "data": {
        "name": "Margarete Daniel",
        "email": "goldner.berniece@example.net",
        "verified": "2020-03-20T07:15:56.000000Z"
    }
}

How I can change api resource and get example response:

{
    "name": "Margarete Daniel",
    "email": "goldner.berniece@example.net",
    "verified": "2020-03-20T07:15:56.000000Z"
}
Andreas Hunter
  • 4,504
  • 11
  • 65
  • 125

9 Answers9

52

Add this to your resource

public static $wrap = null;
Mustafa Akçakaya
  • 1,069
  • 2
  • 11
  • 12
  • 5
    This should be the accepted answer - this disables the data wrapping per resource rather than the entire application – Tricky Jun 22 '21 at 11:30
23

You can disable data wrapping by calling the withoutWrapping static method of your resource in the AppServiceProvider. In your case it will be:

public function boot()
{
    UserResource::withoutWrapping();
}

You can refer to Laravel documentation about data wrapping for more explanation.

22

Answering as I keep stumbling on the same problem myself.

The easiest way to return a Laravel resource without the data wrap is to simply return it in a JSON response. So instead of doing:

return new UserResource($user);

You would do:

return response()->json(new UserResource($user));

This way you also don't have to worry about stuffing your AppServiceProvider with a lot of calls to the withoutWrapping method.

J. Pinkman
  • 416
  • 4
  • 7
  • 2
    Why returning JsonResponse removes the wrap? Any link to documentation? – rock3t Aug 12 '21 at 13:29
  • @rock3t If you convert a resource to a JsonResponse manually (like the example above), JsonResponse assumes that there is always a $data property in the resource and uses it like `$resource->data`. That's why the unwrapping only happens when the resource is translated into the response by itself. i.e. `return new UserResource($user);` – Mustafa Akçakaya Nov 23 '21 at 14:05
15

To remove the data wrapper for all resources inside your project just add:

use Illuminate\Http\Resources\Json\JsonResource    

public function boot()
{
    JsonResource::withoutWrapping();
}

Inside the boot method of your AppServiceProvider.php.

Mattias
  • 576
  • 5
  • 8
8

this worked for me

return UserResource::make($user)->toArray($request);

and for collection

return UserResource::collection($users)->collection;
Ahmed Aboud
  • 1,232
  • 16
  • 19
4

For some reason this works:

$user = User::find(1);

return UserResource::make($user)->resolve();

Without ->resolve() it's not working.

trckster
  • 430
  • 1
  • 6
  • 11
2

For those like me who need to remove the wrapper on an ad-hoc basis (like using Inertia props), you can set the wrapper to null.

$comment = Comment::findOrFail(10);
$commentData = new CommentResource($comment);
$commentData->wrap(null);
return Inertia::render('Comment/Show', [
    'myExtraPropDatum' => 'extra_data',
    'comment' => $commentData,
]);
1
class MainBannerResource extends JsonResource
{
    public static $wrap = null;

    public function toArray(Request $request): array
    {
        return [
            'id' => $this->id,
            'created_at' => $this->created_at,
            'updated_at' => $this->updated_at,
        ];
    }
}

write public static $wrapp = null; for resource

  • Your answer could be improved with additional supporting information. Please [edit] to add further details, such as citations or documentation, so that others can confirm that your answer is correct. You can find more information on how to write good answers [in the help center](/help/how-to-answer). – Community Apr 13 '23 at 05:43
  • This is exactly what I was looking for. Removing the data key without globally removing it – Kolawole Emmanuel Izzy May 06 '23 at 06:05
1

use JsonResource::withoutWrapping(); or DeviceResource::withoutWrapping(); in your controller just before the response line

JsonResource::withoutWrapping();
return $this->response(JsonResource::make($reportArray),JsonResponse::HTTP_OK);

This way it will affect only your current resource response otherwise it will affect other responses too. If you want to wrap it in any other key you may use

JsonResource::wrap('reportData');

and it will use this key instead of data. Also you may add static $wrap = null; in the resource, file to avoid the data key.

Ahmed Memon
  • 120
  • 5