Eine SQL Abfrage für Sprache oder Alternativsprache

  • Eine SQL Abfrage für Sprache oder Alternativsprache

    Hallo zusammen

    Ich steh bei einer Datenbankabfrage an... Es geht darum, dass ich aus einer Tabelle alle Einträge einer Unterseite der Website in der gewählten Sprache auslesen möchte.

    Angenommen, ich habe eine Tabelle mit der folgenden Struktur:
    id key lang text
    1 form1_eintrag1 de Dies ist mein erster Text
    2 form1_eintrag1 en This is my first text
    3 form1_eintrag2 de Zweiter Text
    4 form1_eintrag2 en Second text
    5 form1_eintrag3 de Dritter Text
    6 form2_eintrag1 de Formular zwei, Eintrag 1
    7 form2_eintrag1 en Second form, first entry


    Die Standardsprache ist Deutsch (de); für jeden key ist sicher immer ein deutscher Eintrag in der Datenbank. Wenn aber z.B. Englisch gewählt ist (en), kann es sein, dass ein Eintrag noch nicht übersetzt wurde (z.B. ID 5). In diesem Fall soll für diesen key der deutsche Eintrag selektiert werden.

    Das Resultat sollte für den Bereich form1_ demnach so aussehen, wenn Deutsch gewählt wurde:
    1 form1_eintrag1 de Dies ist mein erster Text
    3 form1_eintrag2 de Zweiter Text
    5 form1_eintrag3 de Dritter Text


    Und so, wenn Englisch gewählt wurde:
    2 form1_eintrag1 en This is my first text
    4 form1_eintrag2 en Second text
    5 form1_eintrag3 de Dritter Text


    Ich hab's so probiert:
    SELECT * FROM `test` WHERE `key` LIKE 'form1_%' AND (`lang` = 'en' OR `lang` = 'de') GROUP BY `key`;

    Das ergibt folgendes Resultat:
    1 form1_eintrag1 de Dies ist mein erster Text
    3 form1_eintrag2 de Zweiter Text
    5 form1_eintrag3 de Dritter Text


    Wie kann ich das Resultat so sortieren, dass zuerst meine Abfrage auch für den zweiten Fall klappt? Es wäre natürlich wenn das Ganze auch funktionieren würde, wenn die Zweitsprache z.B. be wäre (also im Alphabet vor de).

    Ich bin froh um jeden Tipp!

    Herzlichen Dank und liebe Grüsse
    Michèle
  • Du brauchst erstmal eine Basis aller Schlüssel, sonst weißt du nicht welche überhaupt fehlen:

    Quellcode

    1. SELECT * FROM test WHERE lang = 'de'


    Das verknüpst du dann mit allen englischsprachigen Elementen, deren Schlüssel übereinstimmt

    Quellcode

    1. SELECT * FROM test A LEFT JOIN (SELECT * FROM test WHERE lang = 'en') B ON A.key = B.key WHERE lang = 'de';


    Dank dem LEFT JOIN stehen auf der rechten Seite Nullen, wenn kein Eintrag existiert
    Und wie entscheiden wir uns nun, was wir eigentlich selektieren? Mit einer IF Abfrage.

    Quellcode

    1. SELECT A.key, IF(ISNULL(B.lang), A.lang, B.lang) as lang FROM ....


    So in etwa wird das funktionieren ;)
  • Hallo d0nut

    Ganz lieben Dank für Deine rasche Antwort!

    Leider bin ich irgendwie zu blöd, um das nachvollziehen zu können. Deine Erklärungen glaube ich zu verstehen, aber die Umsetzung hapert, weil ich bisher keine Ahnung davon hatte, wie kompliziert so eine Abfrage sein kann... Ich kam bisher nicht über simple Select .. Where ... Abfragen hinaus.

    Wenn ich Deine Abfrage (auch schon die zweite) direkt eingebe, dann bekomm ich einen Syntax-Fehler zurück...

    Kannst Du mir evtl. erklären, was es mit diesem A und B auf sich hat? Ist das ein Alias? Müsste dann nicht noch ein AS davor stehen? Aber es klappt auch nicht mit AS davor, also ist es das wohl auch nicht... Ich hab auch schon probiert, statt dem Stern alle einzelnen Spalten anzugeben und jeweils einem Alias zuzuweisen, dann bekomme ich aber ebenfalls den Syntax-Fehler. Hochkommas hab ich auch reingenommen.

    Ich werde mich jetzt nochmals hinter die MySQL-Dokumentation klemmen. Vielleicht kannst Du mir in der Zwischenzeit nochmal einen kleinen Tipp geben, wo der Syntax-Fehler sein könnte? Das wäre ganz schön lieb!

    Also nochmals ganz lieben Dank!
    Michèle
  • oh klar, die WHERE Abfrage gehört ganz nach hinten.

    alt:

    Quellcode

    1. SELECT * FROM test A WHERE lang = 'de' LEFT JOIN (SELECT * FROM test WHERE lang = 'en') B ON A.key = B.key;

    neu:

    Quellcode

    1. SELECT * FROM test A LEFT JOIN (SELECT * FROM test WHERE lang = 'en') B ON A.key = B.key WHERE lang = 'de';


    Wenn noch ein Fehler kommt, poste bitte die Fehlermeldung.
    Hab mein Posting aktualisiert, damit du Erklärung und Lösung in einem Posting hast.

    Korrekt, bei A und B handelt es sich um Aliase. Kann man mit oder ohne AS schreiben.
    Eventuell musst du key noch als `key` schreiben, weils ein Schlüsselwort sein könnte.
  • Hallo d0nut

    Vielen Dank für Deine Hilfe!!! Du hast meinen Abend gerettet! *freu*

    MySQL meldete nach Eingabe der neuen Abfrage erst noch: Column 'lang' in where clause is ambiguous. Daher habe ich bei lang jeweils noch den Tabellennamen hinzugefügt, bis MySQL zufrieden war.

    Die fertige Abfrage sieht nun so aus:

    Quellcode

    1. SELECT A.id, A.key, IF(ISNULL(B.lang), A.lang, B.lang) AS lang, A.text FROM test A LEFT JOIN (SELECT `key`, `lang` FROM test WHERE test.lang = 'en') B ON A.key = B.key WHERE A.lang = 'de' AND A.key LIKE 'form1_%';


    Nochmals ganz herzlichen Dank!

    Einen schönen Abend allerseits!
    Michèle
  • Sprache / Alternativsprache per SELECT

    Kaum hatte ich offline meine Frage (hoffentlich) genau beschrieben um sie in diesem Forum zu posten, sehe ich daß sie schon gestellt wurde. Allerdings mit leicht verändertem Vorzeichen und leider hilft mir Donuts Lösung auch nicht weiter. Die Tabellenstruktur ist eine andere (2 Tabellen statt einer um keine redundanten Daten vorhalten zu müssen) und deshalb möchte ich versuchen den Subselect zu vermeiden den Donut vorgeschlagen hatte, da ich sonst für jede sprachabhängige Tabelle drei Tabellen abfragen müßte. Zudem halte ich die IF-Abfragen pro auszulesender Spalte für nicht sehr praktikabel wenn man einige zig Spalten ausliest.

    Hat da jemand noch eine Idee für mich???

    SPLIT BY D0NUT -> Hier gehts weiter