Entwickler-Ecke

Programmierwerkzeuge - ADO statt BDE


D. Annies - Do 16.07.09 21:12
Titel: ADO statt BDE
Hi, Delpher,

anbei mein erster (umständlicher?) Versuch mit den ADOTables:
Klappt soweit, aber ich habe die Fehlermeldung:
EOleException [Microsoft][ODBC-dBaseDriver] Syntaxfehler in FROM-Klausel



Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
31:
32:
33:
34:
35:
36:
37:
38:
39:
40:
41:
42:
43:
44:
45:
46:
47:
48:
49:
50:
51:
52:
53:
54:
55:
56:
57:
58:
59:
60:
61:
62:
63:
64:
65:
66:
67:
68:
69:
70:
71:
72:
73:
74:
75:
76:
77:
78:
79:
80:
81:
82:
83:
84:
85:
86:
87:
88:
89:
90:
91:
92:
93:
94:
95:
96:
97:
98:
99:
100:
101:
102:
103:
104:
105:
106:
107:
108:
109:
110:
111:
procedure TForm2.FormCreate(Sender: TObject);
var n : smallint;
begin
  bordericons := bordericons - [biminimize];
  home := getcurrentdir;
  showmessage('HOME = ' + home);
  label1.Caption := 'Hier werden die Punkte  ( = Summe ) eingetragen ' + #13 +
                    '     [und evtl. neue Schüler]' + #13 + #13 +
                    '  zur Auswertung --> den Button  [weiter]  betätigen';
  opendialog1.Filter := 'DBDateien (*.dbf)|*.dbf';

  ADOConnection1.ConnectionString :=
        'Provider=MSDASQL.1;Persist Security Info=False;User ID=an;'+
        'Data Source=dBASE-Dateien;'+
        'Initial Catalog=G:\BundesjugendspieleD;';

  ADOConnection1.CursorLocation := clUseClient;
  ADOConnection1.Mode := cmReadWrite;
  ADOConnection1.Provider := 'MSDASQL';

  ADODataset1.Connection := ADOConnection1;
  ADODataset1.CursorLocation := clUseClient;
  ADODataset1.DataSource := DataSource1;

  ADOTable1.Connection := ADOConnection1;
  ADOTable1.CursorLocation := clUseClient;

  if not fileexists(concat(home, '\''schule.dbf')) then
  begin
    if opendialog1.Execute then
    begin
      ADOtable2.Active := false;
        ADOtable2.TableName := opendialog1.filename;
          //ADOtable2.DatabaseName := 'schuelertss';  //'';
        ADOtable2.readonly := false;
      ADOtable2.active := true;

      chdir(home);

      with ADOTable1 do
      begin
        Active := False;
        //DatabaseName := '';  // !!!
        TableName := concat(home, '\''schule.dbf');
        //TableType := ttDefault;  //ttDBase;
        FieldDefs.Clear;
        FieldDefs.Add('Name',       ftString,   25, False);
        FieldDefs.Add('Vorname',    ftString,   25, False);
        FieldDefs.Add('Klasse',     ftString,    5, False);
        FieldDefs.Add('Geschlecht', ftString,    1, False);
        FieldDefs.Add('Gebdat',     ftString,   10, False); //ftDate ??
        FieldDefs.Add('Punkte',     ftinteger);
        //CreateTable;
        active := true;
      end;

      ADOtable2.First;
      while not ADOtable2.Eof do
      begin
        ADOtable1.append;
        ADOTable1.fieldbyname('NAME').asstring :=       ADOtable2.fieldbyname('NAME').asstring;
        ADOTable1.fieldbyname('VORNAME').asstring :=    ADOtable2.fieldbyname('VORNAME').asstring;
        ADOTable1.fieldbyname('KLASSE').asstring :=     ADOtable2.fieldbyname('KLASSE').asstring;
        ADOTable1.fieldbyname('GESCHLECHT').asstring := ADOtable2.fieldbyname('Geschlecht').asstring;
        ADOTable1.fieldbyname('GEBDAT').asstring :=     ADOtable2.fieldbyname('gebdat').asstring;
        ADOTable1.fieldbyname('PUNKTE').asinteger :=    0;
        ADOtable1.Post;
        ADOtable2.Next;
      end;
      showmessage('Tabelle ' + ADOtable1.TableName + ' ist erzeugt im Verzeichnis:' + getcurrentdir);
    end
  end;

  with ADOTable1 do
  begin
    Active := False;
      //DatabaseName := '';  // !!!
      TableName := concat(home, '\''schule.dbf');
    active := true;
  end;
  showmessage('Tabelle ' + ADOtable1.TableName + ' ist geladen aus Verzeichnis:' + getcurrentdir);

                         /////// Hier kommt die Fehlermeldung!

  //datasource1.dataset := ADOtable1;
  form1.Label21.Caption := extractfilename(ADOtable1.TableName);  //opendialog1.filename;
  sanz := ADOtable1.recordcount;
  form1.Label22.Caption := home;

  for n := 0 to dbgrid1.FieldCount-1 do
    dbgrid1.Columns[n].ReadOnly := true;
  dbgrid1.Columns[5].ReadOnly := false;
  dbgrid1.PopupMenu := NIL;

  listbox1.ItemIndex := 2;
  stringgrid1.Cells[0,0] := 'Nr';
  stringgrid1.Cells[1,0] := 'Punkte';
  stringgrid1.Cells[2,0] := 'Geschlecht';
  stringgrid1.Cells[3,0] := 'Klasse';
  stringgrid1.Cells[4,0] := 'Name';
  stringgrid1.Cells[5,0] := 'Vorname';

end;

procedure Tform2.qq1(sender:tobject);
begin
  //ADOquery1.DatabaseName := ADOtable1.DatabaseName;
  ADOquery1.Close;
    ADOquery1.SQL.Text := format('select * from "%s" order by klasse, name, vorname', [ADOTable1.tablename]);
  ADOquery1.Open;
end;


Kann mal jemand freundlicherweise Fehler-lesen? :?


koegi - Do 16.07.09 21:31

Hallo!

Meines Erachtens liegt der Fehler in den Anführungsstrichen vor und nach %s. Versuchs mal ohne die Anführungsstriche.

Viele Grüße

Thomas


D. Annies - Do 16.07.09 22:23

Hi, Thomas,
das war es leider nicht.
Gruß, Detlef


D. Annies - Fr 17.07.09 21:13

Gibt es denn ein paar andere Hinweise für mich oder ein Tutorium?
:( :roll: Gruß, Detlef


Muck - Fr 17.07.09 22:23

Hallo,

ich arbeite viel mit den ADO Komponenten, meistens jedoch mit MSSQL.

Was ist denn der Inhalt von AdoTable1.TableName?
Vielleicht stoert ja ein enthaltenes ".DBF" im SQL Command.

Am besten einfach mal mit einem konstanten SQL Command in der Function qq1 versuchen.

bis denne

Markus


Bronstein - Fr 17.07.09 22:33

Ich würde das so machen:

Delphi-Quelltext
1:
ADOquery1.SQL.Add('select * from '+ADOTable1.tablename+' order by klasse, name, vorname');                    


Muck - Fr 17.07.09 22:46

Hallo,

wenn ADOTable1.TableName den Inhalt z.B. 'Schule.dbf' hat erhaelts Du:

select * from Schule.dbf order by klasse, name, vorname

Ich weiss nicht welche Datenbank da benutzt wird, aber in MSSQL wuerde als Datenbank: 'Schule' und als Tabelle: 'dbf' gewertet.

Aber:
select * from Schule order by klasse, name, vorname

wuerde funktionieren. Mag sein, dass das der Grund ist.

bis denne

Markus

(editiert, war ein 'order' zuviel im SQL String)


D. Annies - Sa 18.07.09 08:50

Hi, Muck und Bronstein,

so, ich habe das jetzt, wie ihr gesagt habt, umgebaut, geht. :)
Das Programm startet jetzt, aber:
Jetzt habe ich (natürlich) einen anderen Fehler

Variante des Typs(Null) konnte nicht in Typ(String) konvertiert werden. :shock:

Keine Ahnung, wo das her kommt,
Detlef


eva13 - Do 03.09.09 15:36

Hallo Detlef

Solltest du bereits eine Lösung für dein Problem gefunden haben so ist meine Bemerkung für alle anderen die noch am Suchen sind.

Zitat:
ADOTable1.fieldbyname('NAME').asstring := ADOtable2.fieldbyname('NAME').asstring;


Sobald eine Kolonne in der Tabelle den Wert NULL hat bekommst du dieses Problem.
Am besten bereits im SQL-Command unterbinden, soweit die DB und/oder Provider es erlaubt.
Ich habe es in einer MSSQL-DB die folgende Lösung gefunden:

Zitat:
SELECT ISNULL(SUM(BETRAG), 0) AS Total FROM ....


Das lässt sich auch mit Stringkolonnen machen

Zitat:
SELECT ISNULL(NAME), '') AS _Name FROM ....


Gruss
Eva