IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Bases de données Delphi Discussion :

SELECT qui ne fonctionne pas, problème unicode ?


Sujet :

Bases de données Delphi

  1. #1
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut SELECT qui ne fonctionne pas, problème unicode ?
    Bonjour,

    Dans ma petite base de données SQLite, j'ai une table "Countries" avec des colonnes ID, Name et Url; j'insère mes données dans cette table avec ce bout de code:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    SQL.Text := 'INSERT OR IGNORE INTO Countries (Name, Url) VALUES (:p0, :p1);';
    Params[0].AsString := o.S['CountryName'];
    Params[1].AsString := o.S['CountryUrl'];
    ExecSQL;
    ("o" étant un ISuperObject)

    Le problème est qu'une fois les données insérées, si j'essaye de faire un...

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    SQL.Text := 'SELECT ID FROM Countries WHERE Name = :p0';
    Params[0].AsString := o.S['CountryName'];
    Open;
    iCountryID := Fields[0].AsInteger;
    ... ça ne marche pas (retourne "0" alors que l'entrée est bien présente dans la BDD avec un ID > 0) !

    Par contre si je fais...

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    SQL.Text := 'SELECT ID FROM Countries WHERE Name LIKE :p0';
    Params[0].AsString := o.S['CountryName'];
    Open;
    iCountryID := Fields[0].AsInteger;
    ... là ça marche !?

    J'ai l'impression que c'est un problème avec l'unicode, auriez-vous des suggestions pour m'en sortir ?

    PS: aperçus dans SQLiteSpy...







    EDIT: après vérification avec un autre outil (extension "SQLite Manager" pour Firefox), j'ai ces drôles de caractères invisibles dans mes cellules, savez-vous à quoi ils correspondent ?

  2. #2
    Expert confirmé
    Avatar de Ph. B.
    Homme Profil pro
    Freelance
    Inscrit en
    Avril 2002
    Messages
    1 784
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Freelance
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2002
    Messages : 1 784
    Points : 5 915
    Points
    5 915
    Par défaut
    Bonjour,
    Je pensais au cas où il y aurait des espaces en fin de champ.
    Quelle est la structure de la table (type des colonnes) ? char ou varchar ?
    As tu essayé (si SqLite l'accepte) ceci :
    Code sql : Sélectionner tout - Visualiser dans une fenêtre à part
    SELECT ID FROM Countries WHERE RTrim(Name) = :p0'
    ou en complémentant le paramètre avec le nombre d'espaces adéquats ?
    --
    Philippe.

  3. #3
    Expert confirmé
    Avatar de Ph. B.
    Homme Profil pro
    Freelance
    Inscrit en
    Avril 2002
    Messages
    1 784
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Freelance
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2002
    Messages : 1 784
    Points : 5 915
    Points
    5 915
    Par défaut
    Citation Envoyé par GoustiFruit Voir le message
    EDIT: après vérification avec un autre outil (extension "SQLite Manager" pour Firefox), j'ai ces drôles de caractères invisibles dans mes cellules, savez-vous à quoi ils correspondent ?
    Caractères de fin de chaines à zero terminal. Tu devrais transformer tes chaines avant de les passer en paramètres, en chaines Pascal en utilisant la fonction StrPas() de l'unité SysUtils
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    function StrPas(const Str:PChar):string;
    --
    Philippe.

  4. #4
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut
    Hum, ça ne passe pas :-\
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    E2251 Ambiguous overloaded call to 'StrPas'

  5. #5
    Membre chevronné Avatar de philnext
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    1 552
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 1 552
    Points : 1 780
    Points
    1 780
    Par défaut
    C'est quand même étrange comme fonctionnement ! Une petite idée (qui ne résoud pas le pb de fond) :
    Faire
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Params[0].AsString := Trim(o.S['CountryName']);

  6. #6
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut
    Non j'avais aussi pensé aux espaces, en fait c'est déjà trim-mé un peu avant (mais par acquis de conscience j'ai rajouté un Trim comme dans ton exemple).

    Bon avant d'essayer de retirer ce caractère, je vais essayer de comprendre à quel moment il est inséré (parce que ce n'est pas dans mon code !)... je vois deux possibilités, je vais faire des tests et je reviendrai plus tard. Merci de ton aide en attendant.

  7. #7
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut
    Ah ben il semblerait que c'était plutôt la troisième possibilité :-D

    Quoi que j'insère comme texte dans cette BDD, je me retrouve avec ce caractère et le SELECT ne fonctionne pas... J'utilisais le composant (Aducom SQlite) avec Delphi 7 sans soucis, là je suis avec D2010, je vais voir si il y a un problème de ce côté là...

  8. #8
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut
    Ca semble bien venir du composant: j'ai essayé avec un autre et le texte inséré dans la BDD n'a pas ce caractère superflu...
    Et le SELECT fonctionne bien dans ca cas là.

  9. #9
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 586
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 13 586
    Points : 25 262
    Points
    25 262
    Par défaut
    Ce composant (Aducom SQlite), tu as bien sûr télécharger la nouvelle version ?
    La version datant de D7 peut certes compiler mais peut ne pas fonctionner correctement !

    Vérifie aussi la connexion avec SQLite, voir si il fonctionne en ANSI (latin1, 8859-1 ou windows-1252) ou un UTF8 par exemple !
    Il faut aussi vérifier le Charset de stockage (indépendant du charset de connexion), idem vérifié ce qu'il utilise

    Fait aussi des Essais en utilisant explicitement des AnsiString à la place de simple String (qui sont en fait des UnicodeString)

    Pour le JSON pense aussi à regarder, il me semble qu'il y a fonctionnalités en standard avec XE2

  10. #10
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut
    Oui c'est bien la dernière version disponible, spécialement adaptée à Delphi 2009 et plus.

    J'ai déjà joué avec le charset de connexion (standard ou utf8).

    Et j'ai fait des essais en "typecastant" en AnsiString, mais bon, comme ce sont des requêtes paramétrées, au final je n'ai pas mon mot sur le type puisque ça passe par .AsString !? Ex:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    with MyQry do begin
      SQL.Text := 'INSERT OR IGNORE INTO Countries (Name, Url) VALUES (:p0, :p1);';
      StartTransaction;
      for i1 := 0 to 99 do begin
        Params[0].AsString := AnsiString('Pays' + IntToStr(Random(10000)));
        Params[1].AsString := 'Url' + IntToStr(Random(10000));
        ExecSQL;
      end;
      Commit;
    end;
    J'ai le même résultat dans les deux colonnes, les chaînes terminées par des #0 (enfin je suppose que c'est un #0, le caractère affiché dans l'extension SQLite Manager le laisse croire).

    Pour le JSON pour l'instant je suis en Delphi 2010 et SuperObject fonctionne très bien pour mes besoins... le seul (gros !) inconvénient c'est que son auteur n'est franchement pas aimable, je n'ai pas encore osé m'inscrire sur son forum tellement il est mauvais... enfin c'est peut-être une tactique à lui pour éviter de se laisser envahir, tactique qui vu le nombre de messages semble efficace... bref)

  11. #11
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 586
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 13 586
    Points : 25 262
    Points
    25 262
    Par défaut
    Il existe aussi AsAnsiString pour gérer la compatibilité dans le TParam

    Je pense que c'est même deux Zéro en fait, l'Unicode utilise deux zéros pour se terminer
    Le caractère de remplacement du simple zéro c'est un symbole nul (idem un petit nul dans un carré), la comme c'est 00 00 !

  12. #12
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut
    Dire que je n'ai même pas voulu taper "AsAn..." pour voir si le CodeInsight me proposait AsAnsiString tellement j'étais certain que ce n'était pas le cas... Ben en effet ça existe, et en plus ça marche !
    Mais je ne suis pas sûr que ce soit la meilleure méthode, d'abord ça me cause un warning à la compilation et je n'aime pas les warnings (typecast de string en ansistring pouvant causer des pertes de données) et ensuite si je veux effectivement stocker du unicode, le SELECT ne fonctionnera toujours pas Et pourquoi, oh pourquoi, ça fonctionne avec l'autre composant/unité que j'ai testé ? (pour info, SQLite3 4 Delphi v1.0, sur http://www.torry.net/pages.php?id=1173)
    Je crois que je vais bêtement passer à ce dernier, même si il est tout récent, il reste simple d'utilisation, j'ai pu adapter mon code très rapidement...

  13. #13
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 586
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 13 586
    Points : 25 262
    Points
    25 262
    Par défaut
    Cela vient de l'implémentation des composants
    Le TDataSet, le TParam ... c'est des classes abstraites, des coquilles vides qui imposent un mécanisme, mais ensuite chaque bibliothèque va implémenter sa solution et il est possible que tous les cas ne soient pas testés à chaque nouvelle version du compilateur ou de la lib, et que chez certaines personnes des étrangetés apparaissent

    Là où je bosse, on a eu le même problème, en fait depuis 5 (ou plus), l'application utilise le DSN ODBC pour accéder à Sybase avec DBExpress, dans la conf du DSN cela indique le CharSet cp863 (un truc historique d'une ancienne version de Sybase)
    En fait, je me suis rendu compte que la base ne stockait pas vraiment du cp863 mais du Windows-1252, tous les API utilisant le DSN gérait correctement les accents (BDE, DBExpress ainsi que Crystal Report) mais les outils Sybase eux montraient les vrais données, en fait, depuis des années l'application fonctionnaient plus ou moins en exploitant ce que je considère comme un Bug !

    Lors du passage de C++Builder 2007 à XE2, il semble que l'on ne peut plus indiquer un DSN ODBC comme base dans DBExpress mais seulement le vrai nom de la Base (*)
    Et là patatra, mon responsable constate à son tour ces erreurs d'accents, la solution au final pour le moment, c'est extraction de la DB, création d'une DB en Windows1252 et non cp863, modification des fichiers exportés pour retirer le marquer cp863 puis importation
    La DB étant des données embarqués, ça fait un petit Mo, l'opération n'est donc pas douloureuse !

    (*) Si quelqu'un sait quelque chose à ce sujet, cela m'intéresse quand même !

  14. #14
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut
    Bah de toutes façons je n'ai pas les compétences pour essayer de corriger le bin's. J'ai signalé le problème chez Aducom, maintenant je vais essayer avec SQlite 4 Delphi, en espérant ne pas rencontrer un nouveau problème insoluble (pour moi) en cours de route.

  15. #15
    Membre chevronné Avatar de philnext
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    1 552
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 1 552
    Points : 1 780
    Points
    1 780
    Par défaut
    Ça va pas répondre à ta question mais tu peux jeter un coup d'oeil à mORMot qui est un ORM Delphi Open Source qui s'appuie sur SQLlite. C'est bien documenté et le développeur fait de bons softs et est réactif aux demandes. Je ne l'ai pas essayé, si tu jettes un coup d'oeil laisse une petite info...

  16. #16
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut
    Je connais, mais c'est trop pointu pour moi, et puis l'ORM ne correspond pas à mes besoins. C'est dommage parce que le framework propose aussi des outils JSON que j'utilise d'autre part, mais idem, c'est trop pointu pour moi. Et puis pendant que j'y suis, il propose aussi une unité implémentant WinHTTP qui pourrait m'être utile, mais toujours trop pointu pour moi. C'est de la pointure quoi :-D Mais j'aime bien consulter le forum de temps en temps, parce que ça discute pas mal d'optimisations en Delphi donc toujours intéressant...

  17. #17
    Membre éclairé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    707
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 707
    Points : 777
    Points
    777
    Par défaut
    Edit: j'ai commencé à rencontrer des problèmes avec "SQLite3 4 Delphi" - probablement de ma faute, j'ai du mal à comprendre certains aspects - du coup j'ai décidé de revenir aux composants Aducom: j'ai corrigé une petite ligne et maintenant ça marche. En fait je pense que je ne fais que countourner le problème, mais ça me suffit pour l'instant.

Discussions similaires

  1. Select qui ne fonctionne pas sur script VBS
    Par jamy69 dans le forum VBScript
    Réponses: 4
    Dernier message: 24/05/2012, 21h07
  2. Problème de htmlspecialchars qui ne fonctionne pas
    Par jeremie74 dans le forum Langage
    Réponses: 3
    Dernier message: 31/07/2006, 17h40
  3. requête de selection qui ne fonctionne pas
    Par emmablue dans le forum Requêtes et SQL.
    Réponses: 4
    Dernier message: 28/07/2006, 13h55
  4. [Dev-Pascal] Problème avec l'unité Graph (2 fenêtres et ReadKey qui ne fonctionne pas)
    Par Van der Elst dans le forum Autres IDE
    Réponses: 10
    Dernier message: 01/06/2006, 07h49
  5. [VBA-E]Select case qui ne fonctionne pas :(
    Par DonKnacki dans le forum Macros et VBA Excel
    Réponses: 20
    Dernier message: 31/01/2006, 12h13

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo