Benutzer mit den meisten Antworten
Anbindung SQL-Server an ACCDB

Frage
-
Hallo,
wir haben ein ADP-Projekt, dass auf SQL-Server 2000/2005 zugreift. Da ADPs unter Acc2007/2010 nur noch eingeschränkt unterstützt werden, wollen wir die Anwendung auf ACCDB umstellen (wie von Microsoft für den Zugriff auf SQL-Server empfohlen). Wie ist hier die beste Vorgehensweise für die Anbindung von Formularen?
Eine Abfrage über die eingebundenen Tabellen funktioniert zwar, ist aber bei komplexen Kriterien langsam. Eine Pass-Through Abfrage ist schnell, aber nicht aktualisierbar.
Bin für jeden Tip dankbar!
Gruß Thomas
Antworten
-
hallo Thomas,
Wenn ich die View im adp öffne, kann ich löschen.
Mache ich etwas falsch, oder geht das generell nicht?Es geht nicht. Das kannst du ganz leicht prüfen, in dem du einen Datensatz im SSMS zu löschen versuchst.
Das es im ADP geht ist eher ein Feature vom ADP.
Hier ist mußt du eigentlich einen Trigger verwenden (ganz am Ende):
USE [test] ; GO SET ANSI_NULLS ON ; GO SET QUOTED_IDENTIFIER ON ; GO IF EXISTS ( SELECT * FROM sys.triggers WHERE object_id = OBJECT_ID(N'[dbo].[tr_AB_Del]') ) DROP TRIGGER [dbo].[tr_AB_Del] ; GO IF EXISTS ( SELECT * FROM sys.views WHERE object_id = OBJECT_ID(N'[dbo].[AB]') ) DROP VIEW [dbo].[AB] ; GO IF EXISTS ( SELECT * FROM sys.objects WHERE object_id = OBJECT_ID(N'[dbo].[A]') AND type IN ( N'U' ) ) DROP TABLE [dbo].[A] ; GO IF EXISTS ( SELECT * FROM sys.objects WHERE object_id = OBJECT_ID(N'[dbo].[B]') AND type IN ( N'U' ) ) DROP TABLE [dbo].[B] ; GO CREATE TABLE [dbo].[A] ( [aID] [int] NOT NULL, [aText] [varchar](255) NULL, [aTS] [timestamp] NOT NULL, [abID] [int] NULL, PRIMARY KEY CLUSTERED ( [aID] ASC ) WITH ( PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON ) ON [PRIMARY] ) ON [PRIMARY] ; GO CREATE TABLE [dbo].[B] ( [bID] [int] NOT NULL, [bText] [varchar](255) NULL, [bTS] [timestamp] NOT NULL, PRIMARY KEY CLUSTERED ( [bID] ASC ) WITH ( PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON ) ON [PRIMARY] ) ON [PRIMARY] ; GO CREATE VIEW [dbo].[AB] AS SELECT A.*, B.* FROM A LEFT OUTER JOIN B ON A.abID = B.bID ; GO CREATE TRIGGER [dbo].[tr_AB_Del] ON [dbo].[AB] INSTEAD OF DELETE AS SET NOCOUNT ON ; DELETE FROM dbo.A WHERE aID IN ( SELECT aID FROM DELETED ) ; GO
Microsoft MVP Office Access
https://mvp.support.microsoft.com/profile/Stefan.Hoffmann- Als Antwort markiert Thomas Warnke Montag, 4. Oktober 2010 13:32
Alle Antworten
-
hallo Thomas,
Eine Abfrage über die eingebundenen Tabellen funktioniert zwar, ist aber bei komplexen Kriterien langsam.
Du bist auf dem richtigen Weg.
Komplexe, langlaufende Abfragen bekommen eigene Sichten. Dadurch übernimmt der SQL Server die Filterung. Access/Jet repektive ODBC fragen den SQL Server dann in etwa "SELECT * FROM view WHERE complexCriteria;".
Microsoft MVP Office Access
https://mvp.support.microsoft.com/profile/Stefan.Hoffmann -
Hallo,
Thomas Warnke wrote:
wir haben ein ADP-Projekt, dass auf SQL-Server 2000/2005 zugreift. Da
ADPs unter Acc2007/2010 nur noch eingeschränkt unterstützt werden,
wollen wir die Anwendung auf ACCDB umstellen (wie von Microsoft für den
Zugriff auf SQL-Server empfohlen).Das ist richtig, aber ADP funktioniert auch weiterhin. Es ist mit 2007/2010
moeglich, neue ADPs anzulegen und wenn das BE ein SQL 2008 ist, kann man
sogar wieder Serverobjekte bearbeiten.Wie ist hier die beste Vorgehensweise für die Anbindung von Formularen?
Eine Abfrage über die eingebundenen Tabellen funktioniert zwar, ist aber
bei komplexen Kriterien langsam. Eine Pass-Through Abfrage ist schnell,
aber nicht aktualisierbar.Genau das. Wenn du eine aktualisierbare RecordSource brauchst, verwende
eingebundene Tabellen, fuer komplexe Read-only-Abfragen PT. Du kannst aber
auch wie gewohnt ueber ADO zugreifen.Situationen, in denen Konstrukte ueber eingebundene Tabellen zu langsam
waeren, sind eher die Ausnahme und muessten individuell behandelt werden,
z.B. ueber Korrekturen im Datenmodell oder eben, wie bisher ueber ADO.Gruss - Peter
Mitglied im http://www.dbdev.org
FAQ: http://www.donkarl.com -
Hallo StefanDas ist soweit richtig. Für die, die's noch nie gemacht haben: Die Views (Sichten) werden in Access dann als Tabellen eingebunden und sehen dann aus wie Tabellen. Views sind per se allerdings nicht immer aktualisierbar, das hängt davon ab, wie die Tabellen verknüpft sind. Wenn diese allerdings in einem ADP aktualsierbar waren, sollten diese auch als eingebundene "Tabellen" in Acces aktualisierbar sein.Ein wichtiger Hinweis für das Einbinden der Tabellen in Access ist, dass alle Tabellen mit einer TimeStamp Spalte versehen werden sollten. Das macht die Updates wesentlich schneller und entlastet das Netzwerk.GrussHenry"Stefan Hoffmann" <=?utf-8?B?U3RlZmFuIEhvZmZtYW5u?=> wrote in message news:970588b5-2efd-4e7b-9ec1-c7f9083c5ab2...
hallo Thomas,
Eine Abfrage über die eingebundenen Tabellen funktioniert zwar, ist aber bei komplexen Kriterien langsam.
Du bist auf dem richtigen Weg.
Komplexe, langlaufende Abfragen bekommen eigene Sichten. Dadurch übernimmt der SQL Server die Filterung. Access/Jet repektive ODBC fragen den SQL Server dann in etwa "SELECT * FROM view WHERE complexCriteria;".
Microsoft MVP Office Access
https://mvp.support.microsoft.com/profile/Stefan.Hoffmann
[MVP Office Access] -
Danke für die Antworten.
Eine Abfrage auf eine eingebundene View habe ich auch schon probiert. Allerdings kann ich in der View keine Datensätze löschen (Bearbeiten und Anfügen funktioniert). Wenn ich die View im ADP öffne kann ich löschen.
Gruß Thomas
-
Am 30.09.2010 schrieb Thomas Warnke:
Eine Abfrage auf eine eingebundene View habe ich auch schon probiert. Allerdings kann ich in der View keine Datensätze löschen (Bearbeiten und Anfügen funktioniert). Wenn ich die View im ADP öffne kann ich löschen.
In der FAQ von Bernd Jungbluth finden sich Tipps dazu:
http://www.berndjungbluth.de/sqlfaq/faqb2.htmServus
Winfried
Connect2WSUS: http://www.grurili.de/tools/Connect2WSUS.exe
GPO's: http://www.gruppenrichtlinien.de
Community Forums NNTP Bridge: http://communitybridge.codeplex.com/ -
In der FAQ von Bernd Jungbluth finden sich Tipps dazu:
http://www.berndjungbluth.de/sqlfaq/faqb2.htmHallo Winfried,
ohne Primarykey kann ich nicht ändern. Mit Primarykey kann ich ändern und erfassen, aber nicht löschen.
Gruß Thomas
-
Hallo!
Thomas Warnke schrieb:
wir haben ein ADP-Projekt, dass auf SQL-Server 2000/2005 zugreift. Da ADPs unter Acc2007/2010 nur noch eingeschränkt unterstützt werden, wollen wir die Anwendung auf ACCDB umstellen (wie von Microsoft für den Zugriff auf SQL-Server empfohlen). Wie ist hier die beste Vorgehensweise für die Anbindung von Formularen?
Ich nutze gerne ADODB-Recordsets als Datenquelle für das Formular.
Dann entspricht das Formular (bezüglich Formular-Eigenschaften)
ungefähr einem ADP-Formular (Unique-Table-Eigenschaft ist verfügbar).
Eindeutiger Nachteil gegenüber verknüpften Tabellen (den man auch als
Vorteil betrachten kann ;-)): Die Datenquelle muss per Code
eingestellt werden.
Vorteil: man kann auch gespeicherte Prozeduren als Datenquelle
einsetzen und muss dabei nicht den Umweg über PT-Abfragen gehen.Bei der Bindung ist allerdings zu beachten, dass ein Client-seitiger
Cursor zum Einsatz kommen muss, sonst streikt Access bei der Zuweisung
des Recordset.
Das RS kann übrigens auch verbindungslos genutzt werden.mfg
Josef -
hallo Thomas,
ohne Primarykey kann ich nicht ändern. Mit Primarykey kann ich ändern und erfassen, aber nicht löschen.
Das ist einer der schönen Sachen: Access/Jet/ACE müssen nur an einen Primärschlüssel glauben. D.h. du muß für eingebundene Sichten lediglich einen mittels
CurrentDb.Execute _ "CREATE INDEX pk_AName " & _ "ON linkedView (primaryKeyFieldList) " & _ "WITH PRIMARY;"
anlegen.
Microsoft MVP Office Access
https://mvp.support.microsoft.com/profile/Stefan.Hoffmann- Bearbeitet Peter DoeringMVP, Moderator Donnerstag, 30. September 2010 13:13 Formatierung korrigiert
-
Hallo Stefan,
ich hab jetzt alles probiert, aber beim Löschen kömmt immer der Fehler "Die Sicht oder Funktion ist nicht aktualisierbar, da die Änderung sich auf mehrere Basistabellen auswirkt".
Meine Testobjekte:
Tabelle A
----------
aID INT, PK
aText VARCHAR
aTS TIMESTAMP
abID INTTabelle B
----------
bID INT, PK
bText VARCHAR
bTS TIMESTAMPView
------
SELECT A.*, B.*
FROM A LEFT OUTER JOIN B ON A.abID = B.bIDBeim Einbinden wähle ich im PopUp-Formular "Eindeutigen Datensatzbezeichner auswählen" aID aus. Hab es auch per Code gemacht aber das sollte das Gleiche sein (oder?).
In aText kann ich Daten ändern und eingeben. Beim Löschen eines DS kommt der obige Fehler.
Wenn ich die View im adp öffne, kann ich löschen.
Mache ich etwas falsch, oder geht das generell nicht?
Danke & Gruß
Thomas
-
hallo Thomas,
Wenn ich die View im adp öffne, kann ich löschen.
Mache ich etwas falsch, oder geht das generell nicht?Es geht nicht. Das kannst du ganz leicht prüfen, in dem du einen Datensatz im SSMS zu löschen versuchst.
Das es im ADP geht ist eher ein Feature vom ADP.
Hier ist mußt du eigentlich einen Trigger verwenden (ganz am Ende):
USE [test] ; GO SET ANSI_NULLS ON ; GO SET QUOTED_IDENTIFIER ON ; GO IF EXISTS ( SELECT * FROM sys.triggers WHERE object_id = OBJECT_ID(N'[dbo].[tr_AB_Del]') ) DROP TRIGGER [dbo].[tr_AB_Del] ; GO IF EXISTS ( SELECT * FROM sys.views WHERE object_id = OBJECT_ID(N'[dbo].[AB]') ) DROP VIEW [dbo].[AB] ; GO IF EXISTS ( SELECT * FROM sys.objects WHERE object_id = OBJECT_ID(N'[dbo].[A]') AND type IN ( N'U' ) ) DROP TABLE [dbo].[A] ; GO IF EXISTS ( SELECT * FROM sys.objects WHERE object_id = OBJECT_ID(N'[dbo].[B]') AND type IN ( N'U' ) ) DROP TABLE [dbo].[B] ; GO CREATE TABLE [dbo].[A] ( [aID] [int] NOT NULL, [aText] [varchar](255) NULL, [aTS] [timestamp] NOT NULL, [abID] [int] NULL, PRIMARY KEY CLUSTERED ( [aID] ASC ) WITH ( PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON ) ON [PRIMARY] ) ON [PRIMARY] ; GO CREATE TABLE [dbo].[B] ( [bID] [int] NOT NULL, [bText] [varchar](255) NULL, [bTS] [timestamp] NOT NULL, PRIMARY KEY CLUSTERED ( [bID] ASC ) WITH ( PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON ) ON [PRIMARY] ) ON [PRIMARY] ; GO CREATE VIEW [dbo].[AB] AS SELECT A.*, B.* FROM A LEFT OUTER JOIN B ON A.abID = B.bID ; GO CREATE TRIGGER [dbo].[tr_AB_Del] ON [dbo].[AB] INSTEAD OF DELETE AS SET NOCOUNT ON ; DELETE FROM dbo.A WHERE aID IN ( SELECT aID FROM DELETED ) ; GO
Microsoft MVP Office Access
https://mvp.support.microsoft.com/profile/Stefan.Hoffmann- Als Antwort markiert Thomas Warnke Montag, 4. Oktober 2010 13:32
-
Hallo Stefan,
es funktioniert *schwer begeistert*.
Ich werde für jedes Formular eine VIEW erstellen, welche dann ohne JOINs gefiltert werden kann.
Der Ansatz von Josef, ADODB-Recordsets als Datenquelle für das Formular zu verwenden, gefällt mir auch. Da immer alle Daten geladen werden, funktioniert es aber nur bei kleinen Datenmengen hinreichend schnell.
Gruß
Thomas