mirror of
				https://github.com/yiisoft/yii2.git
				synced 2025-11-04 06:37:55 +08:00 
			
		
		
		
	Fixes #16766: yii\filters\ContentNegotiator was not setting Vary header to inform cache recipients
				
					
				
			This commit is contained in:
		@ -4,6 +4,7 @@ Yii Framework 2 Change Log
 | 
				
			|||||||
2.0.16 under development
 | 
					2.0.16 under development
 | 
				
			||||||
------------------------
 | 
					------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					- Bug #16766: `yii\filters\ContentNegotiator` was not setting `Vary` header to inform cache recipients (koteq, cebe, samdark)
 | 
				
			||||||
- Bug #11960: Fixed `checked` option ignore in `yii\helpers\BaseHtml::checkbox()` (misantron)
 | 
					- Bug #11960: Fixed `checked` option ignore in `yii\helpers\BaseHtml::checkbox()` (misantron)
 | 
				
			||||||
- Bug #14759: Fixed `yii\web\JsonResponseFormatter` output for `null` data (misantron)
 | 
					- Bug #14759: Fixed `yii\web\JsonResponseFormatter` output for `null` data (misantron)
 | 
				
			||||||
- Bug #16490: Fix schema on rbac init (marcelodeandrade)
 | 
					- Bug #16490: Fix schema on rbac init (marcelodeandrade)
 | 
				
			||||||
 | 
				
			|||||||
@ -154,9 +154,15 @@ class ContentNegotiator extends ActionFilter implements BootstrapInterface
 | 
				
			|||||||
        $request = $this->request ?: Yii::$app->getRequest();
 | 
					        $request = $this->request ?: Yii::$app->getRequest();
 | 
				
			||||||
        $response = $this->response ?: Yii::$app->getResponse();
 | 
					        $response = $this->response ?: Yii::$app->getResponse();
 | 
				
			||||||
        if (!empty($this->formats)) {
 | 
					        if (!empty($this->formats)) {
 | 
				
			||||||
 | 
					            if (\count($this->formats) > 1) {
 | 
				
			||||||
 | 
					                $response->getHeaders()->add('Vary', 'Accept');
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
            $this->negotiateContentType($request, $response);
 | 
					            $this->negotiateContentType($request, $response);
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
        if (!empty($this->languages)) {
 | 
					        if (!empty($this->languages)) {
 | 
				
			||||||
 | 
					            if (\count($this->languages) > 1) {
 | 
				
			||||||
 | 
					                $response->getHeaders()->add('Vary', 'Accept-Language');
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
            Yii::$app->language = $this->negotiateLanguage($request);
 | 
					            Yii::$app->language = $this->negotiateLanguage($request);
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
				
			|||||||
@ -76,4 +76,45 @@ class ContentNegotiatorTest extends TestCase
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
        $filter->beforeAction($action);
 | 
					        $filter->beforeAction($action);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    public function testVaryHeader()
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					        list($action, $filter) = $this->mockActionAndFilter();
 | 
				
			||||||
 | 
					        $filter->formats = [];
 | 
				
			||||||
 | 
					        $filter->languages = [];
 | 
				
			||||||
 | 
					        $filter->beforeAction($action);
 | 
				
			||||||
 | 
					        $this->assertFalse($filter->response->getHeaders()->has('Vary'));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        list($action, $filter) = $this->mockActionAndFilter();
 | 
				
			||||||
 | 
					        $filter->formats = ['application/json' => Response::FORMAT_JSON];
 | 
				
			||||||
 | 
					        $filter->languages = ['en'];
 | 
				
			||||||
 | 
					        $filter->beforeAction($action);
 | 
				
			||||||
 | 
					        $this->assertFalse($filter->response->getHeaders()->has('Vary'));  // There is still nothing to vary
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        list($action, $filter) = $this->mockActionAndFilter();
 | 
				
			||||||
 | 
					        $filter->formats = [
 | 
				
			||||||
 | 
					            'application/json' => Response::FORMAT_JSON,
 | 
				
			||||||
 | 
					            'application/xml' => Response::FORMAT_XML,
 | 
				
			||||||
 | 
					        ];
 | 
				
			||||||
 | 
					        $filter->languages = [];
 | 
				
			||||||
 | 
					        $filter->beforeAction($action);
 | 
				
			||||||
 | 
					        $this->assertContains('Accept', $filter->response->getHeaders()->get('Vary', [], false));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        list($action, $filter) = $this->mockActionAndFilter();
 | 
				
			||||||
 | 
					        $filter->formats = [];
 | 
				
			||||||
 | 
					        $filter->languages = ['en', 'de'];
 | 
				
			||||||
 | 
					        $filter->beforeAction($action);
 | 
				
			||||||
 | 
					        $this->assertContains('Accept-Language', $filter->response->getHeaders()->get('Vary', [], false));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        list($action, $filter) = $this->mockActionAndFilter();
 | 
				
			||||||
 | 
					        $filter->formats = [
 | 
				
			||||||
 | 
					            'application/json' => Response::FORMAT_JSON,
 | 
				
			||||||
 | 
					            'application/xml' => Response::FORMAT_XML,
 | 
				
			||||||
 | 
					        ];
 | 
				
			||||||
 | 
					        $filter->languages = ['en', 'de'];
 | 
				
			||||||
 | 
					        $filter->beforeAction($action);
 | 
				
			||||||
 | 
					        $varyHeader = $filter->response->getHeaders()->get('Vary', [], false);
 | 
				
			||||||
 | 
					        $this->assertContains('Accept', $varyHeader);
 | 
				
			||||||
 | 
					        $this->assertContains('Accept-Language', $varyHeader);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user