Ankündigung

Einklappen
Keine Ankündigung bisher.

[erledigt] Fehlermeldung, wenn ich zweimal den selben Konstruktor aufrufe [Doctrine]

Einklappen

Neue Werbung 2019

Einklappen
X
  • Filter
  • Zeit
  • Anzeigen
Alles löschen
neue Beiträge

  • [erledigt] Fehlermeldung, wenn ich zweimal den selben Konstruktor aufrufe [Doctrine]

    Ich bekomme folgende Fehlermeldung:

    Code:
    Warning: Trying to access array offset on value of type bool in D:\xampp\htdocs\forum\src\controller\controller.php on line 13
    
    Fatal error: Uncaught Error: Value of type null is not callable in D:\xampp\htdocs\forum\src\controller\controller.php:13 Stack trace: #0 D:\xampp\htdocs\forum\src\controller\userController.php(9): Controller->__construct() #1 D:\xampp\htdocs\forum\src\controller\messageSteuerung.php(11): UserController->__construct() #2 D:\xampp\htdocs\forum\index.php(3): require_once('D:\\xampp\\htdocs...') #3 {main} thrown in D:\xampp\htdocs\forum\src\controller\controller.php on line 13
    Ich vermute, es liegt daran, dass ich zweimal folgende Zeile ausführe.

    PHP-Code:
    $container = require_once __DIR__ '/../../config/db-config.php';
            
    $em $container[\Doctrine\ORM\EntityManagerInterface::class](); 
    Mein Aufbau:

    PHP-Code:
    <?php
    use Doctrine\ORM\Tools\SchemaTool;
    require_once 
    __DIR__ '/../../config/smarty.php';

    /** @var \Doctrine\ORM\EntityManager $entityManager */
    class Controller
    {
        protected 
    $em;

        function 
    __construct()
        {
            
    $container = require_once __DIR__ '/../../config/db-config.php';
            
    $em $container[\Doctrine\ORM\EntityManagerInterface::class]();

        }

        protected function 
    persistenceDB()
        {
            try {
                
    $this->em->flush();
            } catch (
    Exception $e) {
                echo 
    $e->getMessage();
                die();
            }
        }
    }
    ?>
    PHP-Code:
    <?php
    use model\message;
    require_once 
    'controller.php';
    require_once 
    'userController.php';

    class 
    MessageController extends Controller
    {

        function 
    __construct()
        {
            
    parent::__construct();
        }

        public function 
    getAllMessages()
        {
            return 
    $this->em->getRepository(Message::class)->findAll();
        }

        public function 
    findMessageByFromUser($user)
        {
            return 
    $this->em->getRepository(Message::class)->findBy(array(
                
    'fromUser' => $user
            
    ));
        }

        public function 
    findSentMessages($user)
        {
            return 
    $this->em->getRepository(Message::class)->findBy(array(
                
    'fromUser' => $user
            
    ));
        }

        public function 
    findMessageById($id)
        {
            return 
    $this->em->find(Message::class, $id);
        }

        public function 
    addMessage($message)
        {
            
    $this->em->persist($message);
            
    $this->persistenceDB();
        }

        public function 
    deleteMessage($message)
        {
            
    $this->em->remove($message);
            
    $this->persistenceDB();
        }
    }

    ?>
    Folgende PHP-Datei wird gestartet:
    PHP-Code:
    <?php
    require_once 'messageController.php';
    require_once 
    'userController.php';

    $messageController = new MessageController();

    $userController = new UserController();
    $user1 $userController->findUserById(1);
    $user2 $userController->findUserById(2);
    $message = new Message("Betreff""Dies ist eine Nachricht"date("d.m.Y H:i:s"), $user1$user2);
    $messageController->addMessage($message);
    $messages $messageController->getAllMessages();

    $smarty->assign('messages'$messages);
    $smarty->display('message.tpl');
    ?>

    PHP-Code:
    <?php
    use model\user;
    require_once 
    'controller.php';

    class 
    UserController extends Controller
    {

        function 
    __construct(){
            
    parent::__construct();
        }

        public function 
    getAllUsers()
        {
            return 
    $this->em->getRepository(User::class)->findAll();
        }

        public function 
    findUsersByUserName($userName)
        {
            return 
    $this->em->getRepository(User::class)->findBy(array(
                
    'username' => $userName
            
    ));
        }

        public function 
    findUserById($id)
        {
            return 
    $this->em->find(User::class, $id);
        }

        public function 
    addUser($user)
        {
            
    $this->em->persist($user);
            
    $this->persistenceDB();
        }

        public function 
    deleteUser($user)
        {
            
    $this->em->remove($user);
            
    $this->persistenceDB();
        }
    }
    ?>
    Was genau ist das Problem daran es zweimal aufzurufen?? Und wie kann ich es verhindern?

    PHP-Code:
    $messageController = new MessageController();

    $userController = new UserController(); 
    Hier scheint das Problem wenn ich die Zeile $userController = new userController(); rausnehme, kkommt nicht die Fehlermeldung. Aber durch das Anlegen des Objektes userController wird der Kontruktor vom Controller aufgerufen und dann knallt es, weil man diesen Befehl wohl nicht ein 2. mal aufrufen darf.

  • #2
    Wie der Name schon sagt wird require once nur einmal zu Laufzeit ausgeführt. Besser wäre es den Container dem Konstruktor zu übergeben. Noch besser wäre es wenn die Abhängigkeit als Konstruktor Parameter übergeben wird.

    Kommentar


    • #3
      Zitat von Zeichen32 Beitrag anzeigen
      Wie der Name schon sagt wird require once nur einmal zu Laufzeit ausgeführt. Besser wäre es den Container dem Konstruktor zu übergeben. Noch besser wäre es wenn die Abhängigkeit als Konstruktor Parameter übergeben wird.
      Sorry stehe gerade auf dem Schlauch, was genau soll ich übergeben?

      Kommentar


      • #4
        Zitat von Heisenberg85 Beitrag anzeigen
        Sorry stehe gerade auf dem Schlauch, was genau soll ich übergeben?
        Sauber wäre es den Entity Manager im Konstruktor zu übergeben.

        PHP-Code:
        $container = require_once __DIR__ '/../../config/db-config.php';
        $em $container[\Doctrine\ORM\EntityManagerInterface::class]();

        $messageController = new MessageController($em);
        $userController = new UserController($em); 
        Und der Konstruktor entsprechend:

        PHP-Code:
        public function __construct(\Doctrine\ORM\EntityManagerInterface $em)
        {
            
        $this->em $em;


        Nebenbei:
        1. das was du als "Controller" bezeichnest, ist von der derzeitigen Funktionalität ein "Repository". Du kannst die Repositories die Doctrine automatisch erstellt, auch manuell erweitern. (siehe Doku) Sowas wie $this->em->getRepository(User::class)->findByUserName(), ->findById() sind da aber auch schon von Hausee aus dabei.
        2.
        PHP-Code:
        try {
            
        $this->em->flush();
        } catch (
        Exception $e) {
            echo 
        $e->getMessage();
            die();

        Wenn du mit einer Exception nix sinnvolles anstellen kannst, dann Fang sie nicht. Eine unbehandelte Exception beendet das Script automatisch und wird je nach Konfigruation auch ausgegeben und/oder protokolliert. Mit dem Stück Code hast du dafür keine Kontrolle mehr und du nimmst dir jede Möglichkeit eventuell an anderer Stelle auf diesen Fehler zu reagieren.

        Kommentar


        • #5
          Ah ok danke, hat jetzt funktioniert,

          jetzt habe ich ein anders Problem. Ich versuche eine neue Message in die Tabelle zu schreiben. Und übergbebe als fromUser, toUser, 2 Userobjekte aud er Datenbank. Jetzt versucht er immer die User-Obejkte in die Tballe User zu schreiben. Das will ich ja nicht, der soll vorhandene User die ich vorher aus der Datenbank auslese, einfach nur als Ids in die Message Tabelle schreiben.

          Sieht so aus

          PHP-Code:
          $userController = new UserController($em);
          $messageController = new MessageController($em);



          $message = new Message("Betreff""Dies ist eine Nachricht", new DateTime(), $userController->findUserById(1), $userController->findUserById(2));
          $messageController->addMessage($message); 
          Das der Benutzername nur einmal vorkommen kann, bekomme ich natürlich folgende Fehlermeldung
          Code:
          An exception occurred while executing a query: SQLSTATE[23000]: Integrity constraint violation: 1062 Duplicate entry 'Betzi1985' for key 'UNIQ_8D93D649F85E0677'
          Aber wieso bekomme ich die?? Ich will doch nur, dass er eine neue Message schreibt, mit jeweils User1 udn User2, wieso versucht er auch zusätzlich einen neuen Benutzer zu schreiben???

          Kommentar


          • #6
            Das lässt sich anhand deines Codes nicht sagen. Ich denke mal, dass du ein Fehler in der Konfiguration oder den Entities hast. Der Fehler passiert meistens, wenn man mehrere Entity Manager mischt oder das Object vorher nicht durch den EntityManager abgefragt wurde. Im Grunde ist ist das Entity Doctrine zu der Zeit nicht bekannt und will daher ein neues anlegen.

            Kommentar


            • #7
              Das Problem war diese Zeile
              PHP-Code:
              em->persist($message
              es musste
              PHP-Code:
              em->merge($message
              heißen, warum auch immer.

              Kommentar

              Lädt...
              X