Contao-Camp 2024
Ergebnis 1 bis 8 von 8

Thema: Routing -> User-ID des eingeloggten nutzers

  1. #1
    Contao-Nutzer Avatar von chatjack
    Registriert seit
    02.09.2012.
    Ort
    Essen
    Beiträge
    160

    Standard Routing -> User-ID des eingeloggten nutzers

    Hallo zusammen,

    ich schlage mich gerade etwas mit Routing in Verbindung mit einem eingeloggten Frontend-User herum.

    Es geht um eine Seite, über die eine Onlineschulung für eingeloggte Mitglieder stattfinden soll. Damit am Ende ein Zertifikat ausgestellt werden kann, soll das System in der Lage sein zu erkennen, wie lange ein User die Onlineschulung angesehen hat.

    Meine Idee war, dafür ein Routing auf eine URL einzurichten, die per JavaScript ein Mal pro Minute aufgerufen wird. Für den jeweils eingeloggten User sollen dann Daten in die Datenbank geschrieben werden.

    Ich habe es inzwischen hinbekommen ein Routing über eine eigene Erweiterung einzurichten.

    PHP-Code:
    <?php

    // src/Controller/UpdateMemberStatsController.php

    namespace BohnMedia\MemberStatsBundle\Controller;

    use 
    Contao\CoreBundle\Framework\ContaoFramework;
    use 
    Contao\FrontendUser;
    use 
    Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
    use 
    Symfony\Component\HttpFoundation\Response;
    use 
    Symfony\Component\HttpFoundation\Session\Session;

    class 
    UpdateMemberStatsController extends AbstractController
    {
        protected 
    $rootDir;
        protected 
    $session;
        protected 
    $framework;

        public function 
    __construct(string $rootDirSession $sessionContaoFramework $framework)
        {
            
    $this->rootDir      $rootDir;
            
    $this->session      $session;
            
    $this->framework    $framework;
        }

        public function 
    loadAction(): Response
        
    {

            
    // $objUser = FrontendUser::getInstance();

            
    return $this->json(['path' => 'it works']);

        }
    }
    Der Controller wurde in der services.yml registriert.

    Code:
    services:
        BohnMedia\MemberStatsBundle\Controller\UpdateMemberStatsController:
            arguments:
                - '%kernel.project_dir%'
                - "@session"
                - "@contao.framework"
            tags: ['controller.service_arguments']
            calls:
                - [setContainer, ['@service_container']]
    Die Route wurde wie folgt eingerichtet.

    Code:
    update_member_stats:
        path: /update_member_stats
        defaults:
            _controller: BohnMedia\MemberStatsBundle\Controller\UpdateMemberStatsController:loadAction
            _scope: frontend
            _token_check: true
    Zurzeit versuche ich, an die ID des im Frontend eingeloggten Nutzers zu kommen, was per "FrontendUser::getInstance()" in der Funktion "loadAction" auch bereits funktioniert, wenn man eingeloggt ist.

    PHP-Code:
    $objUser FrontendUser::getInstance();
    $userId $objUser->id
    Bin ich jedoch nicht eingeloggt, erhalte ich folgende Fehlermeldung.

    Code:
    Call to a member function get() on null
    Ausgelöst wird der Fehler in der FrontendUser.php in Zeile 89.

    PHP-Code:
    $objToken System::getContainer()->get('security.token_storage')->getToken(); 
    Nun bin ich mir nicht ganz sicher, ob FrontendUser hier überhaupt die richtige Herangehensweise ist.

    Ist der Weg hier korrekt oder gibt es einen eleganteren und vor allem auch sicheren Weg, hier zweifelsfrei an die ID des eingeloggten Nutzers innerhalb einer eigenen Route zu kommen?

    Danke und VG
    Dennis

  2. #2
    Contao-Nutzer Avatar von chatjack
    Registriert seit
    02.09.2012.
    Ort
    Essen
    Beiträge
    160

    Standard

    Ok, es läuft. Prüfe vor dem Ausführen von "FrontendUser::getInstance()" jetzt, ob (FE_USER_LOGGED_IN === true) ist. Zudem werden jetzt keine Argumente mehr übergeben.

    src/Resources/config/services.yml
    Code:
    services:
        BohnMedia\MemberStatsBundle\Controller\MemberStatsController:
            tags: ['controller.service_arguments']
            calls:
                - [setContainer, ['@service_container']]
    src/Resources/config/routing.yml
    Code:
    update_member_stats:
        path: /update_member_stats
        defaults:
            _controller: BohnMedia\MemberStatsBundle\Controller\MemberStatsController:update
            _scope: frontend
            _token_check: true
    src/Controller/MemberStatsController.php
    PHP-Code:
    <?php

    namespace BohnMedia\MemberStatsBundle\Controller;

    use 
    Contao\FrontendUser;
    use 
    Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
    use 
    Symfony\Component\HttpFoundation\Response;

    class 
    MemberStatsController extends AbstractController
    {

        public function 
    update(): Response
        
    {
            
    $userId "";

            
    // Get user id when user is logged in
            
    if (FE_USER_LOGGED_IN === true) {
                
    $objUser FrontendUser::getInstance();
                
    $userId $objUser->id;
            }
            
            
    // Return user id
            
    return $this->json(['userId' => $userId]);
        }
    }
    Bin für jeden Verbesserungsvorschlag dankbar.

    Viele Grüße
    Dennis

  3. #3
    Contao-Nutzer Avatar von chatjack
    Registriert seit
    02.09.2012.
    Ort
    Essen
    Beiträge
    160

    Standard

    Inzwischen bin ich auf eine elegantere Methode gestoßen.

    Der verwendete AbstractController von Symfony bietet die Funktion "getUser" an, über die die User-ID ebenfalls ermittelt werden kann.

    PHP-Code:
    <?php

    namespace BohnMedia\MemberStatsBundle\Controller;

    use 
    Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
    use 
    Symfony\Component\HttpFoundation\Response;

    class 
    MemberStatsController extends AbstractController
    {

        public function 
    update($page): Response
        
    {    
        
            
    // Get frontend user id
            
    $userId $this->getUser()->id;

            
    // Return user id
            
    return $this->json(['userId' => $userId]);
        }
    }

  4. #4
    Community-Moderator
    Wandelndes Contao-Lexikon
    Avatar von Spooky
    Registriert seit
    12.04.2012.
    Ort
    Scotland
    Beiträge
    33.896
    Partner-ID
    10107

    Standard

    Anstatt vom AbstractController erben zu müssen könntest du auch den Symfony Security Helper injecten: https://docs.contao.org/dev/referenc...ecurity-helper
    » sponsor me via GitHub or PayPal or Revolut

  5. #5
    Contao-Nutzer Avatar von chatjack
    Registriert seit
    02.09.2012.
    Ort
    Essen
    Beiträge
    160

    Standard

    Hallo Spooky,

    danke für den Tipp. Ich versuche gerade, in einem anderen Projekt jetzt mal per Security-Helper an die User-ID zu kommen, scheine hier aber noch etwas falsch zu machen.

    In der services.yml übergebe ich den Security-Helper.

    Code:
    services:
        App\Controller\ShowUserId:
            arguments:
                - '@security.helper'
            tags:
                - controller.service_arguments
    Innerhalb meiner Test-Klasse verwende ich dann, wie in der Dokumentation beschrieben, getUser() um an den eingeloggten Benutzer zu kommen.

    PHP-Code:
    <?php

    namespace App\Controller;

    use 
    Symfony\Component\HttpFoundation\Request;
    use 
    Symfony\Component\HttpFoundation\Response;
    use 
    Symfony\Component\Routing\Annotation\Route;
    use 
    Symfony\Component\Security\Core\Security;

    /**
     * @Route("/showUserId", name=ShowUserId::class)
     */
    class ShowUserId
    {
        private 
    $security;

        public function 
    __construct(Security $security)
        {
            
    $this->security $security;
        }

        public function 
    __invoke(Request $request): Response
        
    {
            
    var_dump($this->security->getUser());
            exit();
            
            return new 
    Response('ok'200);
        }
    }
    Leider gibt mir der var_dump hier NULL zurück, obwohl ich im Frontend angemeldet bin.

  6. #6
    Community-Moderator
    Wandelndes Contao-Lexikon
    Avatar von Spooky
    Registriert seit
    12.04.2012.
    Ort
    Scotland
    Beiträge
    33.896
    Partner-ID
    10107

    Standard

    Ja im Contao Frontend bist du angemeldet. Deine Route ist aber unabhängig, daher greift dort auch die Contao Firewall nicht mehr. Damit die Contao Firewall greift musst du den _scope auf frontend setzen
    » sponsor me via GitHub or PayPal or Revolut

  7. #7
    Contao-Nutzer Avatar von chatjack
    Registriert seit
    02.09.2012.
    Ort
    Essen
    Beiträge
    160

    Standard

    Genial, hat geklappt. Danke!

    services.yml
    Code:
    services:
        App\Controller\ShowUserId:
            arguments:
                - '@security.helper'
            tags:
                - controller.service_arguments
    ShowUserId.php
    PHP-Code:
    <?php

    namespace App\Controller;

    use 
    Symfony\Component\HttpFoundation\Request;
    use 
    Symfony\Component\HttpFoundation\Response;
    use 
    Symfony\Component\Routing\Annotation\Route;
    use 
    Symfony\Component\Security\Core\Security;

    /**
     * @Route("/showUserId", name=ShowUserId::class, defaults={"_scope": "frontend"})
     */
    class ShowUserId
    {
        private 
    $security;

        public function 
    __construct(Security $security)
        {
            
    $this->security $security;
        }

        public function 
    __invoke(Request $request): Response
        
    {
            
    $frontendUser $this->security->getUser();
            
            if (
    $frontendUser) {
                return new 
    Response($frontendUser->id200);
            } else {
                return new 
    Response("No user found"404);
            }
        }
    }

  8. #8
    Contao-Nutzer
    Registriert seit
    22.10.2021.
    Beiträge
    45

    Standard

    Zitat Zitat von chatjack Beitrag anzeigen
    Genial, hat geklappt. Danke!

    services.yml
    Code:
    services:
        App\Controller\ShowUserId:
            arguments:
                - '@security.helper'
            tags:
                - controller.service_arguments
    ShowUserId.php
    PHP-Code:
    <?php

    namespace App\Controller;

    use 
    Symfony\Component\HttpFoundation\Request;
    use 
    Symfony\Component\HttpFoundation\Response;
    use 
    Symfony\Component\Routing\Annotation\Route;
    use 
    Symfony\Component\Security\Core\Security;

    /**
     * @Route("/showUserId", name=ShowUserId::class, defaults={"_scope": "frontend"})
     */
    class ShowUserId
    {
        private 
    $security;

        public function 
    __construct(Security $security)
        {
            
    $this->security $security;
        }

        public function 
    __invoke(Request $request): Response
        
    {
            
    $frontendUser $this->security->getUser();
            
            if (
    $frontendUser) {
                return new 
    Response($frontendUser->id200);
            } else {
                return new 
    Response("No user found"404);
            }
        }
    }
    Ich habe gerade genau das selbe Problem.



    Ich bin im backend als Admin angemldet .... bekomme auch null zurück.


    PHP-Code:
        public function __construct(Security $security)
        {
            
    $this->security $security;
        } 

    PHP-Code:

        
    /**
         * @Route("/preview/{kitName}",
         *     defaults={"_scope": "frontend"}
         * )
         */
        
    public function myroute1($kitName)
        {
            
    $frontendUser $this->security->getUser();
            
    dump($frontendUser);

    Können bei einer Frontened Route nur Frontend User gefunden werden ?
    Wenn ich als admin auf die Route gehe wird nichts angezeigt ?
    Geändert von Medy (10.12.2021 um 16:21 Uhr)

Aktive Benutzer

Aktive Benutzer

Aktive Benutzer in diesem Thema: 1 (Registrierte Benutzer: 0, Gäste: 1)

Lesezeichen

Lesezeichen

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •