Ankündigung

Einklappen
Keine Ankündigung bisher.

Werte aus einer anderen Tabelle holen

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

  • Werte aus einer anderen Tabelle holen

    Hallo Forum,
    ich muss nach einiger Zeit eine bestehende CC Installation erweitern und habe irgendwie ein Brett vor´m Kopf. Ich hoffe jemand von Euch kann es mir abreißen!

    Ich habe 2 CC Kataloge. 1x Produktdaten und 1x Mitarbeiterdaten.

    Nun soll zu jedem Produkt 1 Mitarbeiter als Ansprechpartner zu diesem Produkt zugeordnet werden und später im Frontend beim Produkt entsprechend mit ausgegeben werden.
    Ich möchte das mit "offiiziellen" CC Methoden lösen und nicht direkt im Template php Datenbankabfragen einbauen.

    Mein Ansatz war, beim Inhaltselement für die Produktdaten, ein weiteres Feld "Datenbank-Auswahl" hinzuzufügen. Darüber kann ich dann später im Template problemlos, auf den verknüpften Wert aus der MItarbeiter Tabelle (z.B. Name) zugreifen.

    ABER: Ich möchte nicht nur einen Wert aus der Mitarbeiter-Tabelle im Leser-Template für die Produktdaten verwenden. Ich brauche auch die andereren Werte (Bild, E-Mail, etc),
    Wie komme ich da denn am elegantesten heran? Ich kriegs nicht hin das mit den SQL Insert Tags zu bauen und wäre dankbar für etwas Syntaxhilfe.
    Oder ist evtl.sogar ein ganz anderer Weg richtig?

    Vielen, vielen Dank schon mal für Eure Hilfe!


  • #2
    DB Auswahl ist schon mal gut. Damit haste auch gleich einen eindeutigen Wert in der DB, also nicht wie Tags einen Array. Damit geht eine direkte DB Abfrage:

    PHP-Code:
    $myValue $entry->field('myDbSelect')->value();

    $objResult = \Database::getInstance()->prepare("SELECT * FROM myTable_2 WHERE id=?")->limit(1)->execute($myValue);

    echo 
    $objResult->id// ist der gleiche Wert wie im SelectDb :)
    echo $objResult->name// Feldwert, Spalte Name 
    http://www.premium-contao-themes.com

    Kommentar


    • #3
      Cool, danke für Deine schnelle Antwort! Aber das ist ja doch wieder meine "klassische" php DB Abfrage. Was für mich vollkommen ok ist! Ich bin sehr dankbar, wenn Du diese Methode hier als die empfohlene angibst.
      Könntest Du mir bitte noch kurz helfen, wie ich jetzt noch sauber gerenderte Werte bekomme? Wenn ich z.B. ein Bild oder ein Tag in der abgefragten Datenbank habe, dann kommt mit der obigen Methode für diese Inhaltstypen noch nichts lesbares heraus.
      Danke Dir!

      Kommentar


      • #4
        Für ein Bild habe ich die Lösung gefunden:

        PHP-Code:
        <img class="bild" src="<?php echo $this->getImage(\FilesModel::findByUuid($objResult->bild)->path5050'center_center'?>" alt="">

        wobei "bild" der Name der Spalte in der angefragten Tabelle ist.
        Danke!

        Kommentar


        • #5
          Ein Bild ist ein binärer String. Tags sind serialisierte Arrays, die mit deserialize zurück gewandelt werden müssen.
          http://www.premium-contao-themes.com

          Kommentar


          • #6
            Ja, vielen Dank nochmal für Deine wirklich immer helfenden Hinweise!

            Für die Tags will ich auch noch kurz meine "Lösung" bereitstellen. Die "Schwierigkeit" hierbei war, dass in der verlinkten Tabelle für die Tags eben mehrere Werte (das serialisierte Array) stehen können und ich es nciht hinbekommen habe, auf direktem Weg die Datenbankabfrage zu machen (Wie kann ich das execute() für die Datenbankklasse direkt mit einem Array ausführen??).
            Ich habe mir also nur über eine Schleife helfen können ... aber .. die Werte stehen mir am Ende zur Verfügung und das zählt ja auch ein bissle ;-).

            PHP-Code:

            <?php
            $myTag 
            =  deserialize($objResult->katalognummer);
                    for (
            $i=0;$i<count($myTag);$i++) {
                        
            $objTagResult = \Database::getInstance()->prepare("SELECT katalognummer FROM tl_pct_customelement_tags WHERE id IN(?)")->execute($myTag[$i]);    
                        
            $objTag[] = $objTagResult->katalognummer;
                    }
            ?>

            <div class="test"><?php print_r($objTag); ?></div>    <!-- raw array zur Ergebniskontrolle-->

            Kommentar


            • #7
              Datt is falsch. In der tl_pct_customelement_tags gibts keine Spalte "katalognummer". phpmyadmin ist unerlässlich, wenn man den Aufbau nicht vor Augen hat.

              Um zu prüfen, ob ein gewisser Tag-Wert oder mehrere in einem Zieldatensatz enthalten sind (so arbeiten auch Filter), musst du den Zieldatensatz abfragen (im Härtefall ALLE durchgehen) und die entsprechende Zielspalte nach dem gesuchten Wert. Treffer dann sammeln

              ps. Eine for Schleife ist nicht verkehrt. Deutlich einfacher ist eine foreach Schleife direkt auf den Array.
              http://www.premium-contao-themes.com

              Kommentar


              • #8
                Yepp, datt is wirklich falsch. Korrekt muss es sein:
                PHP-Code:
                <?php
                $myTag 
                =  deserialize($objResult->katalognummer);
                        for (
                $i=0;$i<count($myTag);$i++) {
                            
                $objTagResult = \Database::getInstance()->prepare("SELECT title FROM tl_pct_customelement_tags WHERE id IN(?)")->execute($myTag[$i]);    
                            
                $objTag[] = $objTagResult->title;
                        }
                ?>

                <div class="test"><?php print_r($objTag); ?></div>    <!-- raw array zur Ergebniskontrolle-->
                katalognummer kommt aus der vorangegangene Abfrage (siehe Deine erste Antwort ganz oben) und ist das Feld in der verlinkten Tabelle, welches die Tags enthält.

                Danke für den Hinweis zur Prüfung auf bestimmte Tag-Werte. Kann ich bestimmt zukünftig mal brauchen.

                Kommentar


                • #9
                  Ein id IN sollte eine kommaliste fahren, nicht innerhalb einer Schleife aufgerufen werden. Hier öffnest du für jeden Eintrag im Tags array eine Datenbankabfrage. Nutzt man id IN(1,2,3,4...) ist es nur eine Abfrage für Alle kommenden Werte.
                  http://www.premium-contao-themes.com

                  Kommentar


                  • #10
                    Ja, das stimmt. Das steht da noch von meinen Versuchen die DB Abfrage in nur einem Schritt mit einem ->execute("InhaltDesArrays") hinzubekommen. Ich habe das Array aber nicht in ein passendes Format bekommen und es dann über die Schleife als Einzelabfrage gemacht. Dann ist ein IN() eigentlich überzogen und man kann es auf
                    PHP-Code:
                    $objTagResult = \Database::getInstance()->prepare("SELECT title FROM tl_pct_customelement_tags WHERE id=?")->execute($myTag[$i]); 
                    reduzieren.

                    Kommentar


                    • #11
                      So würde ich es schreiben:

                      PHP-Code:
                      $objTags =\Database::getInstance()->prepare("SELECT * FROM tl_pct_customelement_tags WHERE id IN(".implode(',',$arrTags).")")->execute();
                      while(
                      $objTags->next())
                      {
                      echo 
                      $objTags->title;

                      http://www.premium-contao-themes.com

                      Kommentar


                      • #12
                        Ich habe Deinen Hinweis zur Zielwertsuche weiter oben
                        Um zu prüfen, ob ein gewisser Tag-Wert oder mehrere in einem Zieldatensatz enthalten sind (so arbeiten auch Filter), musst du den Zieldatensatz abfragen (im Härtefall ALLE durchgehen) und die entsprechende Zielspalte nach dem gesuchten Wert. Treffer dann sammeln
                        mal verfolgt. Nicht ganz so trivial wie ich finde. Ich habe es dann mit Hilfe von Regular Expressions im SQL Query gelöst. So müsste auch ein guter Teil der Arbeit auf der SQL Server Seite liegen. Falls es es jemand mal brauchen kann:

                        PHP-Code:
                        <?php
                        $objSelf 
                        $this->field('id')->value(); //Objekt selbst nicht noch mal finden
                                
                        $myValue deserialize($this->field('myTags')->value());  //Abfragewerte finden
                                
                        $qryString ".*;s:[0-9]+:"A".*"//Querystring für die SQL Abfrage zusammenbauen > Zu suchende Tags in RegEx mit ODER zusammenbauen
                                
                        foreach ($myValue as $myValueTemp) {
                                    
                        $qryString $qryString "|.*;s:[0-9]+:"".$myValueTemp."".*";
                                    }

                                
                        $objResult = \Database::getInstance()->prepare("SELECT A.id from myTable A join tl_pct_customcatalog_language B
                                on A.id = B.id
                                where B.source = 'myTable'
                                AND B.lang = ?
                                AND A.id not like ?
                                AND A.myTags REGEXP ? order by RAND()"
                        )->limit(5)->execute($GLOBALS['TL_LANGUAGE'],$objSelf,$qryString);

                                while (
                        $objResult->next())
                                      {
                                       
                        ?>
                                         <div><?php echo $objResult->id?></div>
                                    <?php
                                    
                        }
                                    
                        ?>

                        Die Abfrage ist etwas komplizierter weil ich noch die Sprachabhängigkeit bei mir beachten musste aber prinzipiell scheint es mir mit Hilfe von REGEXP am einfachsten zu sein, die Datensätze zu finden. Oder spricht aus Deiner Sicht etwas dagegen?

                        Kommentar


                        • #13
                          Oh ha, dann schau dir mal lieber die Attribut Klassen an. Das ist hier wirklich sehr aufwendig gelöst für Mehrsprachigkeit (leider auch nicht vollständig richtig. Contaos Sprachvariable ist im BE != FE bei z.B. de_CH != de-CH).
                          Die Attribut Klasse bringt genug öffentliche Methoden mit, dass man sich all das sparen kann.

                          Speziell für Tags werden alle Übersetzungen in dem Übersetzungswidget (mit Contaos Name: MetaWizard) gespeichert je Datensatz. Dafür benötigt es keine extra DB Abfrage.
                          Einmal die PCT\CustomElements\Attributes\Tags anschauen, dort wird auch gezeigt, wie die mehrsprachigen Labels gesetzt werden. Diese sollten durch die Methode ->addTranslation auch im Attribut Objekt hinterlegt werden, was spätere erneute Abfragen überflüssig macht.
                          http://www.premium-contao-themes.com

                          Kommentar


                          • #14
                            Die Tags haben keine Mehrsprachigkeit. Das sind in dem Fall festehende Abkürzungen/Nummern. Für alle Sprachen identisch. Aber die Datensätze sind mehrsprachig und dadurch habe ich die Tags ja auch für jede Sprache 1x in "myTable". Ich begrenze die Suche hier nur auf die Einträge der aktuelle Sprache. Der join ist kein Ding.

                            Danke für die Zusatzinfos zur Mehrsprachigkeit bei Tags, dass kann sicher noch mal nützlich werden!

                            Kommentar

                            Lädt...