MSDE FunClub 現在までのアクセスカウント数 最終更新日 : 2000/08/21
Microsoft Data Engine FunClub
Since 2000.08.21
SQLServer7.0/MSDE 完全トレーニングテキスト(上巻)
【第8章456p 〜 459p掲載】

-- [SQL08_01.SQL]
--             SQLServer7.0  Transact-SQL言語
--             日本技術ソフト開発  堀川 明
--            http://www.horikawa.ne.jp/msde/
--
-- このSQLプログラムは、
--           明示的なトランザクションでよく誤る例
-- です
-- トランザクション内の整合性違反によって全体がロールバック
-- されると勘違いする例です
--
-- この[社員]テーブルは、AccessのNorthwindデモデータベース
-- の[社員]テーブルをSQLServerに転送したものです
--

-- カレントデータベースを MySampleTest にする
    USE MySampleTest
GO

-- (件処理されました)のメッセージを抑止する
    SET NOCOUNT ON
GO


-- *********************************************************
--                    【事前確認チェック】
-- [社員]テーブルの[社員コード]に主キーが設定されていますか?
-- Accessのテーブルを単純に転送コピー(Export)しただけでは
-- 主キーは設定されません
-- [参照]
--    SQL07_06でも主キー検査を行っていますが、ここでは
--    ストアドプロシージャ sp_pkeys を使った方法を使います
-- *********************************************************
    DECLARE @CNT int , @CL_NAME sysname
     SELECT @CNT      = 0  ,
            @CL_NAME  = ''

    -- sp_pkeysの結果受け取り用一時テーブルの作成
    CREATE TABLE #TMP_PKEYS(
             TABLE_QUALIFIER sysname  , -- テーブル識別子の名前
             TABLE_OWNER     sysname  , -- テーブル所有者の名前
             TABLE_NAME      sysname  , -- テーブルの名前
             COLUMN_NAME     sysname  , -- 返される TABLE_NAME の各列の列名
             KEY_SEQ         smallint , -- 連結主キーのシーケンス番号
             PK_NAME         sysname    -- 主キー識別子
    )

    -- sp_pkeysを実行する
    -- 社員テーブルの主キー情報を一時テーブルに格納する
    INSERT INTO #TMP_PKEYS EXECUTE sp_pkeys '社員'

    -- 主キーがありますか?(得られた行数は1行でないとダメ)
    SELECT @CNT = COUNT(*) FROM #TMP_PKEYS    
    IF( @CNT <> 1 )
       BEGIN
          DROP TABLE #TMP_PKEYS  -- 一時テーブル削除
          IF( @CNT = 0 )
            BEGIN
              PRINT '社員表に主キーが設定されていません。'
              PRINT 'ACCESSのテーブルを転送しただけでは、主キーは設定されません。'
              PRINT '社員コードに主キーを設定してください'
              RAISERROR('主キーがありません。中止します',16,127)
            END
          ELSE
            BEGIN
             RAISERROR('列数(%d)個に振られた連結主キーです。単一列にしてください',16,127,@CNT)
            END
         RETURN
       END

    -- その主キーは、社員コードに付けられたものでしょうか?
    SELECT @CL_NAME = COLUMN_NAME FROM  #TMP_PKEYS
    IF( @CL_NAME <> '社員コード' )
        BEGIN
          DROP TABLE #TMP_PKEYS  -- 一時テーブル削除
          RAISERROR('主キーが列名(%s)に付けられています。社員コード列にしてください'
                       ,16,127, @CL_NAME)
          RETURN
        END

    DROP TABLE #TMP_PKEYS  -- 一時テーブル削除
    PRINT ''
    -- PRINT '社員コード列に主キーが設定されています(事前確認OK!)'
GO

-- レコード挿入位置にレコードがあれば削除します
    DELETE FROM 社員 WHERE( 社員コード BETWEEN 10 AND 20 )
GO

-- *********************************************************
--         【トランザクションを使ったレコード挿入処理】
-- トランザクション内で主キーの重複登録整合性違反を発生させます
-- *********************************************************
    BEGIN TRANSACTION  -- トランザクション開始
                                                   --(注)実際は、半角カナ文字です
        INSERT INTO 社員(社員コード,フリガナ,氏名) VALUES(10,'ヤマダ イチロウ' , '山田 一郎')
        INSERT INTO 社員(社員コード,フリガナ,氏名) VALUES(11,'ヤマダ ジロウ' , '山田 二郎')
        INSERT INTO 社員(社員コード,フリガナ,氏名) VALUES(12,'ヤマダ サブロウ', '山田 三郎')
        -- 社員コード11番は、整合性違反。主キーがすでに登録済み
        INSERT INTO 社員(社員コード,フリガナ,氏名) VALUES(11,'カトウ イチロウ'  , '加藤 一郎')

    COMMIT TRANSACTION
GO

-- *******************************
--    レコードの登録結果を表示
-- *******************************
    DECLARE @社員コード int , @フリガナ varchar(20) , @氏名 varchar(20)
    DECLARE @Str社員コード varchar(4) , @strout varchar(80)
    DECLARE hC INSENSITIVE CURSOR FOR 
         SELECT 社員コード,フリガナ,氏名 FROM 社員
         WHERE( 社員コード BETWEEN 10 AND 20 )

    -- カーソルを開いてレコードを表示する
    OPEN hC

    -- レコードはありますか?
    IF( @@CURSOR_ROWS = 0 )
      BEGIN
             PRINT ''
             PRINT '*** レコードは存在しません ***'
             PRINT '    レコード登録に失敗!!      '
             GOTO L9999
      END

   -- タイトル行の出力 
    EXEC master..xp_sprintf @strout OUTPUT , '[%.2s][%12s][%12s]' ,
              'NO' , 'フリガナ' , ' 氏 名 '
    PRINT ''
    PRINT '**** 登録結果 ****'
    PRINT @strout

    -- 先頭行の取り出し
    FETCH NEXT FROM hC INTO @社員コード,@フリガナ,@氏名
 
    -- 0の時は、正常に取得できました
    WHILE( @@FETCH_STATUS = 0 )
      BEGIN
            -- 取り出し内容の編集とその出力
            SELECT @Str社員コード = CONVERT(char(4),@社員コード) 
            EXEC master..xp_sprintf @strout OUTPUT , '[%.2s][%12s][%12s]' ,
                     @Str社員コード , @フリガナ , @氏名
            PRINT @strout
            -- 次行の取り出し
            FETCH NEXT FROM hC INTO @社員コード,@フリガナ,@氏名
     END

L9999:
    -- カーソルを閉じて破棄する
    CLOSE hC
    DEALLOCATE hC
GO




技術評論社の書籍ガイドへ
上巻:ISBN4-7741-0965-7

ウィンドウを閉じる


(株)日本技術ソフト開発 責任編集:堀川 明
MSDE FunClubに関するご意見・ご要望等ございましたら、 msdefun@horikawa.ne.jp までご連絡下さい。
HOME: http://www.horikawa.ne.jp/msde/


MSDE FunClubの運営は、マイクロソフト社とは一切の関係はありません