Hallo,
ich habe eine Tabellenerstellungsabfrage mit einer festen Zielverknüpfung.
Diese muss ich jedoch ändern können und hierfür möchte ich die Zielverknüpfung in einer Tabelle ablegen und bei Ausführung der Abfrage auslesen und verwenden.
Hierzu möchte ich die Tabellenerstellungsabfrage in VBA umwandeln, bekomme das aber nicht hin. Kommen dauernd irgendwelche Fehler - egal was ich mache.
Das ist der SQL-Code in der Abfrage:
SELECT PMDB.IdentNr AS PMID, PMDB.Firma AS FIRMENNR, PMDB.IDoWAG AS ZIFFER, PMDB.Klassifizierung AS KLASSE, PMDB.Bezeichnung AS BEZEICHN, PMDB.Kalibrierdienst AS KDIENST, Format([Kalibrierdatum],"dd\.mm\.yyyy") AS KDATUM INTO PMM_Indexierung IN '\\faramir.wittag.net\PMM\Austausch\PMM-Archivierung.mdb'
FROM PMDB
WHERE (((PMDB.Standort)<>'Klärung'));
Den Pfad wohin geschrieben werden soll möchte ich dann per Variable einbinden. (...faramier...)
Was muss ich beachten, wenn ich das in einen VBA-Code umwandeln möchte. Denn einach in strSQL = ".... kopieren funktioniert leider nicht.
Vielen Dank
gruß Christoph
Hallo Christoph,
mit dem Kopieren komme ich gut klar.
Abfrag in SQL-Ansicht und den String kopieren
In VBA SqlString = einfügen
jetzt noch den String in "" setzen.
Variable Felder so einstellen SqlString = "abc " & me!feldname & " def" usw.
Anführungszeichen nur für die Begrenzung vom String sonst Hochkomma, siehe dein Format(Kalibrierdatum,"dd/mm/yyyy")
Gruß
Johann
Hallo,
versuch mal so:
Dim strPfad as String, strSQL as String
strPfad = DLookup("PfadFeld","PfadTabelle")
strSQL = "SELECT PMDB.IdentNr AS PMID, PMDB.Firma AS FIRMENNR, PMDB.IDoWAG AS ZIFFER, PMDB.Klassifizierung AS KLASSE, PMDB.Bezeichnung AS BEZEICHN, " & _
"PMDB.Kalibrierdienst AS KDIENST, Format([Kalibrierdatum],'dd\.mm\.yyyy') AS KDATUM INTO PMM_Indexierung IN " & strPfad & " FROM PMDB " _
"WHERE (((PMDB.Standort)<>'Klärung'));"
CurrentDb.Execute strSQL
HTH
Vielen Dank!
Hallo,
ich habe das jetzt erst testen können.
@database: Ich habe am Ende der zweiten Codezeile von strSQL noch ein "&" eingefügt.
Hierbei kommt jedoch folgende Fehlermeldung: "Die SELECT-Anweisung schließt ein reserviertes Wort oder einen Argumentennamen ein, das/der falsch, mit falscher Zeichensetzung oder überhaupt nicht eingegeben wurde.
Dim strPfad As String, strSQL As String
strPfad = DFirst("Verz_Saperion", "werk")
strSQL = "SELECT PMDB.IdentNr AS PMID, PMDB.Firma AS FIRMENNR, PMDB.IDoWAG AS ZIFFER, PMDB.Klassifizierung AS KLASSE, PMDB.Bezeichnung AS BEZEICHN, " & _
"PMDB.Kalibrierdienst AS KDIENST, Format([Kalibrierdatum],'dd\.mm\.yyyy') AS KDATUM INTO PMM_Indexierung IN " & strPfad & " FROM PMDB " & _
"WHERE (((PMDB.Standort)<>'Klärung'));"
CurrentDb.Execute strSQL
Gruß Christoph
Hallo,
Da solltest Du halt mal alle die verwendeten Namen und den Inhalt der Variablen verifizieren und "Ziffer" sowie "Klasse" umbenennen.
Weiterhin, wenn "KDATUM" in der Zieltabelle den Datentyp Datum/Uhrzeit erhalten soll, dann sollte es so aussehen:
[Kalibrierdatum] AS KDATUM
ggfls auch:
Format([Kalibrierdatum],'\#yyyy-mm-dd\#') AS KDATUM
Guten Morgen,
Ziffer und Klasse sind keine Variablen, sondern die Zieltabellen.
Ich habe sie mal in ZIFFER_N und KLASSE_N geändert.
Der Fehler kommt aber weiterhin. Ich habe auch mal beide Varianten mit dem Datum ausprobiert...
Eigentlich habe ich den Code ja nur von einer Abfrage in SQL Ansicht rauskopiert.
Dim strPfad As String, strSQL As String
strPfad = DFirst("Verz_Saperion", "werk")
strSQL = "SELECT PMDB.IdentNr AS PMID, PMDB.Firma AS FIRMENNR, PMDB.IDoWAG AS ZIFFER_N, PMDB.Klassifizierung AS KLASSE_N, PMDB.Bezeichnung AS BEZEICHN, " & _
"PMDB.Kalibrierdienst AS KDIENST, Format([Kalibrierdatum],'\#yyyy-mm-dd\#') AS KDATUM AS KDATUM INTO PMM_Indexierung_NEU IN " & strPfad & " FROM PMDB " & _
"WHERE (((PMDB.Standort)<>'Klärung'));"
CurrentDb.Execute strSQL
Zitat von: cyberchris am März 14, 2012, 07:16:53
PMDB.Klassifizierung AS KLASSE_N, PMDB.Bezeichnung AS BEZEICHN, " & _
"PMDB.Kalibrierdienst AS KDIENST, Format([Kalibrierdatum],'\#yyyy-mm-dd\#') AS KDATUM AS KDATUM INTO PMM_Indexierung_NEU IN " & strPfad & " FROM PMDB " & _
"WHERE (((PMDB.Standort)<>'Klärung'));"
CurrentDb.Execute strSQL
Warum doppelt?
Hallo,
neben dem von Harald hinterfragten Fehler:
Zitat
Ziffer und Klasse sind keine Variablen, sondern die Zieltabellen.
???
Die beiden Bezeichnungen sind Aliasnamen und keine Zieltabellen. Die Zieltabelle heißt lt. des SQL-Strings "PMM_Indexierung_NEU" und befindet sich in der ext. Datenbank(datei) mit dem Namen , der in der Variablen "strPfad" steht, so er denn mit der mit Vorsicht zu geniesenden DFirst-Funktion auch richtig ermittelt wird.
Ja, ich muss mich entschuldigen :-)
Ziffer und Klasse sind natülich nicht die Tabellen, sondern die Spalten in der Tabelle wie genannt.
Das doppelte "AS KDATUM" war nur hier im Code so. Habe es auch nochmal probiert. Kommt aber immer der gleiche Fehler.
Zur Sicherheit habe ich es dann auch nochmal hiermit probiert, dass das auslesen des Pfads nicht der Fehler ist:
strPfad = "\\faramir11.wittag.net\PMM\Austausch\PMM-Archivierung.mdb"
Die klassische Abfrage funktioniert, dass ist ja das seltsame.
Gruß Christoph
Hallo,
ok, sehe gerade dass da noch Hochkommata, bzw. Gänsefüße fehlen:
...IN """ & strPfad & """ FROM PMDB " & _
...IN '" & strPfad & "' FROM PMDB " & _
Hallo,
Das wars! Jetzt gehts.
Nur beim 2. mal kommt die Meldung, dass die Tabelle bereits besteht. Und macht dann nichts. Muss ich die Tabelle vorher immer löschen? Oder wie löst man das am besten?
Danke
gruß Christoph
Hallo,
ja, wobei sich dann die grundsätzliche Frage nach der Verwendung einer Tabellenerstellungsabfrage stellt
so hatte ich es halt bei der klassischen Acces Abfrage drin und hatte funktioniert.
Was ist dann am besten, wenn ich die Tabelle immer aktualisieren möchte.
Löschen
Einfügen
oder
Leeren
Anfügen
Gruß Christoph
ZitatWas ist dann am besten, wenn ich die Tabelle immer aktualisieren möchte.
Löschen
Einfügen
oder
Leeren
Anfügen
Definiere "am besten"?
Für Aufwand bzgl. Performance könnte man folgendes Gleichnis verwenden: Man möchte sein Wohnzimmer "aktualisieren".
- Würde man das Wohnzimmer komplett ausräumen und einschließend wieder einräumen (Leeren + Anfügen)
- oder zusätzlich noch Wände einreißen und neu aufbauen (Löschen + Einfügen)
- oder einfach die Kommode, die im Weg steht, entfernen, den Tisch, der falsch steht, umstellen und den Stuhl, der fehlt, ins Zimmer tragen?
MfGA
ebs
ich würde das Wohnzimmer komplett aus- und wieder einraumen. Dann würde ich bestimmt auch wieder ein paar Sachen finden...
Wahrscheinlich UPDATE...:-)
Nur passt dann der Code nicht mehr....ist das vielleicht kompliziert. Für mich zumindest, da ich mich damit eigentlich nicht auskenne.
Einfach SELECT in UPDATE zu ändern geht leider nicht.
Gruß Christoph
Muss ich dann das so machen: (Musste ich mir wieder zusammenstückeln, da die unterschiedlichen Abfragetypen ja nicht 1:1 verwendbar sind. Wird aber sicherlich wieder irgendwo ein Fehler sein...:-(
UPDATE PMDB SET PMDB.IdentNr = '*', PMDB.Firma = '*', PMDB.IDoWAG = '*', PMDB.Klassifizierung = '*', PMDB.Bezeichnung = '*', & _
PMDB.Kalibrierdienst = '*', PMDB.Kalibrierdatum = '*' INTO PMM_Indexierung IN '" & strPfad & "' FROM PMDB " & _
WHERE (((PMDB.Standort)<>'Klärung'));
Ist die Zieltabelle dann immer identisch mit der Ausgangstabelle? D. h., wenn Einträge in der Ausgangstabelle nicht mehr vorkommen werden diese dann auch in der Zieltabelle gelöscht?
In meinem Fall müssen beide Inhalte immer komplett identisch sein!
Danke
Gruß Christoph
Hallo,
nochmal die Frage: Wozu das Ganze?
Das eigentliche Problem ist nicht die Syntax der Abfrage(arten) , eher das Verfahren, irgendwas archivieren/kopieren zu wollen.
Hallo,
ich muss die genannten Daten (Kopie) in eine separate mdb ablegen, damit ein anderes Programm darauf zugreifen kann. Man möchte nicht direkt auf die Livedaten zugreifen (aus Sicherheitsgründen).
Diese Daten muss ich in regelmäßigen Zeitabständen updaten.
gruß Christoph
Hallo,
eigentlich sind das immer noch zu wenig Infos...
Wie auch immer, es geht halt nur, wie schon mehrfach angesprochen , über:
zum Einen: Vor jeder Übertragung erst die Tabelle löschen , dann neu erstellen und Daten einfügen.
zum Anderen: Bei allererster Übertragung (bzw. einmalig von Hand bei der DB-Erstellung) die Tabelle generieren. Dann bei jeder Übertragung zunächst die Tabelle leeren und anschliessend akt. Daten einfügen. Hier kann man sich auch vorstellen, vorhandenen Daten nicht zu löschen und nur akt. Daten neu hinzufügen, je nachdem, was genau gemacht werden soll/muss.
Welche Methodik man für die einzelnen Vorgänge anwendet, ist erst sekundärer von Belang:
SQL (als gespeicherte Abfrage oder SQL-String generiert und ausgeführt per VBA) mittels "IN"-Parameter
Transferdatabase-Methode
Opendatabase/Opencurrentdatabase und Recordsets
Verknüpfung der ext. Tabelle und deren Manipulation.
.
.
Zum Dritten: Wenn Aktualisieren heißt, eine Tabelle der anderen anzugleichen statt zu ersetzen, braucht man einen Schlüssel, um erkennen zu können, ob ein Datensatz vorhanden oder neu ist sowie welcher Datensatz durch welchen Datensatz zu aktualisieren ist. Mit "*" kommt man da nicht weiter.
Prinzipdarstellung (Annahme: Zwei Felder, die gemeinsam den Schlüssel ergeben, zzgl zwei weitere Felder):
' Löschen nicht mehr vorhandener Datensätze
DELETE Zieltabelle Z
WHERE NOT EXISTS
(SELECT Null FROM Quelltabelle Q
WHERE Z.Key1 = Q.Key1 AND Z.Key2 = Q.Key2)
' Aktualisieren vorhandener Datensätze
UPDATE Zieltabelle Z INNER JOIN Quelltabelle Q
ON Z.Key1 = Q.Key1 AND Z.Key2 = Q.Key2
SET Z.Field1 = Q.Field1, Z.Field2 = Q.Field2
' Anfügen (nur) neuer Datensätze
INSERT INTO Zieltabelle (Key1, Key2, Field1, Field2)
SELECT Q.Key1, Q.Key2, Q.Field1, Q.Field2
FROM Quelltabelle Q
WHERE NOT EXISTS
(SELECT Null FROM Zieltabelle Z
WHERE Z.Key1 = Q.Key1 AND Z.Key2 = Q.Key2)
Das ist zwar etwas mehr Text (Programmiereraufwand) als ein Löschen und Kopieren einer Tabelle, hat dafür einige andere Merkmale, auf die man Wert legen könnte:
- Beziehungen, Indizes und Schlüssel werden nicht verletzt. Z.B. könnten die Datensätze der Zieltabelle mit weiteren Daten verknüpft sein. Ein vollständiges Löschen wäre da eine erhebliche Störung.
- Es werden nur die Datensätze bewegt, die wirklich benötigt werden. Das bedeutet weniger Netzwerktraffic und höheren Zeitvorteil. Warum sollte ich z.B. 1 Mio Datensätze löschen und neu übertragen, wenn z.B. nur 21 Datensätze zu aktualisieren wären?
- Die Zieldatenbank wird bei weitem nicht so erheblich aufgebläht durch Löschen und Neuschreiben.
Zur Ansprache einer externen Datenbank ergänzt Du entsprechend das "IN 'Pfad_DB'". Alternativ könntest Du auch die Zieltabelle temporär in die eigene Anwendung verknüpfen:
DoCmd.TransferDatabase acLink, , "X:\irgendwo\eine.MDB", acTable, _
"Quelltabelle", "Temp"
CurrentDb.Execute "DELETE ..." ' Abfragen ausführen
DoCmd.DeleteObject acTable, "Temp"
MfGA
ebs