Instantly share code, notes, and snippets.

Embed
What would you like to do?
Easily respond to content types and url extensions
<?php
namespace App\Http\Responses;
use App\Models\ContactType;
use App\Factories\CsvFactory;
class ContactIndexResponse extends Response
{
public function __construct($contacts)
{
$this->contacts = $contacts;
}
protected function toHtmlResponse()
{
return view('contacts.index', [
'contacts' => $this->contacts,
'types' => ContactType::all(),
]);
}
protected function toJsonResponse()
{
return $this->contacts;
}
// can even inject dependencies
protected function toCsvResponse(CsvFactory $factory)
{
// returns another Responsable object!
return $factory->make($this->contacts);
}
}
<?php
namespace App\Http\Responses;
use Illuminate\Support\Arr;
use Illuminate\Support\Str;
use Illuminate\Contracts\Support\Responsable;
abstract class Response implements Responsable
{
public function toResponse($request)
{
$response = app()->call([$this, $this->responseMethod($request)], ['request' => $request]);
// recursively look for more responsable objects
while ($response instanceof Responsable) {
$response = $response->toResponse($request);
}
return $response;
}
protected function responseMethod($request)
{
return 'to'.Str::studly($this->contentType($request)).'Response';
}
protected function contentType($request)
{
return $this->urlContentType($request) ?? $request->format();
}
protected function urlContentType($request)
{
return $this->extension($this->filename($request));
}
protected function extension($filename)
{
if (Str::contains($filename, '.')) {
return Arr::last(explode('.', $filename));
}
}
protected function filename($request)
{
return Arr::last(explode('/', $request->url()));
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment