Skip to content

Commit

Permalink
feat: 支持直接返回 paginate/simplePaginate/cursorPaginate 数据
Browse files Browse the repository at this point in the history
  • Loading branch information
jiannei committed Oct 11, 2023
1 parent a4be287 commit 26cd36c
Show file tree
Hide file tree
Showing 3 changed files with 154 additions and 28 deletions.
41 changes: 31 additions & 10 deletions src/Support/Format.php
Original file line number Diff line number Diff line change
Expand Up @@ -88,9 +88,9 @@ public function data($data, ?string $message, int $code, $errors = null): array
*/
public function paginator(AbstractPaginator|AbstractCursorPaginator $resource, $transformer = null, $resourceName = null): array
{
$fractal = fractal()->collection($resource, $transformer ?: function ($item) {
return $item->toArray();
}, $resourceName)->serializeWith(DataArraySerializer::class);
$fractal = fractal()
->collection($resource, $transformer ?: fn($item) => $item->toArray(), $resourceName)
->serializeWith(DataArraySerializer::class);

return tap($fractal, $this->formatCollection($resource))->toArray();
}
Expand All @@ -105,9 +105,9 @@ public function paginator(AbstractPaginator|AbstractCursorPaginator $resource, $
*/
public function resourceCollection(ResourceCollection $collection, $transformer = null, $resourceName = null): array
{
$fractal = fractal()->collection($collection->resource, $transformer ?: function (JsonResource $resource) {
return array_merge_recursive($resource->resolve(request()), $resource->with(request()), $resource->additional);
}, $resourceName)->serializeWith(DataArraySerializer::class);
$fractal = fractal()
->collection($collection->resource, $transformer ?: $this->formatJsonResource(), $resourceName)
->serializeWith(DataArraySerializer::class);

return tap($fractal, $this->formatCollection($collection->resource))->toArray();
}
Expand All @@ -122,9 +122,12 @@ public function resourceCollection(ResourceCollection $collection, $transformer
*/
public function jsonResource(JsonResource $resource, $transformer = null, $resourceName = null): array
{
$data = array_merge_recursive($resource->resolve(request()), $resource->with(request()), $resource->additional);
$data = value($this->formatJsonResource(),$resource);

return fractal()->item($data, $transformer ?: fn () => $data, $resourceName)->serializeWith(ArraySerializer::class)->toArray();
return fractal()
->item($data, $transformer ?: fn () => $data, $resourceName)
->serializeWith(ArraySerializer::class)
->toArray();
}

/**
Expand Down Expand Up @@ -172,6 +175,24 @@ protected function formatStatusCode($code, string $from = 'success'): int
return (int) substr($from === 'fail' ? (Config::get('response.error_code') ?: $code) : $code, 0, 3);
}

/**
* Get JsonResource resource data.
*
* @return \Closure
*/
protected function formatJsonResource(): \Closure
{
return function (JsonResource $resource) {
return array_merge_recursive($resource->resolve(request()), $resource->with(request()), $resource->additional);
};
}

/**
* Format paginator data.
*
* @param $collection
* @return \Closure
*/
protected function formatCollection($collection): \Closure
{
return function (Fractal $item) use ($collection) {
Expand All @@ -189,8 +210,8 @@ protected function formatCollection($collection): \Closure
'per_page' => $collection->perPage(),
'current_page' => $collection->currentPage(),
'links' => array_filter([
'previous' => $paginated['prev_page_url'] ?? '',
'next' => $paginated['next_page_url'] ?? '',
'previous' => $collection->previousPageUrl(),
'next' => $collection->nextPageUrl(),
]),
],
]),
Expand Down
6 changes: 3 additions & 3 deletions src/Support/Traits/JsonResponseTrait.php
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ public function noContent(string $message = ''): JsonResponse
* @param int $option
* @return JsonResponse
*/
public function ok(string $message = '', int $code = 200, array $headers = [], int $option = 0)
public function ok(string $message = '', int $code = 200, array $headers = [], int $option = 0): JsonResponse
{
return $this->success([], $message, $code, $headers, $option);
}
Expand All @@ -86,15 +86,15 @@ public function ok(string $message = '', int $code = 200, array $headers = [], i
* @param int $option
* @return JsonResponse
*/
public function localize(int $code = 200, array $headers = [], int $option = 0)
public function localize(int $code = 200, array $headers = [], int $option = 0): JsonResponse
{
return $this->ok('', $code, $headers, $option);
}

/**
* Return a 400 bad request error.
*
* @param string|null $message
* @param string $message
*/
public function errorBadRequest(string $message = ''): void
{
Expand Down
135 changes: 120 additions & 15 deletions tests/SuccessTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
namespace Jiannei\Response\Laravel\Tests;

use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Support\Arr;
use Jiannei\Response\Laravel\Support\Facades\Response;
use Jiannei\Response\Laravel\Tests\Repositories\Enums\ResponseCodeEnum;
use Jiannei\Response\Laravel\Tests\Repositories\Models\User;
Expand Down Expand Up @@ -161,32 +162,29 @@ public function testSuccessWithPaginatedData()
{
// 方式八:返回分页的 Api collection
User::factory()->count(20)->create();
$users = User::paginate();
$users = User::query()->paginate();

$response = Response::success(new UserCollection($users));

$this->assertEquals(200, $response->status());

$paginated = $users->toArray();
$formatData = $users->map(function ($item) {
return [
'nickname' => $item->name,
'email' => $item->email,
];
})->all();
$formatData = Arr::map($users->items(),fn($item) => [
'nickname' => $item->name,
'email' => $item->email,
]);

$data = [
'data' => $formatData,
'meta' => [
'pagination' => [
'count' => $paginated['to'] ?? 0,
'per_page' => $paginated['per_page'] ?? 0,
'current_page' => $paginated['current_page'] ?? 0,
'total' => $paginated['total'] ?? 0,
'total_pages' => $paginated['last_page'] ?? 0,
'count' => $users->lastItem(),
'per_page' => $users->perPage(),
'current_page' => $users->currentPage(),
'total' => $users->total(),
'total_pages' => $users->lastPage(),
'links' => array_filter([
'previous' => $paginated['prev_page_url'] ?? '',
'next' => $paginated['next_page_url'] ?? '',
'previous' => $users->previousPageUrl(),
'next' => $users->nextPageUrl(),
]),
],
],
Expand Down Expand Up @@ -233,4 +231,111 @@ public function testSuccessWithCustomMessageAndCode()

$this->assertJsonStringEqualsJsonString($expectedJson, $response->getContent());
}

public function testLengthAwarePaginator()
{
User::factory()->count(20)->create();
$users = User::query()->paginate();

$response = Response::success($users);

$this->assertEquals(200, $response->status());

$formatData = Arr::map($users->items(),fn($item) => $item->toArray());

$data = [
'data' => $formatData,
'meta' => [
'pagination' => [
'count' => $users->lastItem(),
'per_page' => $users->perPage(),
'current_page' => $users->currentPage(),
'total' => $users->total(),
'total_pages' => $users->lastPage(),
'links' => array_filter([
'previous' => $users->previousPageUrl(),
'next' => $users->nextPageUrl(),
]),
],
],
];
$expectedJson = json_encode([
'status' => 'success',
'code' => 200,
'message' => ResponseCodeEnum::fromValue(200)->description,
'data' => $data,
'error' => (object) [],
]);

$this->assertJsonStringEqualsJsonString($expectedJson, $response->getContent());
}

public function testSimplePaginator()
{
User::factory()->count(20)->create();
$users = User::query()->simplePaginate();

$response = Response::success($users);

$this->assertEquals(200, $response->status());

$formatData = Arr::map($users->items(),fn($item) => $item->toArray());

$data = [
'data' => $formatData,
'meta' => [
'pagination' => [
'count' => $users->lastItem(),
'per_page' => $users->perPage(),
'current_page' => $users->currentPage(),
'links' => array_filter([
'previous' => $users->previousPageUrl(),
'next' => $users->nextPageUrl(),
]),
],
],
];
$expectedJson = json_encode([
'status' => 'success',
'code' => 200,
'message' => ResponseCodeEnum::fromValue(200)->description,
'data' => $data,
'error' => (object) [],
]);

$this->assertJsonStringEqualsJsonString($expectedJson, $response->getContent());
}

public function testCursorPaginator()
{
User::factory()->count(20)->create();
$users = User::query()->cursorPaginate();

$response = Response::success($users);

$this->assertEquals(200, $response->status());

$formatData = Arr::map($users->items(),fn($item) => $item->toArray());

$data = [
'data' => $formatData,
'meta' => [
'cursor' => [
'current' => $users->cursor()?->encode(),
'prev' => $users->previousCursor()?->encode(),
'next' => $users->nextCursor()?->encode(),
'count' => count($users->items())
],
],
];
$expectedJson = json_encode([
'status' => 'success',
'code' => 200,
'message' => ResponseCodeEnum::fromValue(200)->description,
'data' => $data,
'error' => (object) [],
]);

$this->assertJsonStringEqualsJsonString($expectedJson, $response->getContent());
}
}

0 comments on commit 26cd36c

Please sign in to comment.