Testing request with CSRF Token in Play framework 2.5 (Scala)

匿名 (未验证) 提交于 2019-12-03 01:33:01

问题:

I'm stuck on a little problem with my functionnal testing.

I have a Play! 2.5 scala project in which I added CSRF verification on some forms, the associated scala-test units test failed, as expected, with the error :

java.lang.RuntimeException: No CSRF token present! 

I'm using FakeRequest with routes in order to test them :

val fakeRequest   = FakeRequest(GET, s"/backOffice/login") val Some(result)  = route(app, fakeRequest) 

How could I add the CRSF Token in order to render my test successful again ?

(Thank you, and sorry for bad english, I'm not native)

回答1:

Update : Like haui said in his comment :

Seems like they added something similar in play version 2.6. There you can use import play.api.test.CSRFTokenHelper._ FakeRequest().withCSRFToken (Scala) and CSRFTokenHelper.addCSRFToken(requestBuilder) (Java) as explained in the Migration guide

For people who are still in 2.5.6, my answer still apply :

So, after looking in Play-scala classes for a certain time, I finally found a way to adapt this answer : https://stackoverflow.com/a/19849420/4496364 to Play 2.5.6

I even made a trait, so if someone need it one day, here it is :

import play.api.Application import play.api.test.FakeRequest import play.filters.csrf.CSRF.Token import play.filters.csrf.{CSRFConfigProvider, CSRFFilter}  import scala.language.postfixOps  trait CSRFTest {   def addToken[T](fakeRequest: FakeRequest[T])(implicit app: Application) = {     val csrfConfig     = app.injector.instanceOf[CSRFConfigProvider].get     val csrfFilter     = app.injector.instanceOf[CSRFFilter]     val token          = csrfFilter.tokenProvider.generateToken      fakeRequest.copyFakeRequest(tags = fakeRequest.tags ++ Map(       Token.NameRequestTag  -> csrfConfig.tokenName,       Token.RequestTag      -> token     )).withHeaders((csrfConfig.headerName, token))   } } 

To use it, simply extend your test class with it, like this :

class LoginSpec extends PlaySpec with OneAppPerSuite /* or whatever OneApp */ with CSRFTest 

then, instead of calling

val fakeRequest = FakeRequest(/* params */) 

simply call

val fakeRequest = addToken(FakeRequest(/* params */)) 

I tried to make it look like the addToken{} in the Controller :)



标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!