レガシーデータベーステーブルを使用している古いビジュアル基本プログラムをより現代的で堅牢な実装に変換しようとしています。具体的な例を示すために浮動小数点数を使用する必要があるときは、多くのvarcharsを使用する必要があります。浮動小数点数から文字列への変換回数が多いため、コードを読みにくくなります。新しいアプリケーションでは避けたいです)更新可能なビューはビジュアルベーシックでランタイムエラーを表示します
下位互換性を維持するために、新しいテーブルで更新可能なビューを作成して、vbの古いアプリケーションが引き続き動作するようにするか、少なくともそれが意図です。 、
SELECT
ArtikelNummer,
CataloogID,
Artikel,
isnull(CONVERT(nvarchar(5), breedte),'') Breedte,
isnull(CONVERT(nvarchar(5), Hoogte),'') Hoogte,
isnull(CONVERT(nvarchar(5), Diepte),'') Diepte,
isnull(CONVERT(nvarchar(5), Aantal),'') Aantal,
FROM
Master.Orders_Catalogen_Artikels
をして、私の代わりに、インサートの作成し、更新が、このビューでトリガーの代わりに、それは更新可能にし、手動で、彼らがOKであることを検証するためにこれらのトリガーをテストするために以下のような
は、私は、ビューを持っています彼らは働く。
しかし、最終テストでVB6プログラムを実行しようとすると、実際に挿入を実行する前に挿入を実行できません。コードは、OLEのものでVB自体に失敗:
With MyDE.rsSelectedArtikel
.Fields("CataloogID").Value = Orders.cCataloogID
.Fields("Artikel").Value = Orders.cbArtikel
.Fields("Aantal").Value = Orders.cAantal ---> fails here
rsSelectedArtikelの背後にあるクエリは、私が上記示したビューの名前ですOrders_Catalogen_artikelsから*簡単な選択です。
私が得るランタイムエラーは、通常、間違ったタイプの使用法などを識別する-2147217887(8004e21)です。しかし、Aantalは、ビューの列を参照するとき、nvarchar(5)として正しく識別されます。
この種の問題の修正または回避策はありますか?
もちろん、長さと幅などの文字列を使用して古いテーブル定義を使用して、新しいアプリケーションのupdatebleビューを作成することもできますが、それは正しいことの逆です。
VBのアプリケーションを少し修正します。ソースがあります。最初に、幅、高さ、長さに浮動小数点数を使用するようにデータモデルを変更しますが、私の好みはそのままです。
私は、更新可能なビューがこの種の問題に対する答えであることを期待していました。
UPDATE 1: "更新可能" ビューが誤った名称である更新トリガーと挿入トリガー
ALTER TRIGGER [dbo].[V_Orders_Catalogen_Artikels_Update] ON [dbo].[Orders_Catalogen_Artikels]
INSTEAD OF UPDATE
AS
BEGIN
-- SET NOCOUNT ON added to prevent extra result sets from
-- interfering with SELECT statements.
SET NOCOUNT ON;
-- Insert statements for trigger here
UPDATE [Master].[Orders_Catalogen_Artikels]
SET [CataloogID] = inserted.CataloogID
,[Artikel] = inserted.Artikel
,[Breedte] = iif(inserted.Breedte = '',null,inserted.Breedte)
,[Hoogte] = iif(inserted.Hoogte = '',null,inserted.Hoogte)
,[Diepte] = iif(inserted.Diepte = '',null,inserted.Diepte)
,[Aantal] = iif(inserted.Aantal = '',null,inserted.Aantal)
,[OmschrijvingNL] = inserted.OmschrijvingNL
,[Positie] = inserted.Positie
,[EenheidsPrijs] = inserted.EenheidsPrijs
,[Opmerking] = inserted.Opmerking
,[PosNr] = inserted.PosNr
,[Binnenkleur] = inserted.Binnenkleur
,[BKleurFront] = inserted.BKleurFront
,[Frontkantdikte] = inserted.Frontkantdikte
,[Poothoogte] = inserted.Poothoogte
,[BTWcode] = inserted.BTWcode
,[Korpuskantdikte] = inserted.Korpuskantdikte
,[ManuelePrijs] = inserted.ManuelePrijs
,[OpmerkingFr] = inserted.OpmerkingFr
,[OmschrijvingFr] = inserted.OmschrijvingFr
,[ArtikelGroepID] = inserted.ArtikelGroepID
,[ArtikelID] = inserted.ArtikelID
,[VolgNr] = inserted.VolgNr
,[Klaar] = inserted.Klaar
,[ScanDatum] = inserted.ScanDatum
,[ScanOpm] = inserted.ScanDatum
,[OpZaaglijst] = inserted.OpZaaglijst
FROM inserted
WHERE [Master].[Orders_Catalogen_Artikels].ArtikelNummer = inserted.ArtikelNummer
END
ALTER TRIGGER [dbo].[V_Orders_Catalogen_Artikels_Insert] ON [dbo].[Orders_Catalogen_Artikels]
INSTEAD OF INSERT
AS
BEGIN
-- SET NOCOUNT ON added to prevent extra result sets from
-- interfering with SELECT statements.
SET NOCOUNT ON;
-- Insert statements for trigger here
INSERT INTO [Master].[Orders_Catalogen_Artikels]
([CataloogID]
,[Artikel]
,[Breedte]
,[Hoogte]
,[Diepte]
,[Aantal]
,[OmschrijvingNL]
,[Positie]
,[EenheidsPrijs]
,[Opmerking]
,[PosNr]
,[Binnenkleur]
,[BKleurFront]
,[Frontkantdikte]
,[Poothoogte]
,[BTWcode]
,[Korpuskantdikte]
,[ManuelePrijs]
,[OpmerkingFr]
,[OmschrijvingFr]
,[ArtikelGroepID]
,[ArtikelID]
,[VolgNr]
,[Klaar]
,[ScanDatum]
,[ScanOpm]
,[OpZaaglijst])
SELECT
[CataloogID]
,[Artikel]
,iif(ISNUMERIC(breedte+'e0')=1,convert(float,[Breedte]),null) as newbreedte
,iif(ISNUMERIC([Hoogte]+'e0')=1,convert(float,[Hoogte]),null) as newhoogte
,iif(ISNUMERIC([Diepte]+'e0')=1,convert(float,[Diepte]),null) as newdiepte
,iif(ISNUMERIC([Aantal]+'e0')=1,convert(float,[Aantal]),null) as newaantal
,[OmschrijvingNL]
,[Positie]
,[EenheidsPrijs]
,[Opmerking]
,[PosNr]
,[Binnenkleur]
,[BKleurFront]
,[Frontkantdikte]
,[Poothoogte]
,[BTWcode]
,[Korpuskantdikte]
,[ManuelePrijs]
,[OpmerkingFr]
,[OmschrijvingFr]
,[ArtikelGroepID]
,[ArtikelID]
,[VolgNr]
,[Klaar]
,[ScanDatum]
,[ScanOpm]
,[OpZaaglijst]
FROM inserted
END
「80040e21」は恐ろしい 'DB_E_ERRORSOCCURRED'です。これは「何かが間違っていて、あなた自身でそれを理解してください」という意味です。サーバー側の動的カーソル*の位置を使って 'INSTEAD OF'トリガーでビューを更新することは可能です(T-SQLで試しました)。* ADOが使用するものでなければなりません。確かに知るには、SQL Profilerでそのステートメントをトレースして、実際に何が行われているかを確認してください。最大限の有用性のために「エラー」イベントを含める。レコードセットがクライアント側または切断されている場合、ADOは計算列を更新できないことを「認識」している可能性がありますが、基本的なシナリオは可能である必要があります。 –
私はあなたの提案を見るためにtommorrow見ているが、私は問題がクライアント側だと思う。私はサーバーへの往復が、割り当てが行われている時点ではないと考えています。非常に役に立つコメントをありがとうございます。 –
問題がコンピュータの列である場合、潜在的だが恐らく非常にリソースがかかる可能性のある回避策は、計算されるように設定された列を持たない新しいレコードセットにコピーすることです。 SQL Serverに、トリガは残りの部分を処理する必要があります。しかし、その時点では、(レコードセットをラップするだけであっても)コードを変更することになります。とにかく書き直してはならないと考える価値があります。 (私もADOで作業しなければならなかったので、数年経ちました:-)) –