Magento 2:コントローラからのカスタムヘッダ/応答を送信する
-
13-12-2019 - |
質問
Magento 2では、コントローラexecute
メソッドから、カスタムヘッダーとエラーページを送信する要求を操作できます。
コンテキスト内容:特定のデータを返す小さな制限付きREST APIエンドポイントを実装しています。 New Magento 2 APIエンドポイントを使用したくない。 2.認証を設定する際のユーザーエクスペリエンス。 3.特定のアプリケーションをサポートするためのデータフォーマットを完全に制御します。そうすることを提案することは微笑み、そして丁寧に無視されます。
APIが不正な要求を受信したときに、適切な403の禁止された応答を送信したいと思います。
のようなことをすることができることを実感しますfunction execute()
{
if(not authorized)
{
header('HTTP/1.0 403 Forbidden');
echo "What are you doing here?";
exit;
}
}
.
しかし、特に実行の停止は他のイベントや発射からのMagentoプロセスを停止するため、理想よりも少なくなります。
ほとんどのPHPフレームワークは、カスタムヘッダと応答文字列を設定するために応答を直接操作する方法があります。
Magento 2は似たようなものを持っていますか?
もしそうであれば、コントローラのexecute
メソッドでそれを使用するための構文/手順/ベストプラクティスは何ですか?応答オブジェクトへの参照を取得して物事を設定するだけですか? execute
から特定のものを返す必要があります(標準ページファクトリの代わりに)。これを実行することをするためのより高いレベルの抽象化は、応答を操作する必要がないのですか?特定の例外を投げる? ETC。
解決
まず、Action Controller Interface \Magento\Framework\App\ActionInterface::execute()
に準拠するために、アクションは\Magento\Framework\Controller\ResultInterface
のインスタンスを返す必要があります(\Magento\Framework\App\ResponseInterface
もサポートされていますが、すべてのコアの使用法がリファクタリングされている場合はM2の将来のリリースで削除されます)。
では、\Magento\Framework\Controller\ResultInterface
の利用可能な実装から選択してください。カスタムREST APIに最も適している(JSONで動作させると仮定すると仮定して)\Magento\Framework\Controller\Result\Json
のようです。ただし、もっとカスタムが必要な場合は、\Magento\Framework\Controller\Result\Raw
を検討してください。
作業サンプル:
<?php
namespace VendorName\ModuleName\Controller;
/**
* Demo of authorization error for custom REST API
*/
class RestAuthorizationDemo extends \Magento\Framework\App\Action\Action
{
/** @var \Magento\Framework\Controller\Result\JsonFactory */
protected $jsonResultFactory;
public function __construct(
\Magento\Framework\App\Action\Context $context,
\Magento\Framework\Controller\Result\JsonFactory $jsonResultFactory
) {
parent::__construct($context);
$this->jsonResultFactory = $jsonResultFactory;
}
public function execute()
{
/** @var \Magento\Framework\Controller\Result\Json $result */
$result = $this->jsonResultFactory->create();
/** You may introduce your own constants for this custom REST API */
$result->setHttpResponseCode(\Magento\Framework\Webapi\Exception::HTTP_FORBIDDEN);
$result->setData(['error_message' => __('What are you doing here?')]);
return $result;
}
}
.
上記のコードは、HTTPステータスコード403
とBody {"error_message":"What are you doing here?"}
他のヒント
Magento 2は、依存性注入を介してインスタンス化するためのMagento\Framework\App\ResponseInterface
抽象タイプを提供します。単純さのために以下で使用されるオブジェクトマネージャ。
/** @var \Magento\Framework\App\ObjectManager $om */
$om = \Magento\Framework\App\ObjectManager::getInstance();
/** @var \Magento\Framework\App\ResponseInterface|\Magento\Framework\App\Response\Http $response */
$response = $om->get('Magento\Framework\App\ResponseInterface');
$response->setHeader('<header name>', '<header value>', $overwriteExisting = true);
.
例えば
です$response->setHeader('Content-Transfer-Encoding', 'binary', true);
.
ステータスヘッダーは特別な場合と見なされます - ここにsetStatusCode
メッセージを使用する必要があります。また、ControllerのgetResponse
メッセージにアクセスできるため、コントローラに注入する乱雑なビジネスを避けることができます
public function execute()
{
$this->getResponse()
->setStatusCode(\Magento\Framework\App\Response\Http::STATUS_CODE_403)
->setContent('Error');
return ;
}
. Magento 2.1以上、最も簡単な方法は結果ファクトリーを使用することです:
public function execute()
{
$resultPage = $this->resultFactory
->create(ResultFactory::TYPE_JSON)
->setHeader("myheaderkey", "value")
->setHttpResponseCode(403);
return $resultPage;
}
.
\Magento\Framework\App\Action\Action
の継承のため、ResultFactoryはすでにコントローラに注入されています。
さらに、あなたはMagento\Framework\Controller\ResultInterface
に対してプログラミングされています。