Philipp
Philipp

Reputation: 139

Encrypt REST Response Stream with Yii 2.0

I want to encrypt the response stream of a REST-Request. I fetch the data from the db and return it as xml (actionAll). This works fine. Then I added an eventHandler that is executed before the response is sent to the client (beforeAction). This works too. My problem is, that the $response within the encryptResponse-method does not contain any data, when the eventHandler calls it. The variables content, data and stream are always null within the response-object.

Thanks for any help!

<?php

namespace app\controllers;

use Yii;
use app\models\Order;
use yii\filters\auth\HttpBasicAuth;
use yii\web\Response;
use app\models\User;

class OrderController extends \yii\rest\Controller{

    /**
    * disable session for REST-Request
    * no loginUrl required  
    */
     public function init(){
        parent::init();
        \Yii::$app->user->enableSession = false;
        \Yii::$app->user->loginUrl = null;
    }

   /**
    * HttpBasicAuth for authentication  
    */
    public function behaviors(){
        $behaviors = parent::behaviors();
        $behaviors['authenticator'] = [
        'class' => HttpBasicAuth::className(),
        'auth'  => function ($username, $password) {
            if($username==\Yii::$app->params['HttpBasicAuth']['username'] &&     $password==\Yii::$app->params['HttpBasicAuth']['password']){
                return new User();
            }else{
                return null;
            }
        }];
        return $behaviors;
    }

   /**
    * set response-format to xml
    * fetch data from db
    *   
    */
    public function actionAll(){
        \Yii::$app->response->format = \yii\web\Response::FORMAT_XML;
        $models = Order::find()->all(); 
        return $models;
    }

   /**
    * hook into action and add event handler    
    */
    public function beforeAction($action){      
        $response = Yii::$app->getResponse();
        $response->on(Response::EVENT_BEFORE_SEND, [$this, 'encryptResponse']);
    }

   /**
    * callback for event-handler    
    */
    public function encryptResponse(){
        $response = Yii::$app->getResponse();
        var_dump($response);
    }   
}

Upvotes: 4

Views: 631

Answers (1)

BHoft
BHoft

Reputation: 1663

You can set your response event in the init.

Or you just have to add return true in your beforeAction function, otherwise data will be null because the action isn't called, this is also mentioned in the Yii2 docs here.

use Yii;

...

public function init() 
{
    parent::init();

    Yii::$app->user->enableSession = false;
    Yii::$app->user->loginUrl = null;
    Yii::$app->response->on(Response::EVENT_BEFORE_SEND, [$this, 'encryptResponse']);
}

public function beforeAction($action)
{      
    $response = Yii::$app->getResponse();
    $response->on(Response::EVENT_BEFORE_SEND, [$this, 'encryptResponse']);

    return true; // << required
}

Upvotes: 2

Related Questions