Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Re: Fehler 3218 Aktualisierung nicht möglich; momentan gesperrt.

367 views
Skip to first unread message

Lutz

unread,
Oct 15, 2013, 4:32:00 AM10/15/13
to
5 Jahre spᅵter und ich habe dasselbe Problem.
Damals half nur ein Workaround - eine Lᅵsung gab es nicht!


Diesmal geht es um eine simple Aktualisierungsabfrage innerhalb einer
Transaktion.

sql = "UPDATE a_BewertungBerech1 SET InvMP=BerInvMP" _
& " WHERE Nz(InvNEU,False)=True"
db.Execute sql, dbFailOnError

Die Abfrage ist auf nur EINER Tabelle. BerInvMP ist ein berechnetes Feld.
SELECT t_InventurPreisAkt.InvNr2, t_InventurPreisAkt.InvMP1,
t_InventurPreisAkt.InvMP2,
IIf([InvMP1]>0,IIf([InvMP1]<[InvMP2],[InvMP1],[InvMP2]),[InvMP2]) AS
BerInvMP, t_InventurPreisAkt.InvMP, t_InventurPreisAkt.InvBeST,
t_InventurPreisAkt.InvBeVM, t_InventurPreisAkt.InvBeVVM,
(t_InventurPreisAkt!InvBeST*3)+(t_InventurPreisAkt!InvBeVM*2)+(t_InventurPreisAkt!InvBeVVM*1)
AS BerInvDB, t_InventurPreisAkt.InvDB, t_InventurPreisAkt.InvNEU
FROM t_InventurPreisAkt;

Das Update ist Teil einer komplexeren Operation deshalb in einer
Transaktion. Der Ablauf steigt immer an dieser Stelle aus.
Fehler 3128 - Aktualisierung nicht mᅵglich; momentan gesperrt.
Das Datenbank-Objekt zeigt direkt vor der Ausfᅵhrung keine weiteren
geᅵffneten Recordsets an. Ich arbeite alleine - niemand anders kann an
den entsprechenden Daten dran sein.

Lasse ich die Operation allerdings nur bis davor laufen und fᅵhre den
Update-Select per Hand auf der Datenbank aus funktioniert er.

Ich habe testweise die Transaktion weggelassen, das Workspace-Objekt
eigens erstellt. Ich habe die Updates versucht auf der Tabelle
auszufᅵhren - nichts hilft.

Hat irgendjemand eine Idee???

Lutz

Am 20.06.2008 12:25, schrieb Lutz Uhlmann:
> Access 2003 Projekt FE + BE
>
> Bei mir kam der Fehler 3218 und machte mir einen Strich durch meinen
> Programm-Ablauf
> Der Fehler tritt bei einer grᅵᅵeren Datenbearbeitung im Code auf, welche ich
> wegen des Umfangs in eine Transaktion gesteckt habe.
> Fᅵr die Bearbeitung ᅵffne ich das BE direkt. Ich arbeite allein auf der
> Datenbank, kann also nicht an einem 2. Benutzer liegen.
>
> In folgendem Code tritt ziemlich am Ende der ganzen Operation der Fehler
> 3218 auf.
>
> sql = "SELECT * FROM t_Material WHERE MatMenge=0"
> Set rsmat = db.OpenRecordset(sql, dbOpenDynaset)
> Do Until rsmat.EOF
> lMatID = Nz(rsmat!MatID, 0)
> sql = "DELETE * FROM t_MaterialFrist WHERE MatID=" & lMatID
> db.Execute sql, dbFailOnError
> sql = "DELETE * FROM t_MaterialRes WHERE MatID=" & lMatID
> db.Execute sql, dbFailOnError
> sql = "DELETE * FROM t_MatDokumente WHERE ANL_ID=" & lMatID
> db.Execute sql, dbFailOnError
> sql = "DELETE * FROM t_MatNotiz WHERE ANL_ID=" & lMatID
> db.Execute sql, dbFailOnError
> sql = "DELETE * FROM t_MatTechnisch WHERE ANL_ID=" & lMatID
> db.Execute sql, dbFailOnError
>
> rsmat.MoveNext
> Loop
> rsmat.Close
> Set rsmat = Nothing
>
> DBEngine.Idle dbRefreshCache '(???)
>
> sql = "DELETE * FROM t_Material WHERE MatMenge=0"
> db.Execute sql, dbFailOnError '<---- Fehler 3218
>
> Bei diesem letzten Execute kommt der Fehler. Habe probiert ob ich mit
> DBEngine.Idle dbRefreshCache vielleicht die vorherige Aktion auf dieser
> Tabelle abschliessen kann. hat nicht geholfen.
> Beheben kann ich das zwar, indem ich das Lᅵschen des Datensatzes mit
> "rsmat.delete" in die Schleife verlege, aber prinzipiell mᅵᅵte doch auch die
> obige Variante funktionieren? Bzw wie kann man die zum Funktionieren
> bringen??? Der Fehler muᅵ ja irgendeine Ursache haben ...
>
> Lutz
>
>

Lutz

unread,
Oct 15, 2013, 7:18:03 AM10/15/13
to
Ich habe jetzt das ganze auf Recordset-Loops umgestellt als Workaround.

Er kommt auch relativ gut durch die einzelnen Updates durch.

Spᅵter in der Operation bekomme ich nun aber den Fehler
3052 - Anzahl der Dateisperrungen ᅵberschritten.
wᅵhrend eines rs.Update Aufrufes.

Ich vermute, daᅵ beide Fehler zusammenhᅵngen und Auswirkung
einundderselben Ursachen sind.

Kᅵnnten die Sperren Probleme bereiten? Auch innerhalb einundderselben
Transaktion obwohl die entsprechenden Recordsets schon wieder
geschlossen wurden?
Was kann man in die Richtung vorbeugend tun?

Lutz

P.S. Habe noch einen Artikel zum ursprᅵnglichen Thema gefunden. Weiᅵ
aber nicht inwieweit der damit zu tun hat. Vielleicht ist es ein
Jet-Problem?
habe es noch nciht ausprobiert. Ich wollte jetzt nicht alles auf ADO
umstellen, da ich im Moment keine Zeit dafᅵr habe.
http://support.microsoft.com/kb/331594/en-us

Ulrich Möller

unread,
Oct 15, 2013, 8:34:13 AM10/15/13
to
Hallo Lutz,

es sieht so aus, als wolltest du einen Massenupdate machen.
Transaktionen muᅵ man sehr bedacht einsetzen, denn ᅵblicherweise will
man damit eine Logik wie "Alles oder gar nichts" umsetzen.
Stelle die Transaktionen in kleinere Update Einheiten zusammen und
versuche sie nur dort zu gebrauchen, wo sie einen Sinn ergeben. Niemals
das "Commit" vergessen!!!. Dieses ist ein Fehler, der immer gerne
gemacht wird. Solange kein Commit gemacht wird, bleiben die geᅵnderten
Datensᅵtze fᅵr gesperrt , wird wohl auch in Access so sein.

ᅵber wie viele Records in den Tabellen reden wir?

Grᅵᅵe
Ulrich

Lutz

unread,
Oct 15, 2013, 10:33:07 AM10/15/13
to
Am 15.10.2013 14:34, schrieb Ulrich Mᅵller:

> Hallo Lutz,
>
> es sieht so aus, als wolltest du einen Massenupdate machen.
> Transaktionen muᅵ man sehr bedacht einsetzen, denn ᅵblicherweise will
> man damit eine Logik wie "Alles oder gar nichts" umsetzen.
> Stelle die Transaktionen in kleinere Update Einheiten zusammen und
> versuche sie nur dort zu gebrauchen, wo sie einen Sinn ergeben. Niemals
> das "Commit" vergessen!!!. Dieses ist ein Fehler, der immer gerne
> gemacht wird. Solange kein Commit gemacht wird, bleiben die geᅵnderten
> Datensᅵtze fᅵr gesperrt , wird wohl auch in Access so sein.

Nunja, es handelt sich um Buchungen. Die mᅵssen auch konsistent sein.
Bei einem Fehler muss alles zurᅵckgerollt werden!
Ich seh auch keine richtige Mᅵglichkeit das in Einzelschritte zu zerlegen.

Die gesamte Operation erfolgt in einer Funktion welche Boolean zurᅵckgibt.
Dieser Aufruf ist durch die Transaktion gekapselt und je nach Ergebnis
erfolgt ein Commit oder Rollback. Das ist eigentlich sicher was das
Beenden der Transaktion angeht.

> ᅵber wie viele Records in den Tabellen reden wir?

Schwierig zu beziffern.

Einmal um die 300 Positionen, fᅵr die es je ca. 7, 8 Buchungen gibt.
Dazu nochmal ein paar 1000 Positionen mit 2 Buchungen.

Der Einfachheit halber mache ich die 1. Buchung fᅵr die 300 Positionen
in einem Rutsch, dann die 2. Buchung usw. Logisch zusammengehᅵrend sind
aber die Buchungen.
Schwierig zu erklᅵren.

Ich schau es mir nochmal an, ob ich dort bestimmte Teile irgendwie in
mehrere Transaktionen teilen kann.


Aber den 3218-Fehler hatte ich auch mit auskommentierter Transaktion.
Deswegen bin ich da bissl unsicher, was die genaue Ursache ist.

Lutz

Ulrich Möller

unread,
Oct 15, 2013, 11:30:02 AM10/15/13
to
dann gibt es ja schon einmal eine logische Aufteilung fᅵr Transaktionen,
nᅵmlich alle Buchungen zu einer Position in eine Transaktion abwickeln -
wenn das notwendig ist. Jede Transaktion mit einem Commit abschlieᅵen,
hierbei aber den Fehlerausgang mit einem Rollback nicht vergessen, falls
etwas nicht geklappt hat, d.h alle Buchungen pro Position wurden
durchgefᅵhrt oder keine!

Kontrolliere in den Optionen die Einstellung fᅵr die Datensatzsperren ->
Standard bei Datensatzsperren = bearbeiteter Datensatz.
Beim Fehler 3128 hat sich wahrscheinlich einen semantischer Fehler
eingeschlichen. Irgendwo wird ein Datensatz geᅵndert, ein Recordset
exklusiv aufgemacht oder schlicht ein Recordset.Close vergessen.

Ulrich


Ingo Moch

unread,
Oct 17, 2013, 4:09:39 PM10/17/13
to
Lutz wrote:
> 5 Jahre spᅵter und ich habe dasselbe Problem.
> Damals half nur ein Workaround - eine Lᅵsung gab es nicht!
>
>
> Diesmal geht es um eine simple Aktualisierungsabfrage
> innerhalb einer Transaktion.
>
> sql = "UPDATE a_BewertungBerech1 SET InvMP=BerInvMP" _
> & " WHERE Nz(InvNEU,False)=True"
> db.Execute sql, dbFailOnError
>
> [...]
>
> Das Update ist Teil einer komplexeren Operation deshalb
> in einer Transaktion. Der Ablauf steigt immer an dieser
> Stelle aus. Fehler 3128 - Aktualisierung nicht mᅵglich; momentan
> gesperrt.

Du kannst die Anzahl der mᅵglichen Sperren erhoehen.
Standard ist 9500.

DAO:

DBEngine.SetOption dbMaxLocksPerFile, 25000

ADO:

Dim con As ADODB.Connection

[Parameter des Connection-Objekts setzen]
con.Open

con.Properties("Jet OLEDB:Max Locks Per File") = 25000

Allerdings bedeutet das, dass entsprechend mehr Speicher
reserviert wird.

Ingo

0 new messages