0

FosUserBundle works fine with the normal web/app_dev.php/login. I've implemented the AuthenticationHandler this way: here

My Angular sends a JSON request:

_csrf_token: "uSRZfxMycFCLKbxD_d9kgp-7WhM5ECrFyP6vtHDOle0"
_password: "welkom"
_submit: "security.login.submit"
_username: "erwin@eberhard.com"

The same data as the 'normal' login form which the FOSUserBundle provides. The CSRF-token is taken from the cookie:

_csrf_token = $cookies['XSRF-TOKEN'].  

It's the same token that lives serverside. It has been checked by var_dump(). The cookie is set in the controller:

    $engine = $this->container->get('templating');
    $content = $engine->render('ErwinEventManagerBundle:Default:index.html.twig', array('name' => "noname"));
    $csrf = $this->get('form.csrf_provider')->generateCsrfToken('authenticate');
    $response = new Response($content);
    $cookie = new Cookie("XSRF-TOKEN", $csrf, time() + 3600 * 24 , '/', null, false, false);
    $response->headers->setCookie($cookie);
    return $this->render('ErwinEventManagerBundle:Default:index.html.twig', array('name' => "noname"));

The response is:

 {"success":false,"message":"Invalid CSRF token."}

Request Headers:

Accept:application/json  
Accept-Encoding:gzip,deflate,sdch
Accept-Language:en-US,en;q=0.8,nl;q=0.6
Authorization:null
Connection:keep-alive
Content-Length:153
Content-Type:application/json;charset=UTF-8
Cookie:XSRF-TOKEN=uSRZfxMycFCLKbxD_d9kgp-7WhM5ECrFyP6vtHDOle0;  
PHPSESSID=o9dc41tglf9dkl07fv7pdjp545
Host:erwin.com
Origin:http://erwin.com
Referer:http://erwin.com/Symfony/web/app_dev.php/
User-Agent:Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko)   
Chrome/35.0.1916.153 Safari/537.36
X-Requested-With:XMLHttpRequest
X-XSRF-TOKEN:uSRZfxMycFCLKbxD_d9kgp-7WhM5ECrFyP6vtHDOle0

My config.yml contains:

framework:
#    #esi:             ~
#    #translator:      { fallback: "%locale%" }
    secret:          "%secret%"
router:
    resource: "%kernel.root_dir%/config/routing.yml"
    strict_requirements: ~
form:            ~
csrf_protection: ~
validation:      { enable_annotations: true }
templating:
    engines: ['twig']
    #assets_version: SomeVersionScheme
    packages:
      jquery:
        base_urls:
#          http: [http://my.cdn.url]
          ssl: [ https://code.jquery.com ]
          http: [ http://code.jquery.com ]
      angular:
        base_urls:
          http: [ http://ajax.googleapis.com/ajax/libs/angularjs/1.2.16 ]
          http: [ https://ajax.googleapis.com/ajax/libs/angularjs/1.2.16 ]
default_locale:  "%locale%"
trusted_hosts:   ~
trusted_proxies: ~
session:
    # handler_id set to null will use default session handler from php.ini
    handler_id:  ~
fragments:       ~
http_method_override: true

My security.yml contains:

encoders:
    FOS\UserBundle\Model\UserInterface: sha512

role_hierarchy:
    ROLE_ADMIN:       ROLE_USER
    ROLE_SUPER_ADMIN: ROLE_ADMIN

providers:
    fos_userbundle:
#            id: fos_user.user_provider.username
        id: fos_user.user_provider.username_email

firewalls:
    main:
        pattern: ^/
        form_login:
#                check_path:      security_check_route
            success_handler: erwin_security.authentication_handler
            failure_handler: erwin_security.authentication_handler
            csrf_provider: form.csrf_provider
        logout:       true
        anonymous:    true

EDIT
After I removed CSRF I got Bad Credentials feedback. Ik add the form twice in my page. The 'normal' version works fine, the ajax-version not.

Community
  • 1
  • 1
erwineberhard
  • 309
  • 4
  • 17

1 Answers1

2

I hope this will help.
I had the same problem but with LexikJWTAuthenticationBundle
The 'normal' form works fine, the ajax-version not. (the form is posted to the check_path )
What I did :

Solution 1 : I installed symfony-json-request-transformer A Symfony 2 event listener for decoding JSON encoded request content.

Solution 2 : (Bad, don't do it, this is for debugging ! -) I modified this symfony listener : Symfony\Component\Security\Http\Firewall\UsernamePasswordFormAuthenticationListener Like this :

    protected function attemptAuthentication(Request $request) {

   // ...
    if ($request->isXmlHttpRequest()) {
        $request->request->replace(json_decode($request->getContent(), true));
    }
  // ...

  }

In AngularJS add : $http.post('path', credentials, {headers : {'X-Requested-with' : 'XMLHttpRequest'}}...

Mohamed Ramrami
  • 12,026
  • 4
  • 33
  • 49