アプリケーション テクニック PowerBuilder® 11.1 DOCUMENT ID: DC37774-01-1110-02 LAST REVISED: October 2008 Copyright © 1991-2008 by Sybase, Inc. All rights reserved. 本書は Sybase ソフトウェアの付属マニュアルであり、新しいマニュアルまたはテクニカル ノートで特に示されないかぎ り、後続のリリースにも付属します。このマニュアルの内容は、予告なく変更されることがありますが、Sybase,Inc. およ びその関連会社では内容の変更に関して一切の責任を負いません。このマニュアルに記載されているソフトウェアはライ センス契約に基づいて提供されるものであり、無断で使用することはできません。 予定したソフトウェアのリリース日にのみアップグレードを提供します。本書に記載されている内容は、Sybase, Inc. およ びその関連会社の書面による事前許可を得ずに、電子的、機械的、手作業、光学的、またはその他のいかなる手段によっ ても複製、転載、翻訳することを禁じます。 Sybase の商標は Sybase の商標ページ のサイト http://www.sybase.com/detail?id=1011207 に記載されています。記載の Sybase およ びマークは Sybase, Inc の商標です。® はアメリカ合衆国における登録商標を示します。 Java およびすべての Java ベースのマークは、米国および他国における Sun Microsystems, Inc. の商標または登録商標です。 Unicode および Unicode のロゴは Unicode, Inc. の登録商標です。 本書で記載されている上記以外の社名および製品名は、各社の商標または登録商標の場合があります。 本書に記載されている内容は、将来予告なしに変更することがあります。また、本ソフトウェアおよび説明書を使用した ことによる損害、または第三者からのいかなる請求についても、サイベース株式会社、その親会社である米国法人 Sybase, Inc. またはその関連会社は、一切の責任を負わないものとします。 目次 本書について ................................................................................................................................ xix 第1部 アプリケーション テクニックの学習 第1章 サンプル アプリケーションの使い方.......................... サンプル アプリケーションについて............................................... Web サイトのサンプル ............................................................. DVD 内のサンプル .................................................................... サンプル アプリケーションのインストール .................................... サンプル アプリケーションを開く .................................................. Code Examples アプリケーションの使い方.................................... サンプルの参照 ......................................................................... サンプルの検索 ......................................................................... サンプルの実行と調査 .............................................................. 3 3 4 4 5 5 6 6 7 8 第2部 言語テクニック 第2章 オブジェクト指向プログラミング ........................... 用語の確認 ..................................................................................... PowerBuilder のテクニック ........................................................... その他のテクニック ....................................................................... 13 15 20 PowerScript についての特別なトピック ..................... ドット表記 ..................................................................................... 定数の宣言 ..................................................................................... インスタンス変数のアクセスの制御.............................................. 名前の重複の解決 .......................................................................... 先祖スクリプトからの戻り値 ........................................................ 関数とイベントの引数の型 ............................................................ 先祖変数と子孫変数 ....................................................................... データウィンドウと外部オブジェクトにおける式の最適化.......... 25 30 30 31 33 35 36 38 第3章 アプリケーション テクニック 13 25 iii 目次 第4章 PowerBuilder での例外処理 ........................................................... 例外処理の基本 ....................................................................... 例外処理用のオブジェクト ..................................................... 例外の処理 .............................................................................. ユーザ定義の例外型の作成 ..................................................... 柔軟性の向上とオブジェクトの再利用の促進 ........................ SystemError イベントと Error イベントの使い方................... ガベージ コレクションとメモリ管理............................................. メモリ管理の設定.................................................................... 効率的なコンパイルとパフォーマンス .......................................... テキスト ファイルとバイナリ ファイルの読み書き ...................... 39 40 40 41 44 46 48 49 51 53 53 PowerBuilder のクラス定義に関する情報の取得 .............. クラス定義情報の概要 ................................................................... 用語 ......................................................................................... PowerBuilder クラス定義の使用について............................... クラス定義の調査 .......................................................................... クラス定義オブジェクトの取得 .............................................. クラスに関する詳細情報の取得 .............................................. クラスのスクリプトに関する情報の取得................................ 変数に関する情報の取得......................................................... 57 58 60 61 61 62 64 67 57 第3部 ユーザ インタフェース テクニック 第5章 MDI アプリケーションの構築................................ MDI について ................................................................................. MDI フレーム ウィンドウの作成 ................................................... シートの使い方 .............................................................................. マイクロヘルプの提供 ................................................................... MDI アプリケーションにおけるツールバーの使い方 .................... ツールバーの動作のカスタマイズ .......................................... ツールバー設定の保存と復元.................................................. クライアント領域のサイズ設定..................................................... MDI アプリケーションにおけるキーボード操作について............. 71 74 75 77 78 78 80 84 87 ウィンドウ インスタンスの管理 ............................. ウィンドウ インスタンスについて ................................................ ウィンドウ インスタンスの宣言.................................................... ウィンドウ配列の使い方................................................................ 子孫オブジェクトのエンティティの参照 ...................................... 91 93 94 97 第6章 iv 71 91 PowerBuilder 目次 第7章 ウィンドウにおけるタブ コントロールの使い方 ............... 99 タブ コントロールについて ........................................................... 99 タブ ページの定義と管理............................................................. 100 タブ コントロールのカスタマイズ .............................................. 104 スクリプトにおけるタブ コントロールの使い方......................... 107 スクリプトでのタブ ページの参照 ....................................... 107 タブ ページにあるコントロールの参照 ................................ 110 タブ ページを開く、閉じる、非表示にする ......................... 111 タブ ページの履歴................................................................. 111 必要なときだけタブ ページを生成 ....................................... 112 タブ コントロールの各部分におけるイベント ..................... 114 第8章 ツリービュー コントロールの使い方........................ ツリービュー コントロールについて........................................... ツリービューの表示..................................................................... 項目挿入関数......................................................................... ルート レベルへの項目の挿入............................................... ルート レベルの下への項目の挿入 ....................................... ツリービューの項目の管理 .......................................................... 項目の削除 ............................................................................ 項目の名前の変更.................................................................. ドラッグ アンド ドロップによる項目の移動 ........................ 項目のソート......................................................................... ツリービュー ピクチャの管理 ..................................................... 項目のピクチャ ..................................................................... ピクチャ リストの設定 ......................................................... オーバーレイ ピクチャの使い方 ........................................... データウィンドウのデータのツリービューへの表示 .................. 117 117 121 122 123 124 127 128 129 130 134 136 136 137 138 139 第9章 ウィンドウでのリストの使い方 ............................ リストの提示について ................................................................. リストの使い方 ............................................................................ ドロップダウン リストの使い方 .................................................. リストビュー コントロールの使い方........................................... 詳細表示の使い方.................................................................. 143 143 144 149 152 158 第 10 章 ドラッグ アンド ドロップ機能の使い方 ..................... 161 ドラッグ アンド ドロップ機能について ...................................... 161 ドラッグ アンド ドロップのプロパティ、イベント、および関数 162 ドラッグされたコントロールの識別............................................ 164 第 11 章 オンライン ヘルプの提供.................................. 165 アプリケーション テクニック v 目次 ヘルプ ファイルの作成 ................................................................ 165 開発者に対するオンライン ヘルプの提供 ................................... 167 エンド ユーザに対するオンライン ヘルプの提供........................ 169 第4部 データ アクセス テクニック 第 12 章 トランザクション オブジェクトの使い方 .................... 173 トランザクション オブジェクトについて ................................... 173 トランザクション オブジェクトのプロパティ ..................... 174 トランザクション オブジェクトのプロパティと PowerBuilder データベース インタフェースのサポート 177 トランザクション オブジェクトの使い方 ................................... 178 トランザクションの基礎....................................................... 179 デフォルト トランザクション オブジェクト ........................ 180 トランザクション オブジェクトのプロパティ値の設定 ....... 181 外部ファイルからの値の読み込み ........................................ 182 データベースへの接続 .......................................................... 183 PowerBuilder アプリケーションで接続するための [プレビュー]タブの使い方........................................... 183 データベースとの接続の解除................................................ 184 複数のデータベース接続におけるトランザクション オブジェクトの定義 ....................................................... 185 SQL 文実行後のエラー処理 .................................................. 188 データベース トランザクションのプール............................. 189 ストアド プロシージャを呼び出すためのトランザクション オブジェクトの使い方.................................................... 190 ステップ 1: 標準クラス ユーザ オブジェクトの定義............ 192 ステップ 2: 外部関数としてのストアド プロシージャの宣言 193 ステップ 3: ユーザ オブジェクトの保存............................... 195 ステップ 4: SQLCA に対するデフォルトの グローバル変数の型の指定 ............................................ 195 ステップ 5: アプリケーションでユーザ オブジェクトを 使用する ......................................................................... 197 ストアド プロシージャを呼び出すとき サポートされている DBMS の機能 ................................ 199 第 13 章 MobiLink 同期の使い方.................................... MobiLink 同期について ................................................................ 同期の動作方法 ............................................................................ PowerBuilder 同期オブジェクトの使い方.................................... ウィザードを使用する準備 ................................................... 生成されるもの ..................................................................... vi 203 203 208 210 210 211 PowerBuilder 目次 MLSync のインスタンスの作成 ............................................ MobiLink 同期の補助オブジェクト ....................................... アプリケーションでの同期オブジェクトの使い方 ............... リモート マシンでの同期の実行時要件 ................................ 統合データベースの準備.............................................................. 接続イベント......................................................................... テーブル イベント................................................................. Sybase Central でのスクリプトおよびユーザに対する作業 リモート データベースの作成 ..................................................... パブリケーションの作成と変更 ............................................ Mobile Link ユーザの作成...................................................... サブスクリプションの追加 ................................................... 同期のテクニック ........................................................................ 212 213 216 219 222 223 224 228 231 231 234 236 237 第 14 章 PowerBuilder XML サービスの使い方 ...................... XML と PowerBuilder について ................................................... PBDOM について......................................................................... PBDOM オブジェクト階層 .......................................................... PBDOM ノード オブジェクト...................................................... PBDOM_OBJECT ................................................................. PBDOM_DOCUMENT .......................................................... PBDOM_DOCTYPE.............................................................. PBDOM_ELEMENT .............................................................. PBDOM_ATTRIBUTE ........................................................... PBDOM_ENTITYREFERENCE ............................................ PBDOM_CHARACTERDATA ............................................... PBDOM_TEXT ...................................................................... PBDOM_CDATA ................................................................... PBDOM_COMMENT............................................................. PBDOM_PROCESSINGINSTRUCTION............................... アプリケーションへの pbdom110.pbx の追加............................. PBDOM の使い方......................................................................... XML の検証 ........................................................................... XML から XML ドキュメントの作成 ..................................... 最初からの XML ドキュメントの作成................................... ノード データへのアクセス .................................................. ノード ツリー階層の操作...................................................... PBDOM 例外の処理 ..................................................................... XML 名前空間 .............................................................................. PBDOM_ATTRIBUTE の名前および名前空間の設定 ........... 241 241 242 243 244 245 247 248 248 251 254 254 255 258 258 259 260 261 261 262 264 265 267 267 269 270 第 15 章 グラフの操作 ............................................ 275 グラフの使い方 ............................................................................ 275 アプリケーション テクニック vii 目次 コードにおけるグラフ コントロールの操作 ......................... グラフへのデータ表示 ................................................................. グラフのプロパティの修正 .......................................................... グラフ要素の表示.................................................................. グラフ要素の参照.................................................................. データのプロパティへのアクセス ............................................... データの情報の取得 .............................................................. グラフのデータの保存 .......................................................... 色や模様、そのほかのデータの修正..................................... ポイント アンド クリックの使い方 ............................................. 276 277 279 280 280 281 282 283 283 283 第 16 章 リッチテキストの作成方法 ................................. 287 アプリケーションにおけるリッチテキストの使い方 .................. 287 リッチテキストの作成 .......................................................... 288 リッチテキスト アプリケーションの配布............................. 288 リッチテキスト データウィンドウ オブジェクトの使い方 ......... 289 リッチテキスト エディット コントロールの使い方 .................... 291 エンド ユーザに制御権を与える ........................................... 292 リッチテキスト エディット コントロールのためのテキスト 293 ActiveX スペル チェック コントロールの使用...................... 302 リッチテキストの書式設定 ................................................... 303 入力フィールド ..................................................................... 304 データベースのデータの使い方 ............................................ 305 リッチテキスト エディット コントロールにおける カーソル位置 .................................................................. 307 プレビューと印刷.................................................................. 308 リッチテキストとエンド ユーザ.................................................. 311 第 17 章 データ ソース間のデータ転送 .............................. データ パイプラインについて ..................................................... 必要なオブジェクトの作成 .......................................................... パイプライン オブジェクトの作成 ....................................... ユーザ オブジェクトの作成 .................................................. ウィンドウの作成.................................................................. パイプライン処理の前準備 .......................................................... パイプライン処理の開始.............................................................. パイプライン処理のモニタ ................................................... パイプライン処理のキャンセル ............................................ 更新処理のコミット .............................................................. エラー行の処理 ............................................................................ エラー行の修復 ..................................................................... エラー行の破棄 ..................................................................... パイプラインの後処理 ................................................................. viii 315 316 317 317 320 321 325 328 330 332 334 335 336 338 339 PowerBuilder 目次 第5部 プログラム アクセス テクニック 第 18 章 DDE の使い方 ........................................... 343 DDE について .............................................................................. 343 DDE 関数とイベント ................................................................... 344 第 19 章 アプリケーションにおける OLE の使い方 ................... 347 PowerBuilder における OLE のサポート ..................................... 347 ウィンドウにおける OLE コントロール ...................................... 349 OLE コントロールと挿入可能なオブジェクト ............................ 352 OLE コントロールの設定...................................................... 352 リンクと埋め込み.................................................................. 356 オフサイト アクティブ化とインプレース アクティブ化 ...... 358 インプレース アクティブ化に対するメニュー ..................... 359 OLE コントロール上でのオブジェクトの修正 ..................... 361 OLE カスタム コントロール ........................................................ 366 OLE カスタム コントロールの設定 ...................................... 366 ActiveX コントロールのプログラミング............................... 368 プログラム可能な OLE オブジェクト.......................................... 370 OLEObject オブジェクト型................................................... 370 OLEControl、OLECustomControl、 OLEObject データ型の代入............................................ 373 オートメーション.................................................................. 375 スクリプトにおける OLE オブジェクト ...................................... 380 オートメーションのインタフェース..................................... 381 オートメーションと Any 型 .................................................. 388 効率的な OLEObjects 変数の使い方 ..................................... 389 エラー処理 ............................................................................ 390 ホット リンクの作成 ............................................................. 393 OLE サーバで使用できる言語............................................... 395 OLE オブジェクトへの低レベル アクセス............................ 396 データウィンドウ オブジェクトにおける OLE オブジェクト 396 オブジェクト ブラウザでの OLE 情報......................................... 400 OLE オブジェクトの高度な操作 .................................................. 402 OLE ストレージの構造 ......................................................... 403 ストレージとストリームに対するオブジェクト データ型 ... 404 ストレージを開く、保存する................................................ 405 ストリームを開く.................................................................. 411 ストレージを使用する際のストラテジ ................................. 416 第 20 章 PowerBuilder のランタイム オートメーション サーバ ........ 417 ランタイム オートメーション サーバの使い方 ........................... 418 アプリケーション テクニック ix 目次 ランタイム オートメーションの用途.................................... 3 つのアクセス方法............................................................... ユーザ オブジェクトをオートメーション サーバとして 使用する方法 .................................................................. サーバとなるクラス ユーザ オブジェクトの作成................. ユーザ オブジェクトのランタイム ライブラリの構築.......... ユーザ オブジェクトの登録 .................................................. ユーザ オブジェクトにアクセスする クライアント アプリケーションのコードの記述 ........... PowerBuilder をオートメーション サーバとして使用する方法 .. アクセスするユーザ オブジェクトの作成............................. ランタイム ライブラリの構築............................................... PowerBuilder とユーザ オブジェクトにアクセスする クライアント アプリケーションのコードの記述 ........... 名前付きサーバの作成と使用 ...................................................... ユーザ オブジェクトとレジストリについての詳細 ..................... 識別子について ..................................................................... オブジェクトに関する情報の登録場所 ................................. レジストリ情報の作成 .......................................................... オートメーション サーバを使用するアプリケーションの配布 ... 複数のバージョンとアップデート ........................................ オートメーション サーバ リファレンス ...................................... PowerBuilder.Application サーバ オブジェクト........................... CreateObject 関数........................................................................ GenerateGUID 関数 ..................................................................... GenerateRegFile 関数.................................................................. GenerateTypeLib 関数 ................................................................. 例外コード ................................................................................... レジストリ更新ファイルのサンプル............................................ 419 420 423 423 424 425 426 428 428 429 430 433 435 435 436 439 443 444 445 445 447 450 452 455 459 460 第 21 章 MAPI の使い方 ........................................... 463 MAPI について ............................................................................. 463 MAPI の使い方 ............................................................................. 464 第 22 章 外部関数とそのほかの拡張処理機能の使い方 ................. 外部関数の使い方 ........................................................................ 外部関数の宣言 ..................................................................... 外部関数の宣言例.................................................................. 引数の受け渡し ..................................................................... UNIX での外部関数とプログラムの呼び出し........................ ユーティリティ関数の使い方 ...................................................... Windows メッセージの送信......................................................... メッセージ オブジェクト............................................................. x 467 467 468 469 471 474 474 476 478 PowerBuilder 目次 メッセージ オブジェクトのプロパティ ................................ コンテキスト情報 ........................................................................ コンテキスト情報サービス ................................................... コンテキスト キーワード サービス ...................................... CORBACurrent サービス ...................................................... エラー ロギング サービス..................................................... インターネット サービス...................................................... Secure Sockets Layer サービス............................................ トランザクション サーバ サービス ...................................... 478 480 482 485 487 487 487 491 491 第6部 分散アプリケーションの開発 第 23 章 PowerBuilder を使った分散アプリケーション開発 ........... 495 分散アプリケーションのアーキテクチャ .................................... 495 サーバのサポート ........................................................................ 496 第 24 章 EAServer コンポーネントの構築........................... EAServer コンポーネントの構築について .................................. ウィザードの使い方について................................................ 開発プロセスについて .......................................................... アプリケーション サーバ プロファイルの作成 .................... 共有コンポーネントおよびサービス コンポーネントの操作....... 共有コンポーネントについて................................................ サービス コンポーネントについて ....................................... スレッド実行の問題とコンポーネントの種類 ...................... EAServer Thread Manager の使い方 .................................... インスタンス プーリングのサポート........................................... トランザクションのサポート ...................................................... EAServer コンポーネントからデータベースへのアクセス ......... 接続キャッシュの使い方....................................................... 検索操作の実行 ..................................................................... 更新の実行 ............................................................................ 結果集合の受け渡し .............................................................. コンポーネント インタフェースの定義 ....................................... 既存インタフェースの実装 .......................................................... 別のサーバ コンポーネントのメソッドの呼び出し ..................... コンポーネント プロパティへのアクセス ................................... Web サービスとしての NVO の公開 ........................................... コンポーネントのテストとデバッグ............................................ ライブ編集 ............................................................................ リモート デバッグ................................................................. EAServer ログへのメッセージ出力 ...................................... アプリケーション テクニック 501 501 502 502 503 505 505 506 508 511 512 516 523 524 528 529 534 537 542 544 546 551 553 553 555 558 xi 目次 データの印刷................................................................................ Solaris オペレーティング システムでの印刷........................ PDF への印刷........................................................................ EAServer へのコンポーネントの配布.......................................... 558 559 563 564 第 25 章 EAServer クライアントの構築 ............................. EAServer クライアントの構築について ...................................... ウィザードの使い方について................................................ 開発プロセスについて .......................................................... EAServer への接続 ...................................................................... コードを手書きする方法....................................................... ウィザードを使用した接続オブジェクトの作成................... EAServer プロキシ オブジェクトの生成 ..................................... コンポーネント メソッドの呼び出し........................................... コンポーネント メソッドの呼び出し.................................... EJB コンポーネント メソッドの呼び出し ............................ インスタンスの破棄 .............................................................. JaguarORB オブジェクトの使用 ................................................. String_To_Object を使用したインスタンス化 ...................... ネーミング サービス API によるインスタンス化 ................. クライアントとコンポーネントを区別するトランザクション .... サーバ メッセージ返送の要求 ..................................................... 例........................................................................................... エラー処理 ................................................................................... CORBA 例外の処理............................................................... Error イベントのスクリプト作成 .......................................... SystemError イベントのスクリプト作成 .............................. クライアント アプリケーションの配布 ....................................... 569 569 570 570 571 571 573 574 576 576 578 582 583 584 586 588 591 592 596 598 599 600 601 第 26 章 PowerBuilder クライアントでの SSL の使い方 .............. EAServer とのセキュアな接続 .................................................... PowerBuilder での SSL 接続........................................................ SSL プロパティ..................................................................... ORB プロパティ.................................................................... セキュアな接続の確立 ................................................................. SSL コールバックの使い方 ......................................................... セッション情報の取得 .......................................................... SSLCallback オブジェクトの実装 ........................................ SSLCallback オブジェクトの指定 ........................................ セッション セキュリティ情報の取得........................................... 603 603 605 605 608 609 612 612 613 615 616 第 27 章 COM/COM+ コンポーネントの構築 ......................... 617 xii PowerBuilder 目次 COM/COM+ コンポーネントの構築について .............................. 617 ウィザードの使い方について................................................ 618 開発プロセスについて .......................................................... 619 コンポーネント オブジェクト モデルについて ........................... 620 PowerBuilder COM サーバについて ..................................... 621 オートメーション サーバと PowerBuilder COM サーバの比較 .................................. 621 コンポーネント インタフェースの定義 ....................................... 624 メソッドとデータ型 .............................................................. 624 コーディング上の制約 .......................................................... 626 ログ ファイルへのエラー記録............................................... 627 COM コンポーネントからデータベースへのアクセス ................ 628 結果集合の受け渡し .............................................................. 629 トランザクションのサポート ...................................................... 632 別のサーバ コンポーネントのメソッドの呼び出し ..................... 635 セキュリティ問題 ........................................................................ 636 プロジェクト ペインタでの COM/COM+ コンポーネントの構築 637 コンポーネントの自動登録 ................................................... 639 COM+ にコンポーネントを配布 ........................................... 639 カスタム インタフェースとデュアル インタフェースの選択 640 埋め込み PBD の設定............................................................ 640 PowerBuilder COM オブジェクトの実行 ..................................... 641 メモリの割り当て.................................................................. 641 PowerBuilder COM サーバの配布 ................................................ 642 COM 対応のアプリケーションによる PowerBuilder COM サーバの使い方............................... 642 クライアントから PowerBuilder COM サーバへのアクセス ....... 643 クライアントとしての Visual Basic...................................... 643 クライアントとしての C++................................................... 644 DCOM での PowerBuilder COM サーバと オブジェクトの使い方.................................................... 647 第 28 章 COM/COM+ クライアントの構築........................... COM/COM+ クライアントの構築について.................................. COM サーバへの接続................................................................... COM コンポーネントとのやり取り ............................................. クライアントからのトランザクション制御................................. 651 651 652 653 654 第 29 章 EJB クライアントの構築 .................................. EJB クライアントの構築について............................................... アプリケーションへの pbejbclient110.pbx の追加 ...................... EJB プロキシ オブジェクトの生成.............................................. EJB プロキシ プロジェクトの使い方 ................................... 657 657 659 660 660 アプリケーション テクニック xiii 目次 ejb2pb110 ツールの使い方 ................................................... 生成されたプロキシの表示方法 ............................................ データ型マッピング .............................................................. Java VM の作成 ........................................................................... サーバへの接続 ............................................................................ コンポーネント メソッドの呼び出し........................................... 例外処理....................................................................................... クライアント管理のトランザクション ........................................ クライアントのデバッグ.............................................................. 664 665 667 668 671 672 677 679 680 第7部 WEB アプリケーションの開発 第 30 章 PowerBuilder での Web アプリケーション開発 .............. Web アプリケーションの作成 ..................................................... .NET Web フォーム アプリケーションとコンポーネント........... Web サービス .............................................................................. JSP ターゲット............................................................................ Web データウィンドウ ................................................................ データウィンドウ Web コントロール ActiveX ............................ データウィンドウ プラグイン ..................................................... PowerBuilder ウィンドウ プラグイン.......................................... PowerBuilder ウィンドウ ActiveX................................................ 683 683 684 684 685 685 687 687 688 689 第 31 章 Web サービス クライアントの構築.......................... Web サービスについて ................................................................ Web サービス クライアントの構築について........................ Web サービス エンジンの選択 ............................................. Web サービスにアクセスするための ファイアウォール設定の指定......................................... エクステンション ファイルのオブジェクトのインポート .......... Web サービス プロキシ オブジェクトの生成.............................. SOAP サーバへの接続 ................................................................. Web サービス メソッドの起動 .................................................... 例外処理....................................................................................... UDDI 照会 API の使い方 .............................................................. 691 691 693 693 データウィンドウ プラグインの使い方 ...................... データウィンドウ プラグインについて ....................................... データウィンドウ プラグインの機能.................................... データウィンドウ プラグインのインストールと設定........... データウィンドウ プラグインの開発と配布 ......................... Powersoft レポート(PSR)の保存 ............................................ 711 711 712 714 714 715 第 32 章 xiv 695 696 698 705 707 707 708 PowerBuilder 目次 第 33 章 第 34 章 HTML ページの作成 ..................................................................... サンプル ページ .................................................................... Web サーバの設定 ....................................................................... ユーザのワークステーションの設定............................................ 716 717 718 719 PowerBuilder ウィンドウ プラグインの使い方 .............. PowerBuilder ウィンドウ プラグインについて ........................... プラグインとなるアプリケーションの種類 .......................... PowerBuilder ウィンドウ プラグインの機能 ........................ PowerBuilder ウィンドウ プラグインのインストールと設定 ...... セキュリティ PowerBuilder ウィンドウ プラグインの使い方 ..... PowerBuilder ウィンドウ プラグイン アプリケーションの 開発と配布...................................................................... PowerBuilder アプリケーションの作成 ....................................... プラグイン アプリケーションの設計の選択 ......................... ウィンドウ ペインタでの開始ウィンドウの定義.................. PowerBuilder でのアプリーションのテスト ......................... 動的ライブラリの構築 .......................................................... HTML ページの作成 ..................................................................... Embed 要素の属性 ................................................................ サンプル ページ .................................................................... 追加属性を持つ Embed 要素................................................. サーバの設定................................................................................ ユーザのワークステーションの設定............................................ 必要なコンポーネント .......................................................... Web ページとプラグイン アプリケーションの表示 ............. 721 722 724 725 727 728 PowerBuilder ウィンドウ ActiveX の使い方 ................ PowerBuilder ウィンドウ ActiveX について ................................ PowerBuilder ウィンドウ ActiveX で動作する アプリケーションの種類 ................................................ PowerBuilder ウィンドウ ActiveX の機能 ............................. PowerBuilder ウィンドウ ActiveX のインストールと設定.... PowerBuilder ウィンドウ ActiveX アプリケーションの 開発と配布...................................................................... PowerBuilder アプリケーションの作成 ....................................... アプリケーションのデザイン................................................ ウィンドウ ペインタでの開始ウィンドウの定義.................. PowerBuilder でのアプリーションのテスト ......................... HTML ページの作成 ..................................................................... Object 要素の属性 ................................................................. 基本ページ ............................................................................ クライアント側のスクリプト................................................ 747 747 アプリケーション テクニック 729 730 731 734 735 736 738 738 740 741 742 743 743 744 748 749 750 751 752 753 756 757 759 760 763 764 xv 目次 PowerBuilder ウィンドウ ActiveX のイベント............................. サーバの設定................................................................................ ユーザのワークステーションの設定............................................ Web ページと PowerBuilder ウィンドウ ActiveX アプリケーションの表示 ................................................ 773 774 774 775 第8部 全般的なテクニック 第 35 章 アプリケーションの国際化 ................................. 国際化アプリケーションの開発................................................... Unicode の使い方......................................................................... Unicode について.................................................................. PowerBuilder での Unicode サポート ................................... ユーザ インタフェースの国際化.................................................. 779 779 780 780 781 786 第 36 章 利用しやすいアプリケーションの作成 ....................... アクセシビリティの課題についての理解 .................................... ソフトウェアおよび Web アプリケーションの アクセシビリティ要件.................................................... PowerBuilder を使用した利用しやすい ソフトウェア アプリケーションの作成 ......................... VPAT について ............................................................................ 製品のアクセシビリティのテスト ............................................... 787 787 第 37 章 印刷 ..................................................... 印刷関数....................................................................................... 印刷の基礎 ................................................................................... ジョブの印刷................................................................................ タブの使い方................................................................................ 印刷ジョブの停止 ........................................................................ 高度な印刷技法 ............................................................................ 799 799 801 801 802 803 804 第 38 章 初期設定ファイルと Windows レジストリの管理 ............. 環境設定とデフォルト設定について............................................ 初期設定ファイルでの情報の管理 ............................................... Windows レジストリでの情報の管理 .......................................... 807 807 808 809 第 39 章 InfoMaker の様式とアクションの作成 ....................... 811 フォーム様式について ................................................................. 811 フォーム様式でのデータウィンドウ コントロールの命名 .......... 815 xvi 790 792 796 796 PowerBuilder 目次 フォーム様式の作成および使用 ................................................... 既存の様式の修正 ........................................................................ 様式の基礎としてのウィンドウの識別 ................................. 最初からの様式の作成 ................................................................. 様式の完成 ................................................................................... セントラル データウィンドウ コントロールに対する作業 .. コントロールの追加 .............................................................. アクションの定義.................................................................. メニューの使い方.................................................................. スクリプトの記述.................................................................. その他の機能の追加 .............................................................. 様式の使い方................................................................................ カスタム フォーム様式を使用したフォームの作成 .............. フォーム様式の使用の管理 ................................................... 816 816 818 819 820 820 821 822 823 824 824 824 825 826 第9部 配布のテクニック 第 40 章 配布用アプリケーションのパッケージ化 .................... アプリケーションの配布について ............................................... アプリケーションの実行版の作成 ............................................... コンパイラの基本事項 .......................................................... パッケージに含まれる要素 ................................................... PowerBuilder リソース ファイルの作成................................ パッケージ化モデルの選択 ................................................... パッケージ化モデルの実装 ................................................... 実行アプリケーションのテスト ............................................ エンド ユーザへのアプリケーションの配布................................ インストール チェックリスト............................................... 配布済みアプリケーションの起動 ........................................ 831 831 832 832 833 839 841 845 846 847 847 851 第 41 章 アプリケーションとコンポーネントの配布 .................. アプリケーション、コンポーネント、 およびサポート ファイルの配布 .................................... PowerBuilder ランタイム パッケージャ ...................................... サードパーティ製コンポーネントと配布 .................................... Apache ファイル................................................................... Microsoft ファイル ................................................................ Sun Microsystems ファイル.................................................. Web サービスの SOAP クライアントで使用する ソフトウェア .................................................................. PowerBuilder ランタイム ファイル ............................................. データベース接続 ........................................................................ 853 アプリケーション テクニック 854 859 863 864 864 865 866 866 869 xvii 目次 ネイティブ データベース ドライバ ...................................... ODBC データベース ドライバとサポート ファイル............. OLE DB データベース プロバイダ........................................ ADO.NET データベース インタフェース.............................. JDBC データベース インタフェース .................................... Java サポート .............................................................................. PowerBuilder エクステンション .................................................. PDF と XSL-FO のエクスポート ................................................. Ghostscript distiller の使い方................................................. Apache FO プロセッサの使い方........................................... データウィンドウ Web コントロール ActiveX ............................ プラグインと PowerBuilder ウィンドウ ActiveX コントロール .. EAServer 上の PowerBuilder コンポーネント ............................. PowerBuilder COM サーバ........................................................... PowerBuilder オートメーション サーバ ...................................... OLE オートメーション オブジェクトの レジストリ情報の作成.................................................... EAServer 上の Web データウィンドウ ....................................... COM+ または IIS 上の Web データウィンドウ ........................... 870 871 876 877 878 879 881 882 882 885 886 887 888 891 892 893 893 895 索引 ............................................................................................................................................. 897 xviii PowerBuilder 本書について 対象とする読者 このマニュアルは、PowerBuilder® によるクライアント / サーバ ア プリケーション、分散アプリケーション、または Web アプリケー ション開発に従事している開発者を対象としています。 このマニュアルの使い方 このマニュアルでは、PowerBuilder アプリケーションとコンポー ネントを作成および配布する際に使用するプログラミング テク ニックを紹介します。ここでは、要件に最も適した方法を選択す るためのアドバイスとともに、様々な一般的なアプリケーション 機能を実装するための技術を紹介しています。 PowerBuilder には、このマニュアルで紹介する問題、機能、およ びテクニックを具体例で示すサンプル アプリケーションが付属し ています。PowerBuilder でサンプル アプリケーションのコンポー ネントを調べて、コードのコメントを読み、実践的な作業例を通 じて学習した内容を実際に試してください。 サンプル アプリケーションの使い方については、第 1 章「サンプ ル アプリケーションの使い方」を参照してください。 関連マニュアル PowerBuilder のすべてのマニュアル一覧については、PowerBuilder の『入門』マニュアルを参照してください。 そのほかの情報 製品に関するそのほかの詳細情報については、PowerBuilder DVD、 アシスト Web サイト、および Sybase 製品マニュアル Web サイト (英語)を参照してください。 • PowerBuilder DVD には、製品マニュアルが収められています。 製品マニュアルは、PDF 形式で提供しています。PDF ファイ ルを読んだり、印刷したりするには、Adobe Acrobat Reader が 必要です。Adobe Acrobat Reader は、Adobe Web サイトから無 料でダウンロードすることができます。 • アシスト Web サイトには、標準の Web ブラウザでアクセスす ることができるオンライン版のマニュアルがあります。この Web サイトでは、PDF および HTML 形式でマニュアルを見る ことができます。 オンライン版のマニュアルには、アシストの PowerBuilder のサ イト http://www.ashisuto.co.jp/prod/powerbuilder/ にある「技術情報」 からアクセスできます。 アプリケーション テクニック xix Sybase 製品マニュアル Web サイト(英語)は、標準の Web ブラウ ザからアクセスでき、Sybase の製品マニュアルのほか、EBF/ メン テナンス、技術文書などへのリンクも含んでいます。 • Sybase 製品マニュアル Web サイトには、製品マニュアル のサイト http://www.sybase.com/support/manuals/ からアクセスできます。 表記規則 このマニュアルでは、以下の表記規則を使用します。 例 説明 Retrieve と Update 左記のフォントが説明文で使用されている場合、 以下を表す • コマンド名、関数名、メソッド名 • キーワード(true、false、null など) • データ型(integer、char など) • データベース カラム名(emp_id、f_name など) 変数(variable)または ファイル名(filename) • ユーザ定義オブジェクト(dw_emp、w_main など) 説明文と構文説明で使用された場合、斜体フォ ントは次のいずれかを表す • 変数(myCounter など) • 代入が必要な入力テキスト部分 (pblname.pbd など) [ファイル|上書き保存] dw_1.Update() • ファイル名とパス名 メニュー名とメニュー項目は単純なテキスト で表示される。 「|」は、選択の移動のしかた メニューを示す。たとえば、 [ファイル|上書 き保存]は、 「[ファイル]メニューから[上書 き保存]を選択する」と同義 左記のフォントは以下のいずれかを示す • ダイアログボックスまたはコマンド ライン に入力する情報 • サンプル スクリプトの一部 • サンプル出力の一部 サポートについて xx 「サポート ハンドブック」を参照してください。 PowerBuilder 第 1 部 アプリケーション テクニック の学習 第 1 部では、PowerBuilder に添付しているサンプル アプ リケーションの概要と、これらのサンプルを使ってプロ グラミング テクニックを学習する方法について説明しま す。 第 1 章 サンプル アプリケーションの使い方 この章について この章では、PowerBuilder サンプル アプリケーションの使い方に ついて説明します。 内容 項目 サンプル アプリケーションについて サンプル アプリケーションのインストール サンプル アプリケーションを開く Code Examples アプリケーションの使い方 ページ 3 5 5 6 サンプル アプリケーションについて PowerBuilder には、サンプルで使用されているテクニックを学ん で活用できるように、ソース コード付きのサンプル アプリケー ションが用意されています。サンプルには、以下の 2 種類があり ます。 アプリケーション テクニック • Web サイトからダウンロードできるサンプル • DVD からインストールできるサンプル 3 サンプル アプリケーションについて Web サイトのサンプル PowerBuilder の最新のサンプル アプリケーションとユーティリティ は、Sybase CodeXchange Web サイト(PowerBuilder Samples and Utilities project のサイト http://powerbuilder.codeXchange.sybase.com/)で利用できま す。このページを開くには、Windows の[スタート|プログラム| Sybase | PowerBuilder 11.0 | PB 11.0 コード サンプル]を選択します。 MySybase にログインしていない場合、CodeXchange にアクセスするに は[Sybase Account Login]ページでログインする必要があります。 MySybase のアカウントがない場合は、このページ上のリンクを使って サインアップできます。MySybase は、Sybase Web サイトへのパーソナ ライズされたポータルを提供する無料サービスです。 これらのサンプルは Sybase の社員とユーザが作成したものであり、頻 繁に更新されます。PowerBuilder の特定の機能を使うスタンドアロン アプリケーションがあり、PowerBuilder ネイティブ インタフェースを 使った Web サービスの使用、EJB クライアントの作成、ビジュアルお よび非ビジュアル エクステンションの記述などの機能も使われてい ます。ほとんどのサンプルには、そこで使われる機能とそのダウンロー ド方法および使い方について説明した readme 文書があります。 DVD 内のサンプル DVD 内には数種類のサンプルがあり、PowerBuilder のインストール時 にインストールできます。サンプルの一部では最新の PowerBuilder で 追加された機能を説明しています。各サンプルには Readme ファイル が含まれており、サンプルの概要とその使い方が記載されています。 DVD に付属しているサンプルは以下のとおりです。 Code Examples PowerBuilder Code Examples アプリケーションには、コーディング テク ニックの学習に活用できる多くのサンプルが含まれています。これら のサンプルは、PowerBuilder の新旧機能を駆使したさまざまなコー ティング テクニックの使い方を示す目的で特別に作成されています。 Web データウィンド ウ Web DataWindow® テクノロジを使用するアプリケーションを開発す るには、EAServer にプリインストールされている汎用サーバ コンポー ネントを使用できます。このコンポーネントは、Microsoft Component Object Model(COM)で使用する DLL として提供されます。また、サ ンプルの Web データウィンドウ PBL をモデルとして、独自の HTML ジェネレータ コンポーネントを作成することもできます。Web データ ウィンドウについての詳細は、『データウィンドウ プログラマーズ ガ イド』マニュアルを参照してください。 4 PowerBuilder 第1章 サンプル アプリケーションの使い方 サンプル アプリケーションのインストール DVD からサンプルをインストールするには、コンポーネントのリスト から「Code Examples」を選択します。Code Examples アプリケーショ ンをインストールするには、 「Example アプリケーション」を選択しま す。Web データウィンドウ PBL をインストールするには、「Web デー タウィンドウ」を選択します。 すべてのサンプルは、PowerBuilder 11.0 ディレクトリの Code Examples サブディレクトリにインストールされます。Code Examples アプリケー ションでは、EAS Demo DB というサンプルの SQL Anywhere® データ ベースを使用します。このデータベースは、Sybase\Shared\PowerBuilder ディレクトリにインストールされています。Code Examples ディレクト リまたは EASDEMO110.DB ファイルが見つからない場合、サンプル ア プリケーションおよびデータベースがインストールされていないこと があります。 サンプル アプリケーションを開く サンプル アプリケーションを開くには、アプリケーション用のワーク スペースを作成し、そのアプリケーションのターゲットをワークス ペースに追加する必要があります。 アプリケーションのターゲット ファイルがない場合は、ワークスペー スに追加することができます。新規作成 ダイアログボックスの[ター ゲット]タブから[既存のアプリケーション]を選択します。起動さ れたウィザードで PowerBuilder 11.0\Code Examples フォルダに移動し、 学習したいアプリケーションが含まれているフォルダと PBL を展開 して、アプリケーションを選択します。 次節では、Code Examples アプリケーションの開き方と実行方法を段階 を追って説明します。 アプリケーション テクニック 5 Code Examples アプリケーションの使い方 Code Examples アプリケーションの使い方 Code Examples アプリケーションは開発環境から実行します。 ❖ Code Example アプリケーションを実行するには 1 メニュー バーから[ファイル|新規作成]を選択し、[ワークス ペース]タブから[ワークスペース]を選択して、 [OK]をクリッ クします。 2 PowerBuilder 11.0\Code Examples\Example App フォルダに移動し、 ワークスペースの名前を入力して、[保存]をクリックします。 3 作成したワークスペースのポップアップ メニューから[ターゲッ トの追加]を選択し、PowerBuilder 11.0\Code Examples\Example App フォルダに移動し、ターゲット ファイル「PB Examples」を選択し て[開く]をクリックします。 ターゲットを展開すると、PBL にアプリケーションが含まれ、ア プリケーションがサポートする PBL がワークスペースに追加され ていることがわかります。 4 パワーバーの[実行]ボタンをクリックします。 サンプルの参照 Code Examples アプリケーションを開くと、左側のペインに、使用可能 なサンプル項目のツリー ビューが表示されます。このツリー ビュー は、さらに展開することもできます。中には、複数の項目に表示され るサンプルもあります。たとえばビジネス クラス サンプルは、継承と ユーザ オブジェクトの両方の項目にリスト表示されます。データスト アやデータウィンドウなど、特定の機能の使い方を知りたい場合は、 その項目を展開してサンプル名を調べてください。 6 PowerBuilder 第1章 サンプル アプリケーションの使い方 左側のペインでサンプルを選択すると、そのサンプルの説明と使い方 が右側に表示されます。 サンプルの検索 PowerBuilder の特定のオブジェクト クラスまたは機能の使い方を知り たい場合は、[サンプル プログラム]ペインの項目とその説明によっ てサンプルを検索できます。特定のイベント、関数、またはユーザ定 義オブジェクトを使用するサンプルを検索するには、 [検索]ペインを 使用します。 ❖ 関数、イベント、またはオブジェクトを検索するには 1 コード サンプルのメイン ウィンドウにある[検索]タブをクリッ クします。 2 [検索対象]グループボックスのラジオボタンを選択します。 3 アプリケーション テクニック ドロップダウン リストで目的の項目を選択し、 [検索開始]ボタン をクリックします。 7 Code Examples アプリケーションの使い方 検索対象の関数、イベント、またはオブジェクトを使用している サンプルの名前がすべて表示されます。 サンプルの実行と調査 学習したい処理を実行するサンプルが見つかったら、そのサンプルを 実行して動作内容を調べ、コードを参照(必要であればコピーも)で きます。 サンプルの実行 8 ハイライト表示されたサンプルを実行するには、サンプルをダブルク リックするかまたは[実行]をクリックします。サンプルのメイン ウィ ンドウにある[ヘルプ|現在のサンプルのヘルプ]ボタンをクリック すると、そのサンプルの使い方と動作内容に関するヘルプが表示され ます。 PowerBuilder 第1章 コードの調査 サンプル アプリケーションの使い方 サンプルに使用されているすべてのオブジェクトを参照するには、右 側のペインにある[関連オブジェクト]タブをクリックし、プラス記 号をクリックしてさらに詳しい項目を表示します。 スクリプトまたは関数のアイコンをダブルクリックして、コードを参 照します。 開発環境でのサンプル の利用 Code Examples アプリケーションを実行したり、サンプルのコードを参 照したりすることによって、多くの情報を得ることができますが、開 発環境でサンプル内のオブジェクトを開けば、さらに詳しい情報を得 ることができます。 たとえば、ペインタでオブジェクトを開く、ブラウザで継承階層を調 べる、デバッガでサンプルをワンステップずつ実行することなどがで きます。さらに、ライブラリ ペインタ内の自分のアプリケーションに オブジェクトをコピーしたり、スクリプト ビューにコード フラグメン トをコピーしたりすることもできます。 Code Examples アプリケーションのライブラリは、オブジェクト型を基準 にして編成されています。たとえば、pbexamd1.pbl および pbexamd2.pbl はデータウィンドウ オブジェクトを含みます。これによって、このマ ニュアルの後半でサンプルとして紹介されているオブジェクトを容易 に見つけることができます。ライブラリ ペインタのリストビューのサ ンプル ライブラリを展開すると、各オブジェクトの用途が表示されま す。 アプリケーション テクニック 9 Code Examples アプリケーションの使い方 10 PowerBuilder 第 2 部 言語テクニック 第 2 部では、PowerBuilder によるアプリケーション開発 でのオブジェクト指向プログラミングのテクニックと、 PowerScript® 言語の使用方法について説明します。 ClassDefinition オブジェクトについても説明します。 第 2 章 オブジェクト指向プログラミング この章について この章では、PowerBuilder におけるオブジェクト指向プログラミ ングのテクニックについて説明します。 内容 項目 用語の確認 PowerBuilder のテクニック その他のテクニック ページ 13 15 20 用語の確認 クラス、プロパティ、メ ソッド オブジェクト指向プログラミングでは、アプリケーション処理を 実行するための再利用可能なクラスを作成します。クラスには、ク ラスの動作を定義するプロパティとメソッドがあります。アプリ ケーション処理を実行するためには、クラスのインスタンスを作 成します。PowerBuilder では、以下のようなコンセプトを実装し ています。 • クラス PowerBuilder オブジェクト(ウィンドウ オブジェク ト、メニュー オブジェクト、ウィンドウ コントロール オブ ジェクト、ユーザ オブジェクトなど) • プロパティ オブジェクト変数とインスタンス変数 • メソッド イベントと関数 この章の後半で、これらの PowerBuilder の用語を使用します。 基本原則 オブジェクト指向のプログラミング ツールは、オブジェクト指向 の 3 つの基本原則である、継承、カプセル化、多相性(ポリモフィ ズム)をサポートします。 継承とは、オブジェクトを既存のオブジェクトから派生さ せ、既存オブジェクトのビジュアル コンポーネント、データ、コー ドにアクセスすることです。継承を使用すると、コーディング時 間を短縮し、コードの再利用性や一貫性を向上することができま す。子孫オブジェクトは、サブクラスとも呼ばれます。 継承 アプリケーション テクニック 13 用語の確認 カプセル化は、オブジェクトにデータとコードを格納し て、外部からのアクセスを必要であれば制限します。カプセル化は、 情報の隠ぺいとも呼ばれます。PowerBuilder は、アクセス レベルやス コープなどで、カプセル化を可能にしています。ただし、PowerBuilder 自身はカプセル化を要求したり、自動的に強化したりはしません。 カプセル化 多相性(ポリモフィズム) 同じ名前の関数は、その関数が定義されてい るオブジェクトによって、異なる動きをします。多相性は、アプリケー ション全体にわたって、またすべてのオブジェクト内において、一貫 性のあるインタフェースの提供を可能にします。 ビジュアル オブジェ クト 現在の多くのアプリケーションは、ウィンドウ、メニュー、ビジュア ル ユーザ オブジェクトなどのビジュアル オブジェクトのオブジェク ト指向の機能を頻繁に使用しています。これにより、アプリケーショ ンは一貫性があり、統一感のあるルック アンド フィールとなります。 非ビジュアル オブ ジェクト PowerBuilder のオブジェクト指向を十分に活用するためには、アプリ ケーションにクラス ユーザ オブジェクト(非ビジュアル ユーザ オブ ジェクト)を実装します。 PowerBuilder の組み込みシステム オブ ジェクト(Transaction オブジェクト、Message オブジェクト、Error オ ブジェクトなど)から、その定義を継承します。Code Examples のサン プル アプリケーションでの nvo_transaction のトランザクション オブ ジェクトは、サブクラス化された標準クラス ユーザ オブジェクトの例 です。カスタマイズされた標準クラス ユーザ オブジェクトを作成すれ ば、PowerBuilder の組み込みシステム オブジェクトを拡張できます。 標準クラス ユーザ オブジェクト カスタム クラス ユーザ オブジェクト PowerBuilder の NonVisualObject ク ラスから定義を継承したオブジェクトです。カスタム クラス ユーザ オ ブジェクトは、データとコードがカプセル化されています。このタイ プのクラス ユーザ オブジェクトは、何も定義されていない状態からオ ブジェクト クラスを定義することができます。Code Examples のサン プル アプリケーションでのユーザ オブジェクト u_business_object は、 カスタム クラス ユーザ オブジェクトの一例です。PowerBuilder のオブ ジェクト指向を最大限に活用するためには、カスタム クラス ユーザ オ ブジェクトを使用しなければなりません。典型的な用途としては、以 下のようなものがあります。 • 14 グローバル変数コンテナ カスタム クラス ユーザ オブジェクトに は、アプリケーションのすべてのオブジェクトで使用できる変数 と関数があります。アプリケーションで適切な場合に、直接また はオブジェクト関数によってアクセスできるように、これらの変 数をカプセル化します。 PowerBuilder 第2章 オブジェクト指向プログラミング • サービス オブジェクト カスタム クラス ユーザ オブジェクトには、 特定のコンテキスト(データウィンドウ オブジェクトなど)やグ ローバルなコンテキスト(文字列操作を行う関数のコレクション など)に役立つ関数や変数があります。 • ビジネス ルール カスタム クラス ユーザ オブジェクトには、ビジ ネス ルールを実装する関数や変数があります。すべてのビジネス ルールに対応した 1 つのオブジェクトを作成することができま す。または、ビジネス ルールの関連するグループに対応した複数 のオブジェクトを作成することもできます。 • 分散コンピューティング カスタム クラス ユーザ オブジェクトに は、サーバ上またはサーバのクラスタ上で実行する関数がありま す。 詳細については、第 6 部「分散処理アプリケーション テクニック」 を参照してください。 PowerBuilder のテクニック PowerBuilder は、ビジュアル オブジェクトとクラス オブジェクトの継 承、カプセル化、多相性を全面的にサポートしています。 再利用可能なオブジェクトの作成 ほとんどの場合、再利用可能なオブジェクトを開発する人と、アプリ ケーションで再利用可能なオブジェクトを使用する人は、同じ人では ありません。ここでは、再利用可能なオブジェクトの定義と作成の仕 方について説明します。使用法については説明しません。 継承の実装 PowerBuilder では、子孫オブジェクトを容易に作成することができま す。指定する先祖オブジェクトから継承するために、ウィンドウ ペイ ンタ、ユーザ オブジェクト ペインタ、メニュー ペインタを使用して、 PowerBuilder は継承を実装します。 ビジュアル オブジェクトの継承の例については、Code Examples サンプ ル アプリケーションでの w_employee ウィンドウと u_employee_object を参照してください。 アプリケーション テクニック 15 PowerBuilder のテクニック カスタム クラス ユーザ オブジェクト の継承を使用する 1 つの例としては、基本サービスを実行する先祖 サービス オブジェクトと、いくつかの子孫サービス オブジェクトを作 成するケースが挙げられます。子孫オブジェクトは、先祖のサービス にアクセスを持つとともに、子孫特有のサービスも実行します。 先祖サービス オブジェクトの例 図 2-1: 先祖サービス オブジェクト 先祖オブジェクトの仮想関数の例 カスタム クラス ユーザ オブジェクト の継承を使用する別の例としては、すべてのプラットフォーム用の関 数を持つクラスを先祖オブジェクトとして作成し、プラットフォーム 特定の関数を実行するクラスを子孫オブジェクトとして作成すること です。この場合、先祖オブジェクトをデータ型として子孫オブジェク トのインスタンスを作成できるように、先祖オブジェクトは仮想関数 (例では uf_change_dir)を持ちます。 図 2-2: 先祖オブジェクトの仮想関数 仮想関数の詳細については、20 ページの「その他のテクニック」を参 照してください。 カプセル化の実装 16 カプセル化は、プライベート(Private)またはプロテクト(Protected) としてインスタンス変数を宣言することによって、外部からのアクセ スを制限し、オブジェクトのデータを外部から隔離することができま す。次に、インスタンス変数への選択的なアクセスを提供するため、 オブジェクト関数を記述します。 PowerBuilder 第2章 オブジェクト指向プログラミング 処理とデータをカプセル化する 1 つのアプローチ は、以下のとおりです。 1 つのアプローチ • 外部へのアクセス程度により、パブリック(Public)、プライベー ト(Private)、またはプロテクト(Protected)としてインスタンス 変数を定義します。完全にカプセル化するには、プライベート (Private)またはプロテクト(Protected)としてインスタンス変数 を定義します。 • 処理の実行や、オブジェクトのデータへのアクセスを提供するに は、オブジェクト関数を定義します。 表 2-1: オブジェクト関数の定義 処理内容 処理の実行 インスタンス変数の 変更 インスタンス変数の 読み込み (オプション) Boolean 型のインスタ ンス変数の読み込み 関数 uf_do_operation uf_set_variablename uf_get_variablename uf_is_variablename 例 データベースから行を検索 する uf_do_retrieve 関数 String 型の変数 is_style の値 を変更する uf_set_style 関数 String 型の変数 is_style の値 を返す uf_get_style 関数 Boolean 型の変数 ib_protected の値を返す uf_is_protected 関数 処理とデータをカプセル化するための別のアプロー チは、実行するアクションを開発者が指定するための、単一のエント リ ポイントを用意することです。 別のアプローチ • 外部へのアクセス程度により、プライベート(Private)またはプロ テクト(Protected)としてインスタンス変数を定義します。 • 処理を実行するための、プライベート(Private)またはプロテクト (Protected)のオブジェクト関数を定義します。 • 実行する処理の種類を示す引数を持つ、1 つのパブリック関数を定 義します。 アプリケーション テクニック 17 PowerBuilder のテクニック 図 2-3: カプセル化のためのパブリック関数の定義 例については、Code Examples サンプル アプリケーションのユーザ オ ブジェクト u_sales_order を参照してください。 分散コンポーネント アプリケーション サーバ コンポーネントを生成すると、生成されたコ ンポーネントのインタフェースでパブリック関数を使用できるように なり、パブリック インスタンス変数を使用可能にするよう選択できま す。プライベートとプロテクトの関数と変数は、生成されたコンポー ネントのインタフェースで公開されません。 詳細については、第 6 部「分散処理アプリケーション テクニック」を 参照してください。 多相性の実装 多相性はプログラミング言語の機能です。この機能を使用すると、デー タ型やクラスに応じてオブジェクトを処理できます。多相性とは、同 じ名前の関数が、参照されているオブジェクトにより、異なる動作を することを意味します。多相性の正確な定義にはいろいろな議論があ りますが、以下のように考えるとわかりやすいでしょう。 独立したオブジェクト間の多相性(Operational polymorphism) 関連のな い別々のオブジェクトに、同じ名前の関数が定義されることがありま す。それぞれの関数は、そのオブジェクトの種類により適切な処理を 実行します。 18 PowerBuilder 第2章 オブジェクト指向プログラミング 図 2-4: 独立したオブジェクト間の多相性(Operational polymorphism) 例については、Code Example サンプル アプリケーションのユーザ オ ブジェクト u_external_functions とその子孫を参照してください。 継承したオブジェクト間の多相性(Inclusional polymorphism) 継承チェー ン内の個々のオブジェクトは、同じ名前の関数を定義できます。 継承したオブジェクト間の多相性によって、現行のオブジェクトが継 承階層のどこに適合するかに基づいて、どの継承チェーン内の関数を 実行するかが決定されます。子孫オブジェクトの関数は、先祖オブジェ クトの関数を上書きして実行します。 図 2-5: 継承したオブジェクト間の多相性(Inclusional polymorphism) 例については、Code Examples サンプル アプリケーションのユーザ オ ブジェクト u_employee_object を参照してください。 アプリケーション テクニック 19 その他のテクニック その他のテクニック PowerBuilder では、さまざまなオブジェクト指向のテクニックを実装 できます。この節では、PowerBuilder に関連するいくつかのテクニッ クについて説明します。 関数の多重定義の使い 方 関数の多重定義では、子孫関数(または同一オブジェクト内の同じ名 前の関数)に、引数の数や引数のデータ型が異なるものがあります。 PowerBuilder は、関数の呼び出しで指定された引数の数と引数のデー タ型を基に、どの子孫関数を実行するかを決定します。 図 2-6: 関数の多重定義 グローバル関数 グローバル関数は多重定義できません。 関数の動的呼び出しと 静的呼び出し 20 関数の動的呼び出し アプリケーションから、クロス プラットフォーム に依存する部分を取り除いた場合、特定のプラットフォームごとに、 別々の子孫オブジェクトを作成します。アプリケーションは、動的に プラットフォームに依存する子孫関数を呼び出します。 PowerBuilder 第2章 オブジェクト指向プログラミング 図 2-7: 関数の動的呼び出し 以下の例で示すように、実行時に適切なオブジェクトのインスタンス を作成します。 // 以下のスクリプトは、動的と静的な両方の // 関数の呼び出しに使用できます。 // 変数は、インスタンス変数とします。 u_platform iuo_platform Environment ienv_env ... GetEnvironment(ienv_env) choose case ienv_env.ostype case windows! iuo_platform = CREATE u_platform_win case windowsnt! iuo_platform = CREATE u_platform_win case else iuo_platform = CREATE u_platform_unix end choose 関数の動的呼び出しは柔軟性がありますが、パフォーマンスを悪くし ます。 パフォーマンスを良くするためには、関数の静的 呼び出しを用いることをお勧めします。ただし、CREATE 文で指定した オブジェクト データ型と異なるデータ型の参照変数を使用して、オブ ジェクトにアクセスすることもできます。 関数の静的呼び出し アプリケーション テクニック 21 その他のテクニック 図 2-8: 関数の静的呼び出し 関数の静的呼び出しを使用するときは、先祖関数のデフォルトの処理 内容を定義しなければなりません。先祖関数は、エラー値(たとえば、 -1)を返して、少なくとも 1 つの子孫関数に上書きされます。 図 2-9: 子孫関数で上書きされる先祖関数 先祖オブジェクトの関数にデフォルトの処理を定義すれば、関数の静 的呼び出しのパフォーマンスが得られるとともに、プラットフォーム に依存しないで済むようになります。 処理の代行 (delegation)の使い 方 処理の代行は、オブジェクトがほかのオブジェクトのために処理を代 行するときに、発生します。 従属関係(aggregate relationship) 従属関係(一体関係と呼ばれること もある)では、 (オーナー オブジェクトと呼ばれる)オブジェクトは、 そのオブジェクトの種類のためにデザインされたサービス オブジェ クトに関連付けられます。 22 PowerBuilder 第2章 オブジェクト指向プログラミング たとえば、データウィンドウ オブジェクトで行の選択を行うサービス オブジェクトを作成できます。この場合、データウィンドウ オブジェ クトの Clicked イベントに、行選択オブジェクトを呼び出すスクリプト を記述します。 ❖ オブジェクトを従属関係で使用するには 1 サービス オブジェクトを作成します(この例では u_sort_dw)。 2 オーナー(この例ではデータウィンドウ コントロール)にインス タンス変数(参照変数とも呼ばれる)を宣言します。 u_sort_dw iuo_sort 3 サービス オブジェクトのインスタンスを作成するため、オーナー オブジェクトにスクリプトを記述します。 iuo_sort = CREATE u_sort_dw 4 サービス オブジェクトのイベントや関数を呼び出すために、オー ナーのシステム イベントまたはユーザ イベントにスクリプトを 記述します。次の例は、データウィンドウ コントロールのユーザ イベント ue_sort に記述するスクリプトを示します。 IF IsValid(iuo_sort) THEN Return iuo_sort.uf_sort() ELSE Return -1 END IF 5 オーナー オブジェクトのユーザ イベントを呼び出すスクリプト を記述します。たとえば、データウィンドウ コントロールのユー ザ イベント ue_sort を呼び出す、コマンドボタンまたは[編集| ソート]などのメニュー項目を作成できます。 6 サービス オブジェクトのインスタンスを破棄するためのスクリプ トをオーナー オブジェクトの Destructor イベントに記述します。 IF IsValid(iuo_sort) THEN DESTROY iuo_sort END IF 独立関係(associative relationship) 独立関係では、オブジェクトは、 特定の種類の処理を実行するためのサービス オブジェクトを関連付 けます。 たとえば、どのアプリケーションのオブジェクトからでも使用できる ような、文字列操作を行うサービス オブジェクトを作成できます。 独立関係のオブジェクトを実装する操作手順は、従属関係と同じです。 アプリケーション テクニック 23 その他のテクニック ユーザ オブジェクトの AutoInstantiate プロパティを有効にした場合、 ユーザ オブジェクトのインスタンスのほかに、ユーザ オブジェクトが 宣言されているオブジェクト、イベント、または関数のインスタンス が生成されます。また、ユーザ オブジェクトのインスタンス変数を宣 言することもできます。これらの 2 つの機能を利用して、構造体とし て機能するユーザ オブジェクトを作成できます。このようなユーザ オ ブジェクトを構造体として使用する利点としては、以下のものがあり ます。 ユーザ オブジェクト の構造体としての使い 方 ❖ • 子孫オブジェクトを作成して拡張できる • 一度にすべての構造体にアクセスする関数を作成できる • 特定のインスタンス変数へのアクセスを制限するためにアクセス 指定子を使用できる 構造体として使用されるカスタムクラス ユーザ オブジェクトを作成するには 1 インスタンス変数だけを定義したユーザ オブジェクトを作成しま す。 2 [全般]プロパティ ページの[インスタンスの自動生成]をオンに して、ユーザ オブジェクトの AutoInstantiate プロパティを有効に します。 3 オブジェクト、関数、またはイベントで、ユーザ オブジェクトを 宣言します。 PowerBuilder は、オブジェクト、イベント、または関数が作成され たときに、ユーザ オブジェクトを生成します。また、オブジェク トが破棄されるか、イベントや関数が終了すると、ユーザ オブジェ クトを破棄します。 データストア オブ ジェクトのサブクラス 化 多くのアプリケーションでは、標準のデータウィンドウ ウィンドウ コ ントロールではなく、データウィンドウのビジュアル ユーザ オブジェ クトを使用します。これを使用すると、エラー チェックやアプリケー ション固有のデータウィンドウの動作を標準化できます。チュートリ アル ライブラリ TUTOR_PB.PBL にある データウィンドウ 型のビジュ アル ユーザ オブジェクト u_dwstandard は、そのようなオブジェクトの 一例です。 データストア は、非表示のデータウィンドウ コントロールとして機能 します。同じアプリケーションや一貫性を必要とする多くのものは、 データウィンドウ コントロールと同様に データストア にも適用され ます。データストア に対するエラー チェックやアプリケーション特有 の動作形態を実装するときは、データストア の標準クラス ユーザ オ ブジェクトを作成することを考慮します。 24 PowerBuilder 第 3 章 PowerScript についての特別な トピック この章について この章では、PowerScript 言語要素のアプリケーションでの使い方 について説明します。 内容 項目 ドット表記 定数の宣言 インスタンス変数のアクセスの制御 名前の重複の解決 先祖スクリプトからの戻り値 関数とイベントの引数の型 先祖変数と子孫変数 データウィンドウと外部オブジェクトにおける式の最適化 PowerBuilder での例外処理 ガベージ コレクションとメモリ管理 効率的なコンパイルとパフォーマンス テキスト ファイルとバイナリ ファイルの読み書き ページ 25 30 30 31 33 35 36 38 39 49 53 53 ドット表記 ドット表記(.)を使用すると、参照先の項目(インスタンス変数、 プロパティ、イベント、関数)を、その項目を所有するオブジェ クトで修飾できます。 ドット表記はオブジェクトに使用します。グローバル変数や関数 はオブジェクトとは独立して存在するため、ドット表記を使用し ません。共有変数にもドット表記を使用することはありません。共 有変数は、オブジェクト インスタンスではなくオブジェクト クラ スに属するからです。 アプリケーション テクニック 25 ドット表記 参照の修飾 ドット表記では、使用する項目をオブジェクト変数名で修飾します。 objectvariable.item オブジェクト変数名は、プロパティまたはそのほかの項目の所有者を 識別する修飾子です。 親修飾子を追加する オブジェクトを完全に識別するには、ドット修飾 子を追加して、オブジェクトの親、そのまた親という具合に指定して いきます。 parent.objectvariable.item 親 オブジェクトは子オブジェクトを包含します。これは祖先と子孫の 関係ではありません。たとえば、ウィンドウはコントロールの親です。 タブ コントロールは、その中にあるタブ ページの親です。メニュー オ ブジェクトは、そのメニューの項目となっているメニュー オブジェク トの親です。 複数の親レベル 親修飾子はアプリケーション レベルまで指定できま す。ただし、通常はウィンドウ レベルまで指定すれば十分です。 たとえば、あるタブ ページにあるデータウィンドウ コントロールの Retrieve 関数を呼び出すには、次のように関数名を修飾します。 w_choice.tab_alpha.tabpage_a.dw_names.Retrieve() メニュー オブジェクトには複数の修飾子が必要になることがよくあ り ま す。た と え ば、w_main ウ ィ ン ド ウ に メ ニ ュ ー オ ブ ジ ェ ク ト m_mymenu が含まれており、その中の[ファイル]メニューに[開く] という項目があるとします。この[開く]項目の Selected イベントを 起動するには、次のように指定します。 w_main.m_mymenu.m_file.m_open.EVENT Selected() このように、名前の修飾は、特にタブ コントロールに含まれるメ ニューやタブ ページでは、複雑になります。 修飾子の数 オブジェクト、関数、イベント、またはプロパティを識別 するのに必要なだけの修飾子を指定する必要があります。 親オブジェクトは、自分に含まれているオブジェクトを認識していま す。ウィンドウのスクリプト内では、そのウィンドウに含まれるコン トロールの名前を修飾する必要はありません。また、各コントロール のスクリプトでは、そのウィンドウ内のほかのコントロールを修飾子 なしで参照できます。 26 PowerBuilder 第3章 PowerScript についての特別なトピック たとえば、w_main ウィンドウに、データウィンドウ コントロール dw_data とコマンドボタン コントロール cb_close が含まれている場合、 このコマンドボタン コントロールのスクリプトは、データウィンドウ コントロールを次のように修飾子なしで参照できます。 dw_data.AcceptText() dw_data.Update() このデータウィンドウ コントロールを別のウィンドウまたはユーザ オブジェクト 内のスクリプトで参照する場合は、次のようにウィンド ウ名で修飾する必要があります。 w_main.dw_data.AcceptText() オブジェクトの参照 オブジェクト自身のスクリプト内でそのオブジェクトの要素を修飾す るには、次の 3 つの方法があります。 • 修飾しない li_index = SelectItem(5) 未修飾の名前は明確でないため、同名のローカルまたはグローバ ルの変数や関数が存在すると名前を一意に特定できないことがあ ります。 • オブジェクト名で修飾する li_index = lb_choices.SelectItem(5) オブジェクト自身のスクリプト内でそのオブジェクトの名前を指 定するのは不必要な指定です。 • オブジェクトへの汎用の参照で修飾する li_index = This.SelectItem(5) 代名詞 This は、その項目を所有するオブジェクトに属することを 示します。 This 代名詞 オブジェクトのスクリプトでは、This を所有オブジェクト への汎用の参照として使用できます。 This.property This.function プロパティや関数はスクリプト内で何の修飾子も付けずに使用できま すが、そうすると読む人によっては、そのプロパティまたは関数が特 定のオブジェクトに属していることに気づかないことがあります。This を使用したスクリプトは、オブジェクトの名前を変更してもそのまま 使えます。したがって、スクリプトを少ない編集作業で再利用できま す。 アプリケーション テクニック 27 ドット表記 This を単独で使用すると、現在のオブジェクトへの参照になります。た とえば、別のユーザ オブジェクト内の関数にデータウィンドウ コント ロールを渡したい場合は、次のように指定します。 uo_data.uf_retrieve(This) データウィンドウ コントロールのスクリプト内でデータウィンドウ 型のインスタンス変数を設定して、一番最近使用されたデータウィン ドウ コントロールがほかの関数に分かるようにするには、次のように 指定します。 idw_currentdw = This Parent 代名詞 Parent 代名詞は、オブジェクトの親を参照します。Parent を使用したスクリプトは、親オブジェクトの名前を変更してもそのま ま使えます。また、ほかのコンテキストでも再利用できます。 たとえば、データウィンドウ コントロールのスクリプトで、そのウィ ンドウの Resize 関数を呼び出すとします。この場合、データウィンド ウ コントロール自体にも Resize 関数が定義されているため、次のよう に修飾する必要があります。 // ウィンドウ関数を呼び出す 2 つの方法 w_main.Resize(400, 400) Parent.Resize(400, 400) // コントロールの関数を呼び出す 3 つの方法 Resize(400, 400) dw_data.Resize(400, 400) This.Resize(400, 400) GetParent 関数 Parent 代名詞が使えるのはドット表記内だけです。親 オブジェクトへの参照を取得したい場合は、GetParent 関数を使用しま す。これは、スクリプトの所有オブジェクト以外のオブジェクトの親 を参照したり、次のように親オブジェクトへの参照を変数に保存した りする場合に使用します。 window w_save w_save = dw_data.GetParent() たとえば、別のコマンドボタン コントロールの Clicked イベント スク リプトで、そのコマンドボタン コントロールの親ウィンドウへの参照 を、あるユーザ オブジェクトに定義されている関数に渡したいとしま す。この場合は、次のように、関数呼び出しの中で GetParent を使用し ます。 uo_winmgmt.uf_resize(This.GetParent(), 400, 600) ParentWindow プロパティと ParentWindow 関数 オ ブ ジ ェ ク ト の 親 を 取得する関数やプロパティはほかにもあります。 28 PowerBuilder 第3章 PowerScript についての特別なトピック • ParentWindow プロパティ – メニュー スクリプト内で、 そのメニュー の親ウィンドウを参照するために使用します。 • ParentWindow 関数 – 任意のスクリプト内で、特定のウィンドウの 親ウィンドウへの参照を取得するために使用します。 これらの代名詞および関数の詳細については、『PowerScript リファレ ンス』マニュアルを参照してください。 コンテナ オブジェク ト内のオブジェクト ドット表記を使用すると、オブジェクトの中のオブジェクトを参照す ることもできます。こうしたコンテナ内のオブジェクトを参照するに は、ドット表記内で Object プロパティを使用します。コンテナ内オブ ジェクトの構造によってアクセス可能なレベル数が決まります。 control.Object.objectname.property control.Object.objectname.Object.qualifier.qualifier.property Object プロパティによってアクセス可能なオブジェクトは次のとおり です。 • データウィンドウ コントロール内のデータウィンドウ オブジェ クト • OLE コントロール内の外部 OLE オブジェクト 次の式は、データウィンドウ コントロール内のデータウィンドウ オブ ジェクトのプロパティを参照しています。 dw_data.Object.emp_lname.Border dw_data.Object.nestedrpt[1].Object.salary.Border コンパイラによるチェックは行わない コンテナ内オブジェクトを含む ドット表記が正しいかどうかは、コンパイラには判断できません。た とえば、データウィンドウ オブジェクトは特定のコントロールにバイ ンドされておらず、いつでも変更できます。このため、Object プロパ ティの後の名前とプロパティが有効かどうかは、実行時に初めて チェックされます。参照名が間違っていると実行時エラーになります。 詳細情報 実行時エラー チェックの詳細については、38 ページの「デー タウィンドウと外部オブジェクトにおける式の最適化」を参照してく ださい。 データウィンドウ オブジェクトのプロパティとデータのドット表記 およびエラー処理についての詳細は、 『データウィンドウ リファレン ス』マニュアルを参照してください。 OLE オブジェクトおよび OLE オートメーションのドット表記の詳細 については、第 19 章「アプリケーションにおける OLE の使い方」を 参照してください。 アプリケーション テクニック 29 定数の宣言 定数の宣言 定数を宣言するには、標準の変数宣言に CONSTANT キーワードを追加 します。 CONSTANT { access } datatype constname = value 定数として宣言できるのは、宣言内に代入文を使用できるデータ型だ けです。このため、Blob 型は定数として宣言できません。 PowerScript の識別子は大文字と小文字を区別しませんが、ここでは命 名規約に従って定数名に大文字を使用します。 CONSTANT integer GI_CENTURY_YEARS = 100 CONSTANT string IS_ASCENDING = "a" 定数の利点 宣言文以外の箇所で定数に値を代入する文を書くと、コンパイル エ ラーになります。定数を宣言すると、宣言文で指定したとおりに定数 が使われるようになります。 また、定数を宣言することで効率も向上します。定数値はコンパイル 時に確定するため、マシン コードでは、その定数値を保持している変 数を参照するのではなく、定数値が直接使用されます。 インスタンス変数のアクセスの制御 インスタンス変数には、アクセス制御のための設定を行えます。この 設定により、ほかのオブジェクトのスクリプトがその変数にアクセス する方法を制御できます。 インスタンス変数のアクセス制御には次の 3 種類があります。 • パブリック ほかのすべてのオブジェクトからアクセス可能です。 • プロテクト そのオブジェクトおよびその子孫オブジェクトのス クリプト内でのみアクセス可能です。 • プライベート そのオブジェクトのスクリプト内だけでアクセス可 能です。 例 public integer ii_currentvalue CONSTANT public integer WARPFACTOR = 1.2 protected string is_starship // 内部計算に使用するプライベート値 30 PowerBuilder 第3章 PowerScript についての特別なトピック private integer ii_maxrpm private integer ii_minrpm パブリック変数とプロテクト変数へのアクセスは、修飾子 PRIVATEREAD、 PRIVATEWRITE、PROTECTEDREAD、または PROTECTEDWRITE を使っ てさらに制限できます。 public privatewrite ii_averagerpm カプセル化のためのプ ライベート変数 アクセス制御は、ほかのスクリプトによる変数の変更を禁止するとき によく使用します。PRIVATE または PUBLIC PRIVATEWRITE アクセスを 設定すると、ほかのスクリプトがその変数を直接変更できなくなりま す。これらの変数には、検証を行ってから変数の変更を許可するパブ リック関数を用意します。 プライベート変数を使用すると、オブジェクトの機能をカプセル化で きます。カプセル化とは、オブジェクトのデータとコードをそのオブ ジェクトの内部に隠ぺいし、外部に提供するインタフェースをオブ ジェクトが決定する手法のことです。 たとえば、カスタム クラス ユーザ オブジェクトから EAServer、 COM+、 またはアプリケーション サーバなどのコンポーネントを生成する場 合、そのコンポーネントのインタフェースによってインスタンス変数 を公開することはできますが、プライベート型またはプロテクト型の インスタンス変数が公開されることは決してありません。 詳細情報 アクセス制御についての詳細は、『PowerScript リファレンス』マニュ アルの「宣言」の章を参照してください。 カプセル化についての詳細は、第 2 章「オブジェクト指向プログラミ ング」を参照してください。 名前の重複の解決 名前の重複が発生するケースとして次の 2 つがあります。 • 異なるスコープ内に定義された変数が同じ名前を持つ場合。たと えば、グローバル変数は、ローカル変数またはインスタンス変数 と同じ名前を持つことがあります。コンパイラはこうした重複す る名前があると警告を出しますが、変数名を変更する必要はあり ません。 • 子孫オブジェクトが先祖オブジェクトから関数やイベントを同じ 名前で継承している場合 アプリケーション テクニック 31 名前の重複の解決 隠された変数または先祖のイベントや関数を参照する必要がある場合 は、ドット表記修飾子またはスコープ演算子を使用します。 隠されたインスタンス 変数 インスタンス変数が、ローカル変数、共有変数、またはグローバル変 数と同じ名前を持つ場合は、そのインスタンス変数をオブジェクト名 で修飾します。 objectname.instancevariable あるウィンドウに birthdate という名前のローカル変数とインスタンス 変数が存在する場合は、インスタンス変数を次のように修飾します。 w_main.birthdate ウィンドウ スクリプトにローカル変数 x が定義されていると、同じ ウィンドウの X プロパティと名前が重複します。その場合は、X プロ パティに修飾子を付けます。次の文では、両者を比較しています。 IF x > w_main.X THEN 隠されたグローバル変 数 グローバル変数がローカル変数または共有変数と同じ名前を持つ場合 は、そのグローバル変数の前にスコープ演算子(::)を付けます。 ::globalvariable 次の式は、total という同じ名前を持つローカル変数とグローバル変数 を比較しています。 IF total < ::total THEN ... 接頭辞を使用して名前の重複を避ける 接頭辞を付けて変数のスコープを識別するという命名規約に従ってい る場合は、スコープの異なる変数は必ず名前も異なるため、変数名が 重複することはありません。 名前の重複を解決する方法を決定する検索順序についての詳細につい ては、『PowerScript リファレンス』マニュアルの「宣言」および「関 数とイベントの呼び出し」の章を参照してください。 上書きされた関数とイ ベント 継承した関数のスクリプトを変更する場合は、先祖オブジェクトの関 数を上書きします。イベントの場合は、ペインタ内で先祖オブジェク トのイベント スクリプトを上書きまたは拡張します。 スコープ演算子を使用すれば、上書きした関数またはイベントの先祖 オブジェクトを呼び出すことができます。それには次のように、スコー プ演算子を表す二重コロンの前に先祖クラス名(変数名ではない)を 指定します。 result = w_ancestor::FUNCTION of_func(arg1, arg2) 32 PowerBuilder 第3章 PowerScript についての特別なトピック 先祖クラスの名前を指定するかわりに、Super 代名詞を使用することも できます。Super は、すぐ上の先祖オブジェクトを参照します。 result = Super::EVENT ue_process() 優れたオブジェクト指向設計では、ほかのオブジェクトの先祖スクリ プトを呼び出すようなことはしません。こうした呼び出し方をするの は、Super を使って現在のオブジェクトのすぐ上の先祖を呼び出す場合 だけにしてください。 先祖スクリプトの戻り値を取得する方法についての詳細は、次の「先 祖スクリプトからの戻り値」を参照してください。 関数の多重定義 同じオブジェクトに同じ名前の関数を複数定義すると、関数名が多重 定義されたものとみなされます。PowerBuilder は、関数定義のシグネ チャ(形式)と関数呼び出しのシグネチャを比較することによって、 どの関数を呼び出すかを決定します。シグネチャには、関数名、引数 リスト、戻り値が含まれます。 多重定義 イベントおよびグローバル関数は多重定義できません。 先祖スクリプトからの戻り値 子孫オブジェクトのイベント スクリプト内で、先祖イベント スクリプ ト の 戻 り 値 に 依 存 し た 処 理 を 実 行 す る 場 合 は、ロ ー カ ル 変 数 AncestorReturnValue を使用します。このローカル変数は自動的に宣言 され、先祖イベントの戻り値が代入されます。 コンパイラは、スクリプト内で先祖イベントを呼び出す CALL 文に出 会うと、AncestorReturnValue 変数を宣言し、それに先祖イベントの戻 り値を代入するコードを暗黙に生成します。 AncestorReturnValue 変数のデータ型は常に、その先祖イベントの戻り 値に定義されているデータ型と同じです。先祖イベントの呼び出し時 には、子孫オブジェクトのイベントに渡された引数がそのまま渡され ます。 イベント スクリプト の拡張 AncestorReturnValue 変数は拡張イベント スクリプト内では常に使用で きます。イベント スクリプトを拡張すると、次の構文が生成され、ス クリプトの先頭に挿入されます。 CALL SUPER::event_name アプリケーション テクニック 33 先祖スクリプトからの戻り値 この文が表示されるのは、オブジェクトの構文を公開している場合だ けです。 イベント スクリプト の上書き イベント スクリプトを上書きした場合に AncestorReturnValue 変数が使 用可能になるのは、次のように CALL 構文を明示的に使用して先祖イ ベントを呼び出したときだけです。 CALL SUPER::event_name または CALL ancestor_name::event_name コンパイラは、SUPER キーワードと先祖名を区別しません。SUPER キーワードは、スクリプトがコンパイルされる前に先祖名で置き換え られます。 AncestorReturnValue 変数が宣言され戻り値が代入されるのは、CALL イ ベント構文を使用した場合だけです。次のように新規イベント構文を 使用した場合、AncestorReturnValue 変数は宣言されません。 ancestor_name::EVENT event_name ( ) 例 拡張イベント スクリプトには次のようなコードを書くことができま す。 IF AncestorReturnValue = 1 THEN // 処理を実行する ELSE // 別の処理を実行する END IF 先祖イベント スクリプトを上書きするスクリプトにも上記の拡張イベ ント スクリプトと同じコードを書くことができますが、 AncestorReturnValue 変数を使用する前に CALL 文を挿入しなければなり ません。 // 前処理を実行するコード CALL SUPER::ue_myevent IF AncestorReturnValue = 1 THEN … 34 PowerBuilder 第3章 PowerScript についての特別なトピック 関数とイベントの引数の型 関数またはユーザ イベントを定義するときは、引数、引数のデータ型、 および引数の渡し方を指定します。 引数の渡し方には、次の 3 つがあります。 • デフォルトの引数の渡し方です。 値渡し 引数値のコピーを渡します。呼び出し先で引数値を変更するとこ のコピーが変更されます。呼び出し元の引数値は変更されません。 • 参照渡し 引数が格納された変数へのポインタを渡します。 参照渡しの引数は呼び出し元の変数へのポインタなので、呼び出 し先の関数スクリプトからその値を変更できます。参照渡しの引 数には、値を変更できるように変数を指定する必要があります。リ テラルや定数を指定することはできません。 • 読み込み専用渡し 引数を値渡しで渡しますが、データのコピーを 作成しません。 読み込み専用渡しでは値渡しのようにデータのコピーを作成しな いため、データ型によってはパフォーマンスが向上します。String、 Blob、Date、Time、DateTime の各データ型は、読み込み専用渡しに するとパフォーマンスが向上します。 上記以外のデータ型の場合でも、読み込み専用渡しにすることで、 その引数の用途(読み込み専用であること)をほかの開発者に伝 えることができます。 関数を上書きするとき の引数型の照合 先祖関数を上書きする関数を子孫オブジェクトに定義する場合は、関 数のシグネチャ、すなわち関数名、戻り値、引数のデータ型、引数の 渡し方がすべて一致していなければなりません。 たとえば、次の関数宣言では、3 つの Long 型引数のうち、2 つを値渡 しで、1 つを参照渡しで渡しています。 uf_calc(long a_1, long a_2, ref long a_3) & returns integer 先祖関数を上書きした子孫関数のシグネチャが先祖関数のものと一致 しない場合は、関数が呼び出されたときに PowerBuilder はもっとも類 似している関数を捜し出して呼び出します。このため、予期せぬ結果 になることがあります。 アプリケーション テクニック 35 先祖変数と子孫変数 先祖変数と子孫変数 PowerBuilder のすべてのオブジェクトは、PowerBuilder システム オブ ジェクト(ブラウザの[システム]ページに一覧表示されるオブジェ クト)の子孫です。 したがって、オブジェクト インスタンスを宣言するときはいつも、子 孫オブジェクトを宣言していることになります。どの程度具体的な宣 言にするかは、開発者が決定します。 できるだけ具体的な宣 言にする場合 たとえば、uo_empdata という名前のユーザ オブジェクト クラスを定義 する場合に、uo_empdata という型の変数を宣言して、uo_empdata ユー ザ オブジェクトへの参照を格納することができます。 uo_empdata uo_emp1 uo_emp1 = CREATE uo_empdata uo_emp1 の型は uo_empdata なので、uo_empdata の定義に含まれる変数 や関数を参照することができます。 アプリケーションに柔 軟性が要求される場合 作成するユーザ オブジェクトがユーザの選択によって決まるとしま す。UserObject という型のユーザ オブジェクト変数を宣言するか、そ のユーザ オブジェクトの先祖クラスを宣言します。そして、インスタン ス化するオブジェクト クラスを文字列変数に格納し、 それを CREATE の 引数に指定してクラスをインスタンス化します。 uo_empdata uo_emp1 string ls_objname ls_objname = ...// 開くユーザ オブジェクトを確定する uo_emp1 = CREATE USING ls_objname この方法は汎用的ですが、オブジェクトの変数や関数へのアクセスが 制限されます。コンパイラは先祖クラス uo_empdata の(システム クラ ス UserObject を宣言した場合はその)プロパティや関数しか知りませ ん。実際に作成されるオブジェクトについては知らないため、その未知 のオブジェクトに定義されたプロパティへの参照を許可できません。 抽象先祖オブジェクト インスタンス化する子孫オブジェクトのプロパ ティや関数を特定するためには、子孫オブジェクトで実装するプロパ ティや関数を含む先祖オブジェクトを定義します。この先祖オブジェ クトの関数に戻り値以外のコードは不要です。この関数を定義する目 的は、コンパイラが関数名を認識できるようにすることだからです。 この先祖クラスの変数を宣言すると、関数を参照できるようになりま す。実行時に、特定の子孫で変数をインスタンス化します。この子孫 が必要な関数を実装しています。 uo_empdata uo_emp1 string ls_objname 36 PowerBuilder 第3章 PowerScript についての特別なトピック // 開く uo_empdata の子孫を確定する ls_objname = ... uo_emp1 = CREATE USING ls_objname // 先祖クラスで関数を宣言する result = uo_emp1.uf_special() この手法の詳細については、20 ページの「関数の動的呼び出しと静的 呼び出し」に記載されています。 宣言したクラスに定義されていない関数を扱うも う 1 つの方法として、動的関数呼び出しがあります。 動的関数呼び出し 関数呼び出しに DYNAMIC キーワードを指定すると、コンパイラはその 関数が有効かどうかをチェックしなくなります。このチェックは、実 行時に、変数が適切なオブジェクトでインスタンス化されたとき行わ れます。 // 子孫クラス内で宣言されていない関数 result = uo_emp1.DYNAMIC uf_special() パフォーマンスとエラー 動的関数呼び出し機能は、アプリケーションの設計によって要求され るとき以外は使用しないでください。実行時評価では、通常はコンパ イラが行う作業を実行時に行う必要があります。このため、動的呼び 出しを頻繁に、または大きなループ内で使用すると、アプリケーショ ンのパフォーマンスが低下します。また、コンパイラによるチェック が省略されるため、本来ならコンパイラが検出していたエラーが実行 時まで検出されません。 ウィンドウとビジュア ル ユーザ オブジェク トの動的オブジェクト 選択 ウィンドウとビジュアル ユーザ オブジェクトを開くには、CREATE 文 ではなく関数呼び出しを使用します。Open および OpenUserObject 関数 を使用すると、開くウィンドウまたはオブジェクトのクラスを指定で きるため、宣言のオブジェクト型とは異なる型の子孫を開けます。 次の例では、s_u_name 文字列に指定された型を持つユーザ オブジェク トを表示し、そのユーザ オブジェクトへの参照を u_to_open 変数に格 納しています。u_to_open 変数は DragObject 型、つまりすべてのユーザ オブジェクトの先祖です。このインスタンス変数は、すべてのユーザ オブジェクトへの参照を保持できます。 DragObject u_to_open string s_u_name s_u_name = sle_user.Text w_info.OpenUserObject(u_to_open, s_u_name, 100, 200) アプリケーション テクニック 37 データウィンドウと外部オブジェクトにおける式の最適化 ウィンドウについても同様のコードを書くと次のようになります。実 際に開かれるウィンドウの型は、w_data_entry クラス、またはその子孫 クラスになります。 w_data_entry w_data string s_window_name s_window_name = sle_win.Text Open(w_data, s_window_name) データウィンドウと外部オブジェクトにおける式の最適化 コンテナ オブジェク トに対するコンパイラ の妥当性チェックは行 われない ドット表記を使用して、データウィンドウ コントロール内のデータ ウィンドウ オブジェクトまたはデータストアを参照すると、コンパイ ラは次の式の妥当性チェックを行いません。 dw_data.Object.column.property Object プロパティ以降の部分はコンパイラによるチェックを受けず、 実行時にチェックされます。 これは、外部 OLE オブジェクトについても同じです。つまり、外部 OLE オブジェクトのチェックも実行時に行われます。 ole_1.Object.qualifier.qualifier.property.Value 部分参照の確定 多くの式を使用すると、実行時の構文チェックに時間がかかるためパ フォーマンスが低下します。同じデータウィンドウ コンポーネント オ ブジェクトまたは外部オブジェクトを繰り返し参照する場合に効率性 を高めるには、適切な型の変数を定義して、その変数に参照の一部を 割り当てます。これにより、参照の大部分を 1 回だけ評価し、以降は その評価結果を再利用できます。 データウィンドウ コンポーネント オブジェクトのデータ型は DWObject です。 DWObject dwo_column dwo_column = dw_data.Object.column dwo_column.SlideLeft = ... dwo_column.SlideUp = ... 部分的に解決されたオートメーション式のデータ型は OLEObject です。 OLEObject ole_wordbasic ole_wordbasic = ole_1.Object.application.wordbasic ole_wordbasic.propertyname1 = value ole_wordbasic.propertyname2 = value 38 PowerBuilder 第3章 PowerScript についての特別なトピック エラー処理 Error イベントと(オートメーション用の)ExternalException イベント は、データウィンドウおよび OLE 式を評価するときに発生します。こ れらのイベントを処理するスクリプトを書けば、SystemError イベント が起動される前にエラーを捕捉することができます。これらのイベン トを使用すると、エラーを無視したり、適切な値で置換したりできま す。ただし、それによって別のエラーを引き起こす条件を設定してし まわないように注意する必要があります。次の「PowerBuilder での例 外処理」で説明するように、try-catch ブロックを使用して例外を処理 することもできます。 詳細情報 データウィンドウのデータ式とプロパティ式、および DWObject 変数に ついての詳細は、『データウィンドウ リファレンス』マニュアルを参 照してください。オートメーションの OLEObject 変数の使い方につい ての詳細は、第 19 章「アプリケーションにおける OLE の使い方」を 参照してください。 PowerBuilder での例外処理 PowerBuilder アプリケーションで実行時エラーが発生した場合に、そ のエラーをトラップしないと、アプリケーション内でのエラー発生の 場所に関係なく、単一のアプリケーション イベント(SystemError)が 発生しエラーが処理されます。システム エラー イベントで処理できる エラーもありますが、発生箇所に近い位置でエラーを捕捉したほうが、 エラー状態から回復できる可能性が高くなります。 例外処理用のクラス構文を使用すれば、PowerBuilder アプリケーショ ンの状況依存エラーを処理できます。つまり、エラー処理用のコード をアプリケーション内に埋め込むことによって、エラー発生箇所に近 い位置でエラーを処理できます。例外処理コードをうまく設計すれば、 ユーザはエラー状態から回復できる可能性が高くなり、アプリケー ションによる作業を中断せずに済みます。 例外処理を行うことにより、例外状態から回復し処理を続行できるア プリケーションを設計できます。アプリケーションが捕捉しない例外 はすべてランタイム システムによって処理されます。その場合は、ア プリケーションが異常終了することがあります。 PowerBuilder クライアントは、アプリケーション サーバ コンポーネン トで送出された例外を捕捉し、例外状態から回復することができます。 PowerBuilder で開発したコンポーネントは、独自の例外の種類を定義 し送出できます。これにより、Java などほかのサーバ コンポーネント との一貫性を高めることができます。 アプリケーション テクニック 39 PowerBuilder での例外処理 例外処理は、Java や C++ などのオブジェクト指向言語でも使われます。 PowerBuilder の例外処理の実装は、Java の例外処理の実装に似ていま す。PowerBuilder の例外処 理では、TRY、CATCH、FINALLY、THROW、 THROWS などの予約語を使用します。Throwable オブジェクトから派 生した PowerBuilder オブジェクトもいくつかあります。 例外処理の基本 例外とは、何らかの例外的な(予想外の)状態やエラーのイベントで 送出されるオブジェクトであり、発生した条件やエラーを記述するも のです。Null オブジェクト参照やゼロによる除算などの標準エラーは 通常、ランタイム システムによって送出されます。この種のエラーは アプリケーション内のどこでも発生する可能性があり、任意の実行ス クリプトにはこれらのエラーから回復するための catch 句を指定でき ます。 ユーザ定義の例外 即座に実行時エラーとはならない例外条件もあります。これらの例外 は通常、関数またはユーザ イベント スクリプトの実行中に発生しま す。これらの例外を伝えるには、PowerScript の Exception クラスから 継承したユーザ オブジェクトを作成します。ユーザ定義の例外は、関 数、またはメソッド プロトタイプ内のユーザ イベントに関連付けるこ とができます。 たとえば、特定のファイルが見つからないことを知らせるためにユー ザ定義の例外を作成させるとします。この例外は、そのファイルを開 く関数のプロトタイプ内で宣言するとよいでしょう。この例外を捕捉 するには、ユーザ定義の例外オブジェクトをインスタンス化して、そ のメソッド スクリプト内で例外インスタンスを送出する必要があり ます。 例外処理用のオブジェクト PowerBuilder には、例外処理用のシステム オブジェクトがいくつかあ ります。 Throwable オブジェク ト型 40 Throwable オブジェクト型は、すべてのユーザ定義の例外およびシス テム エラー型の基本となるデータ型です。2 つのシステム オブジェク ト型 RuntimeError と Exception は、Throwable から派生したデータ型で す。 PowerBuilder 第3章 RuntimeError とその 子孫 PowerScript についての特別なトピック PowerBuilder の実行時エラーは、RuntimeError オブジェクト型で表さ れます。より堅牢なエラー処理機能を実現するために、RuntimeError 型には独自のシステム定義の子孫が定義されていますが、PowerBuilder の実行時エラーを処理するために必要な情報はすべて RuntimeError 型 に含まれています。 RuntimeError の子孫型の 1 つに NullObjectError 型があります。 NullObjectError 型の例外は、Null オブジェクト参照を検出するたびに システムによって送出されます。これにより、Null オブジェクト参照 エラーを、発生する可能性のあるほかの実行時エラーと区別せずに明 示的に処理できます。 RuntimeError から派生したエラー型は通常、実行時エラーを知らせる ためにシステムによって使用されます。RuntimeError は try-catch ブ ロックで捕捉できますが、このようなエラー条件が発生する場所を宣 言する必要はありません。これは PowerBuilder がかわりに行ってくれ ます。というのは、システム エラーはアプリケーション実行時にいつ でもどこでも発生する可能性があるからです。また、RuntimeError 型 のエラーを捕捉することは必須ではありません。 Exception オブジェク ト型 Exception システム オブジェクトも、Throwable から派生したオブジェ クトで、通常、ユーザ定義の例外型の先祖オブジェクトとして使用さ れます。例外のクラスは、すべての検査例外の基本となるクラスです。 検査例外 はユーザ定義の例外で、送出されたら必ず try-catch ブロック 内で捕捉しなければなりません。また、try-catch ブロックの外で送出 される場合は、メソッドのプロトタイプ内で宣言する必要があります。 PowerScript コンパイラは検査例外が送出されるローカルの構文を チェックして、検査例外が必ず宣言または捕捉されるようにします。 RuntimeError の子孫は、それがユーザ定義であっても、またランタイ ム システムによってではなくスクリプト内で送出されるものであっ ても、コンパイラによってチェックされることはありません。 例外の処理 例外は、ランタイム システムによって送出される場合でも、アプリ ケーション スクリプト内の THROW 文によって送出される場合でも、 例外を捕捉することによって処理します。例外を捕捉するには、例外 を送出させる一連のアプリケーション ロジックを、その例外の処理方 法を示すコードで囲みます。 アプリケーション テクニック 41 PowerBuilder での例外処理 TRY-CATCH-FINALLY ブロック PowerScript で例外を処理するには、アプリケーション ロジックの一部 を try-catch ブロックで囲む必要があります。try-catch ブロックは、TRY 句で始まり、END TRY 文で終わります。また、ブロック内には、CATCH 句または FINALLY 句を含める必要があります。FINALLY 句は通常、エ ラー条件の後処理を記述するときに指定します。TRY 句と FINALLY 句 の間には、CATCH 句をいくつでも追加できます。 CATCH 句は必須ではありませんが、 指定する場合は各 CATCH 文の後に 変数を宣言しなければなりません。この変数は、スクリプト内でのロー カ ル 変 数 宣 言 に 関 す る す べ て の 規 則 に 従 っ て い る だ け で な く、 Throwable から派生した型を持っていなければなりません。 TRY-CATCH-FINALLY、TRY-CATCH、TRY-FINALLY の各ブロックは、スク リプト ビューで PowerScript 文の[形式を指定して貼り付け]機能を 使用して追加できます。デザイン オプション ダイアログボックスの [オートスクリプト]タブにある[ステートメント テンプレート] チェックボックスをオンにすると、オートスクリプト機能を使用して 上記の各ブロック構文を挿入できます。 例 次の例は、アプリケーション ユーザに よって(シングルライン エディットに)入力された arccosine 引数の値 が、要求範囲外であることを示すシステム エラーを捕捉する TRYCATCH-FINALLY ブロックです。このエラーを捕捉しないと、システム エラー イベントが発生し、アプリケーションは最終的に異常終了しま す。 システム エラーを捕捉する例 Double ld_num ld_num = Double (sle_1.text) TRY sle_2.text = string (acos (ld_num)) CATCH (runtimeerror er) MessageBox(" 実行時エラー ", er.GetMessage()) FINALLY // クリーンアップ コードをここに追加 of_cleanup() Return END TRY MessageBox(" 完了 ", " 完了しました。") システム実行時のエラー メッセージはエンド ユーザには分かりにく いので、本稼働システムでは、ユーザ定義の例外を捕捉して(44 ペー ジの「ユーザ定義の例外型の作成」の例を参照)、分かりやすいメッ セージを設定するとよいでしょう。 42 PowerBuilder 第3章 PowerScript についての特別なトピック 予約語 TRY は、実行されるブロックの先頭を表します。ブロックには、 1 つまたは複数の CATCH 句を含めることができます。TRY ブロック内 のコードを実行中に例外が送出されると、最初の CATCH 句によって処 理されます。このとき、CATCH 句の変数に、送出された例外の値が代 入されます。CATCH 文の後の変数宣言は、処理される例外の型(この 例ではシステム実行時エラー)を表します。 CATCH 句の順序 1 つの CATCH 句がほかの CATCH 句を隠さないように CATCH 句を配 置することが必要です。先頭の CATCH 句で Exception 型の例外を捕捉 し、次の CATCH 句で Exception の子孫を捕捉するというような場合に、 この問題が発生します。指定した順に処理されるので、Exception の子 孫の例外は最初の CATCH 句で処理されて、2 番目の CATCH 句で処理 されることはありません。PowerScript コンパイラは、こうした状況を 検出すると、コンパイル エラーを発生させます。 どの CATCH 句によっても処理されなかった例外は、コールスタックの 上位に送出され、別の例外ハンドラ(try-catch ブロックの入れ子)、ま たはシステム エラー イベントによって処理されます。例外がコールス タックの上位に送出される前に、FINALLY 句が実行されます。 FINALLY 句 FINALLY 句では、一般的に、TRY 句または CATCH 句の実行後の後処理 を行います。FINALLY 句に指定されたコードは、try-catch ブロック内の いずれかの部分が実行されると、try-catch ブロックの終了状態に関係 なく必ず実行されます。 例外が発生しないと、TRY 句が終了した後、FINALLY 句に指定された文 が実行されます。そして、END TRY 文の次の行から処理が続行されま す。 CATCH 句が 1 つもなく、FINALLY 句だけが存在する場合は、FINALLY 句 に指定されたコードが実行されます。戻り値が検出された場合や TRY 句内で例外が送出された場合でも、FINALLY 句は必ず実行されます。 TRY 句のコンテキストで例外が発生した場合、その例外を処理できる 適切な CATCH 句があればその CATCH 句が実行され、その後、FINALLY 句が実行されます。送出された例外を処理できる適切な CATCH 句が存 在しない場合でも、FINALLY 句は必ず実行され、その後、コールスタッ クの上位に(未処理の)例外が送出されます。 CATCH 句内で例外が発生するか戻り値が検出された場合は、FINALLY 句が実行されてから、プログラム内の次の実行場所に制御が移ります。 アプリケーション テクニック 43 PowerBuilder での例外処理 ユーザ定義の例外型の作成 Exception または RuntimeError、あるいは Exception または RuntimeError から派生した既存のユーザ オブジェクトを継承する標準クラス ユー ザ オブジェクトから、ユーザ定義の固有の例外型を作成することがで きます。 Exception オブジェク ト型からの継承 通常、ユーザ定義の例外型は、Exception 型またはその子孫を継承する 必要があります。RuntimeError 型はシステム エラーを表すために使用 します。ユーザ定義のオブジェクトには、システム内のそのほかの非 ビジュアル ユーザ オブジェクトと同様、イベント、関数、インスタン ス変数を定義できます。 ユーザ定義の例外型は、たとえば、ビジネス ルール違反などの特定の 条件によってアプリケーション ロジックが異常終了する場合の処理 に使うと便利です。こうした条件を記述するユーザ定義の例外型を作 成し、例外を正しく捕捉して処理すれば、実行時エラーを回避できま す。 例外の送出 例外は、エラー条件を示すために、ランタイム エンジンによって送出 されます。潜在的な例外条件を手動で送出する場合は、THROW 文を使 用する必要があります。 THROW 文は通常、ユーザ定義の例外型と組み合わせて使用します。以 下に、THROW 文の使い方を簡単な例を用いて示します。 Exception le_ex le_ex = create Exception Throw le_ex MessageBox (" 注意 ", " 例外変数が " & + " インスタンス化されていなくてはなりません ") この例では、le_ex 例外のインスタンスを送出しています。予約語 THROW の後に続く変数は、Throwable から派生した型を持つ例外オブ ジェクトの有効なインスタンスへのポインタでなければなりません。 インスタンス化されていない Exception 変数を送出しようとすると、 ルーチン内に Null オブジェクト参照が存在することを示す NullObjectError が発生します。これは、アプリケーションのエラー処理を複雑にする だけです。 関数から送出される例 外の宣言 44 メソッド スクリプト内で THROW 文を使用して例外を送出する場合 に、その例外型を処理する try-catch ブロックで THROW 文を囲まない ときは、その例外をそのメソッドが送出可能な例外型(またはその子 孫)として宣言する必要があります。ただし、実行時エラーが送出可 能であることは PowerBuilder がかわりに宣言してくれるので、メソッ ドで宣言する必要はありません。 PowerBuilder 第3章 PowerScript についての特別なトピック ほとんどの PowerBuilder ペインタのスクリプト ビューにあるプロトタ イプ ウィンドウを使用すれば、関数またはユーザ定義のイベントが送 出可能なユーザ定義の例外を宣言できます。システム ツリーまたはラ イブラリ ペインタ ビューからプロトタイプ ウィンドウ内の[Throws] ボックスに例外型をドラッグ アンド ドロップするか、メソッドが送出 可能な例外型をコンマで区切られたリストとして入力します。 例 ユーザ定義の例外を捕捉する例 次 の コ ー ド で は、ア プ リ ケ ー シ ョ ン ユーザが入力した arccosine 引数が指定範囲外である場合にユーザ定義 のエラーを表示します。try-catch ブロック内で wf_acos メソッドを呼び 出します。このメソッドは、システム エラーを捕捉し、ユーザ定義の エラーを設定および送出します。 TRY wf_acos() CATCH (uo_exception u_ex) MessageBox(" 範囲外 ", u_ex.GetMessage()) END TRY wf_acos メソッドの中身は次のとおりです。 uo_exception lu_error Double ld_num ld_num = Double (sle_1.text) TRY sle_2.text = string (acos (ld_num)) CATCH (runtimeerror er) lu_error = Create uo_exception lu_error.SetMessage(" 値は -1 ~ " & + "1 の範囲になければなりません ") Throw lu_error END TRY EAServer との統合 ユーザ オブジェクトのメソッドで例外を宣言し、そのユーザ オブジェ クトを EAServer のコンポーネントとして配布すると、メソッド プロ トタイプの一部として例外が IDL(CORBA)に変換されます。つまり、 EAServer 内の PowerBuilder コンポーネントを、 任意のタイプの EAServer クライアント アプリケーションで処理可能な例外を送出するように 定義できます。 EAServer アプリケーションのそのほかの利点 コンポーネント開発の別 の利点は、コンポーネント内で実行時エラーを処理できることです。 未処理のエラーは自動的に例外に変換され、コンポーネントは実行を 中止します。 アプリケーション テクニック 45 PowerBuilder での例外処理 EAServer コンポーネントを使用した PowerBuilder クライアント アプ リケーションは、どのタイプの EAServer コンポーネントから送出され た例外も処理できます。例外を送出するように定義されたメソッドを 持つ Java EAServer コンポーネントがあり、そのコンポーネントを使用 して PowerBuilder プロキシを作成すると、PowerBuilder プロキシ上の メソッドもユーザ定義の例外を送出するように宣言されます。ユーザ 定義の例外に関する定義は、PowerBuilder プロキシの作成時に自動的 に作成されます。 EAServer のエラー処理についての詳細は、596 ページの「エラー処理」 を参照してください。 IDL の制限 EAServer のコンポーネントを配布する場合は、PowerBuilder 内での例外処理の使い方に制限が課されます。IDL に変換されるのは、 該当する例外型に定義されたパブリックなインスタンス変数だけで す。これは、IDL 例外を送出するようにメソッドを宣言することはで きないためです。したがって、特定の例外型が送出されるように定義 されたメソッドがある場合、それらのメソッドをコンポーネントの実 行中に呼び出すことはできますが、クライアント アプリケーションか らそれらのメソッドを呼び出して送出された例外を捕捉することはで きません。 分散アプリケーションでの例外オブジェクトを設計するときには、こ の制限を忘れないようにしなければなりません。すなわち、分散アプ リケーションでは、すべての例外情報を、例外オブジェクトのアクセ サ メソッドを介してではなく、パブリックなインスタンス変数として 公開する必要があります。 EAServer コンポーネントとして配布されるユーザ オブジェクトの例 外型に適用されるインタフェース上の制限があと 2 つあります。ユー ザ オブジェクト メソッドの例外を表すインスタンス変数は、オブジェ クト データ型を持つことができません。また、Null データは、単純な データ型を持つインスタンス変数の場合だけサポートされています。 インスタンス変数が構造体または配列の場合、各要素の Null 値は維持 されません。 柔軟性の向上とオブジェクトの再利用の促進 例外処理を使用すると、PowerBuilder アプリケーションの柔軟性を高 め、ビジネス ルールをプレゼンテーション ロジックから切り離すこと ができます。たとえば、ビジネス ルールを、以下の非ビジュアル オブ ジェクト(nvo)に格納できます。 46 PowerBuilder 第3章 • PowerScript についての特別なトピック プレゼンテーション オブジェクトへの参照を保持するインスタン ス変数 powerobject my_presenter • プレゼンテーション オブジェクトを登録する関数 登録用関数には次の構文を使用します。 SetObject (string my_purpose, powerobject myobject) • プレゼンテーション オブジェクトによって実装された動的関数を 呼び出すコード(データの表示方法については最小限の機能のみ をサポート) 動的関数呼び出しは、次のように try-catch ブロックで囲む必要が あります。 TRY my_presenter.Dynamic nf_displayScreen(" ") CATCH (Throwable lth_exception) Throw lth_exception END TRY この try-catch ブロックは、プレゼンテーション オブジェクトで発 生するシステム エラーとユーザ定義のエラーをすべて捕捉し、呼 び出し元(この nvo を呼び出したオブジェクト)に送出します。上 の例では、CATCH 文で送出されるオブジェクトの型が Throwable に なっていますが、次のようにユーザ定義の例外オブジェクトをイ ンスタンス化および送出することもできます。 uo_exception luo_exception TRY my_presenter.Dynamic nf_displayScreen(" ") CATCH (Throwable lth_exception) luo_exception = Create uo_exception luo_exception.SetMessage & + (lth_exception.GetMessage()) Throw luo_exception END TRY データ処理用のコードは、プレゼンテーション オブジェクト、ビジネ ス ルール nvo、または nvo によって呼び出されるデータ処理用オブ ジェクトに追加できます。具体的にどのような設計にするかはビジネ スの目的によって異なりますが、このデータ処理用のコードも trycatch ブロックで囲む必要があります。実行するアクションと(処理失 敗時に)報告するエラー メッセージは、処理用コードを囲む try-catch ブロック内でできる限り具体的に指定します。 アプリケーション テクニック 47 PowerBuilder での例外処理 この手法には大きな利点がいくつかあります。まず、ビジネス nvo を 非常に簡単に再利用できるようになります。これにより、同じビジネ ス データをさまざまな方法で表示するオブジェクトからビジネス nvo を使用できます。また、例外処理を追加したことにより堅牢性が大幅 に向上し、アプリケーション ユーザがエラー条件から回復できる可能 性が高くなります。 SystemError イベントと Error イベントの使い方 Error イベント 実行時エラーが発生すると、そのエラーを記述するエラー構造体が作 成されます。リモート サーバ(EAServer など)との接続のコンテキス トでエラーが発生すると、接続、JaguarORB、データウィンドウ、OLE などのコントロール オブジェクトの Error イベントが起動されます。 このとき、エラー構造体の情報が引数として渡されます。 この Error イベント内でエラーを処理するには、特殊な参照引数を使用 してエラーを無視できるようにします。上記のコンテキストでエラー が発生しないか、または上記のコンテキストで発生したエラーが処理 されないと、エラー構造体情報がグローバル エラー変数に格納され、 アプリケーション オブジェクトの SystemError イベントが起動されます。 SystemError イベント SystemError イベントでは、予期せぬエラー条件を制限された方法で処 理できます。一般に、SystemError イベントが起動された後も処理を継 続するのはよくありません。しかし、SystemError イベントにはエラー 処理用のコードを追加できるようになっており、また追加するべきで す。SystemError イベントは通常、アプリケーションを終了する前に データを保存したり、 (ファイルやデータベース接続を閉じるなど)最 後の後処理を実行したりするために使用します。 例外ハンドラおよびイ ベントの優先順位 Error イベント内にコードを書くと、例外発生時にまずそのコードが実 行されます。 上記のどのコンテキストでも例外を送出しないか、オブジェクトの Error イベントによって例外が処理されないか、または Error イベント をコーディングしないと、その例外型を処理できる任意のアクティブ な例外ハンドラ(CATCH 句)によって例外が処理されます。例外を処 理する例外ハンドラが存在しない場合に限って、例外クラスの情報が グローバルなエラー変数にコピーされ、アプリケーション オブジェク トの SystemError イベントが起動されます。 48 PowerBuilder 第3章 新規アプリケーション のエラー処理 PowerScript についての特別なトピック 新規の PowerBuilder アプリケーションでは、接続、データウィンドウ、 OLE などのコントロール オブジェクトの Error イベントをコーディン グするのではなく、try-catch ブロックを使用してエラーを処理するこ とをお勧めします。ただし、捕捉されない例外を処理するために、ア プリケーション オブジェクトには SystemError イベントを設定してお く必要があります。SystemError イベントは本質的に、PowerBuilder ア プリケーションのグローバルな例外ハンドラになります。 ガベージ コレクションとメモリ管理 PowerBuilder のガベージ コレクション機能は、未参照の孤立したオブ ジェクトがないかどうかメモリを自動的にチェックし、もしあればそ れを削除します。これにより、大半のメモリ リークを防ぐことができ ます。ガベージ コレクションを使用すると、DESTROY 文で明示的に指 示することなくオブジェクトを破壊できます。これにより、ほかのプ ロセスで使用中のオブジェクト、ポストされたイベント、および関数 に参照渡しされたオブジェクトを間違って破壊してしまうことによっ て起こる実行時エラーを防ぐことができます。 オブジェクトへの参照とは、値が object 型であるすべての変数のことで す。これらの変数がスコープの外に出るか object 型以外の値が代入さ れると、PowerBuilder はそのオブジェクトへの参照を削除し、残りの 参照数を数えて、参照数がゼロならガベージ コレクション プロセスは そのオブジェクトを破棄します。 ガベージ コレクションが発生するタイミングは、次のとおりです。 • 設定されたガベージ コレクション実行間隔を超え、 PowerBuilder アプリケーションがアイドル状態になったとき • GarbageCollect 関数を明示的に呼び出したとき PowerBuilder はシステムによって起動されたイベントの処理が終了し たとき、前回のガベージ コレクションからの経過時間が、設定された 実行間隔を超えている場合は、ガベージ コレクション操作を実行しま す。デフォルトの実行間隔は 0.5 秒です。このシステムによって起動 されるガベージ コレクションは、PowerBuilder アプリケーションがア イドル状態のときにのみ発生します。そのため、実行間隔を超えたと きに時間のかかる計算や処理を実行している場合、ガベージ コレク ションはすぐには発生しないため、注意が必要です。 アプリケーション テクニック 49 ガベージ コレクションとメモリ管理 GarbageCollect 関数を呼び出して、ガベージ コレクションを強制的に実 行できます。ドット表記および OLEObjects を使用すると、一時変数が 作成されます。これらの一時変数は、ガベージ コレクションが処理さ れている間だけ解放されます。そのため、メモリ リークの原因となっ ている可能性のあるループ内で GarbageCollect を呼び出すことをお勧 めします。 ガベージ コレクション操作では、参照できないオブジェクトとクラス がすべて削除されます。これには循環参照(相互に参照し合うが、ほ かからは一切参照されていないオブジェクト)も含まれます。 イベントと関数のポスト イベントまたは関数をポストしてオブジェクトへの参照を渡すと、 PowerBuilder はそのオブジェクトへの内部参照を追加します。これに より、ポストしてからそのイベントまたは関数が終了するまでの間に、 そのオブジェクトが占有しているメモリがガベージ コレクションに よって収集されなくなります。追加された参照は、そのイベントまた は関数の実行が終了すると削除されます。 ガベージ コレクショ ンの対象にならないオ ブジェクト ガベージ コレクショ ンの発生の制御 50 次のオブジェクトはガベージ コレクションの対象から除外されます。 • ビジュアル オブジェクト 画面に表示されるオブジェクトは、画面 で作成され表示されるときに内部参照が追加されるため、ガベー ジ コレクションは行われません。ビジュアル オブジェクトは、閉 じるときに明示的に破棄します。 • タイミング オブジェクト • 共有オブジェクト SharedObjectRegister 関数は内部参照を追加する ため、登録された共有オブジェクトにはガベージ コレクションは 行われません。SharedObjectUnregister 関数を呼び出すと、追加され た内部参照が削除されます。 タイミング オブジェクトの Start 関数は そのオブジェクトの内部参照を追加するため、現在実行中のタイ ミング オブジェクトにはガベージ コレクションは行われません。 Stop 関数を呼び出すと追加された参照が削除されます。 ガベージ コレクションは PowerBuilder 内で自動的に行われますが、関 数を呼び出して、ガベージ コレクションを強制実行したり、参照カウ ントをチェックする間隔を変更したりすることもできます。ガベージ コレクション発生を制御する関数として、GarbageCollect、 GarbageCollectGetTimeLimit、および GarbageCollectSetTimeLimit の 3 つが 用意されています。 PowerBuilder 第3章 PowerScript についての特別なトピック これらの関数についての詳細は、『PowerScript リファレンス』マニュ アルを参照してください。これらの関数の使用例については、第 1 章 「サンプル アプリケーションの使い方」の Code Examples サンプル ア プリケーションを参照してください。 パフォーマンスに関す る考慮点 トレースとプロファイルを使用すると、ガベージ コレクションの実行 間隔を変更することによるパフォーマンスへの影響を調べることがで きます。 トレースとプロファイルの詳細については、PowerBuilder の『ユーザー ズ ガイド』マニュアルを参照してください。 メモリ管理の設定 PowerBuilder メモリ マネージャが別のメモリ割り当て方法に切り替え るときの閾値を指定するには、PB_POOL_THRESHOLD 環境変数を設 定します。 ほとんどのウィンドウ、データウィンドウ、データストア、またはそ のほかの PowerBuilder オブジェクトがガベージ コレクタによって破棄 または解放されると、PowerBuilder ヒープ マネージャは、そのオブジェ クトに割り当てられていたメモリをグローバル メモリ プールに戻し、 それを利用可能なメモリとしてグローバル フリー リストに記録しま す。解放されたメモリは、オペレーティング システムには戻されませ ん。新規オブジェクトが作成されるときに、PowerBuilder は、グロー バル フリー リストに十分な利用可能メモリがある場合はグローバル メモリ プールのメモリ ブロック、ない場合はオペレーティング シス テムのメモリ ブロックをオブジェクトのメモリ プールに割り当てま す。 オブジェクトに必要なメモリが 256 KB を超える場合、PowerBuilder は 別の方法でメモリを割り当てます。メモリが要求されるとオペレー ティング システムから大きいブロックで以降のメモリを割り当て、オ ブジェクトが破棄されると物理メモリをオペレーティング システム に戻します。また、仮想アドレス空間のフラグメンテーションを抑え るために仮想メモリを保持します。 ほとんどのアプリケーションとコンポーネントでは、必要なメモリが 256 KB の閾値に達したときに、PowerBuilder は「大きいブロック」の 方法に切り替えます。これにより、メモリは適切に割り当てられ、ア プリケーションがピーク時に必要とするメモリも少なくなります。た だし、アプリケーションが使用する全体の物理メモリをできるだけ少 なくする必要がある場合は、この閾値をもっと低く設定できます。 アプリケーション テクニック 51 ガベージ コレクションとメモリ管理 低い閾値を設定すると、グローバル メモリ プールのサイズが縮小され るという利点があります。アプリケーションは、動作していないとき はメモリの大部分を保持しません。ただし、欠点として、設定した閾 値より多くのメモリを必要とするオブジェクトに大きいメモリ ブ ロックが割り当てられた場合、アプリケーションがピーク時に使用す る仮想メモリ量がデフォルトの閾値の場合よりも多くなる可能性があ ります。 低い閾値を設定するのは、長時間動作するクライアント アプリケー ションが動作時間の短いオブジェクトを多数使用する場合に適してい ます。このようなアプリケーションでは、メモリ使用量が少なくなっ たり(アイドル時)多くなったり(動作時)するからです。サーバな どのマルチスレッド アプリケーションの場合は、高い閾値を設定する と、通常は仮想メモリの使用量が少なくなります。 ヒープ マネージャ出 力のログへの記録 PowerBuilder ヒープ マネージャの診断出力をファイルに記録できます。 この情報は、アプリケーションにおけるメモリ割り当ての問題を解決す る際に役立ちます。ファイルの名前と場所は PB_HEAP_LOGFILENAME 環境変数で設定します。 ディレクトリではなくファイル名を指定すると、 ファイルは PowerBuilder の実行ファイルと同じディレクトリに保存されます。または、EAServer で動作している PowerBuilder コンポーネントの場合は、EAServer の bin ディレクトリに保存されます。 存在しないディレクトリを指定した場合、ファイルは作成されません。 または、EAServer で動作している PowerBuilder コンポーネントの場合 は、EAServer のログ ファイル(Jaguar.log)に出力が書き込まれます。 デフォルトでは、ログ ファイルは、PowerBuilder または EAServer を再 起動するたびに上書きされます。診断出力をファイルの最後に追加す るには、PB_HEAP_LOGFILE_OVERWRITE に false を設定します。 環境変数は、アプリケーションを起動するバッチ ファイルで設定する か、アプリケーションまたはコンポーネントを実行するコンピュータ やサーバ上でシステム環境変数またはユーザ環境変数として設定でき ます。 PowerBuilder および EAServer でメモリ管理をチューニングする方法に ついては、テクニカル ドキュメント EAServer/PowerBuilder Memory Tuning and Troubleshooting のサイト http://www.sybase.com/detail?id=1027319 を参照してください。 52 PowerBuilder 第3章 PowerScript についての特別なトピック 効率的なコンパイルとパフォーマンス 関数の記述や変数の定義のしかたは、開発の生産性とアプリケーショ ンのパフォーマンスに影響を与えます。 スクリプトを短くして コンパイル時間を短縮 する 配布アプリケーション用の動的ライブラリを構築する場合は、関数と イベントのスクリプトを短くするようにしてください。スクリプトが 長いとコンパイルに時間がかかります。1 つの長いスクリプトを書く かわりに、ほかの複数の関数を呼び出すスクリプトを作成できるよう に、スクリプトを分割してください。ユーザ オブジェクト内の関数を、 ほかのオブジェクトからも呼び出せるように定義することを考慮して ください。 ローカル変数を使用し てパフォーマンスを向 上 変数のスコープはパフォーマンスに影響を与えます。できるだけロー カル変数を使うようにしてください。そうすれば、パフォーマンスが 向上します。グローバル変数を使うと、パフォーマンスが大幅に低下 します。 テキスト ファイルとバイナリ ファイルの読み書き ライン モードまたはテキスト モードでテキストを読み書きしたり、ス トリーム モードでバイナリ ファイルを読み書きしたりするには、 PowerScript のテキスト ファイル関数を使用します。 • ライン モードでは、キャリッジ リターンか改行(CR/LF)または ファイルの終わり(EOF)が現れるまで、一度に 1 行ずつファイ ルを読み込みます。ファイルに書き込むときは、指定された文字 列を書き込んだ後、CR/LF を追加します。 • ストリーム モードでは、ファイルの中身を、CR/LF も含めてすべ て読み込むことができます。ファイルに書き込むときは、指定さ れた Blob データを書き込みます(ただし、CR/LF は追加しません)。 • テキスト モードでは、ファイルの中身を、CR/LF も含めてすべて 読み込むことができます。ファイルに書き込むときは、指定され た文字列を書き込みます(ただし、CR/LF は追加しません)。 マルチラインエディットにファイルを読み込む ストリーム モードを使用すると、ファイル全体をマルチラインエ ディットに読み込み、修正した後に書き出すことができます。 アプリケーション テクニック 53 テキスト ファイルとバイナリ ファイルの読み書き 位置ポインタ PowerBuilder は、ファイルを開くと、そのファイルに一意な整数を割 り当て、ファイルの位置ポインタを指定された位置、つまりファイル の先頭(バイト オーダー マーク(BOM: Byte-Order Mark)がある場合 はその後)または末尾に設定します。ファイルを読み書きしたり閉じ たりするときに、この一意な整数を使用してファイルを特定します。 位置ポインタは、次の読み書きの開始位置を指します。読み書きを実 行するたびに、位置ポインタが自動的に進められます。 位置ポインタは、FileSeek または FileSeek64 関数を使用して設定するこ ともできます。 ファイル操作関数 PowerScript には、次のファイル操作用組み込み関数が用意されていま す。 表 3-1: PowerScript のファイル操作用関数 関数 戻りデータ型 FileClose Integer FileDelete FileEncoding FileExists FileLength FileLength64 FileOpen FileRead FileReadEx FileSeek エンコーディング 54 動作内容 指定されたファイルを閉じる Boolean 指定されたファイルを削除する Encoding カタロ ファイルで使用されているエンコーディン グ データ型 グを返す Boolean 指定されたファイルが存在するかどうかを 判定する Long サイズが 2 GB 以下のファイルの長さを取 得する LongLong 任意のサイズのファイルの長さを取得する Integer 指定されたファイルを開く Integer 指定されたファイルを読み込む(非推奨) Long 指定されたファイルを読み込む Long サイズが 2 GB 以下のファイル内の特定位 置に位置ポインタを設定する FileSeek64 LongLong FileWrite Integer FileWriteEx Long 任意のサイズのファイル内の特定位置に位 置ポインタを設定する 指定されたファイルに書き込む(非推奨) 指定されたファイルに書き込む FileOpen 関数の最後の引数を指定すると、ANSI、UTF-8、UTF-16LE (リトル エンディアン)、または UTF16-BE(ビッグ エンディアン)ファ イルを作成できます。 PowerBuilder 第3章 PowerScript についての特別なトピック encoding 引数は、FileOpen 関数のファイル名以外のすべての引数と同様 にオプションです。Unicode エンコーディングの新規テキスト ファイ ルを作成する場合のみ必須です。filename 引数に存在しないファイル を指定すると、FileOpen 関数によってファイルが作成され、encoding 引 数に指定された文字エンコーディングが設定されます。 デフォルトでは、存在しないファイルを指定して encoding 引数を指定 しなければ、ファイルは ANSI エンコーディングで開かれます。これ により、PowerBuilder の旧バージョンとの互換性が維持されます。 FileRead 関数と FileWrite 関数は、一度に 32,766 バイトを超えるデータ を読み込むことができません。かわりに FileReadEx 関数と FileWriteEx 関数を使用すると、一度に大量のデータを読み書きできます。 アプリケーション テクニック 55 テキスト ファイルとバイナリ ファイルの読み書き 56 PowerBuilder 第 4 章 PowerBuilder のクラス定義に関する 情報の取得 この章について この章では、クラス定義情報の概要、その使い方、およびサンプ ル コードについて説明します。ツールとオブジェクト フレーム ワークの開発者は、似たような特性を持つオブジェクトの定義や レポートの作成などの作業に関して、クラス定義情報を使用でき ます。一般的なビジネス アプリケーションを構築する場合には、 クラス定義情報を使用する必要はありません。 内容 項目 クラス定義情報の概要 クラス定義の調査 ページ 57 61 クラス定義情報の概要 ClassDefinition オブジェクトは、PowerBuilder オブジェクトの 1 つ であり、別の PowerBuilder オブジェクトのクラスに関する情報を 提供します。PowerBuilder ライブラリ内のクラス、またはインス タンス化されたオブジェクトのクラスを調べることができます。 クラスの ClassDefinition オブジェクトのプロパティを調べること によって、クラスが PowerBuilder のオブジェクト階層構造にどう 収まるかを詳細に知ることができます。 ClassDefinition オブジェクトからは、以下の項目を知ることができ ます。 アプリケーション テクニック • そのクラスに定義された変数、関数、およびイベント • そのクラスの先祖 • そのクラスの親 • そのクラスの子(ネスティッド クラス) 57 クラス定義情報の概要 関連するオブジェクト ClassDefinition オブジェクトは、データ型に関する情報を提供したり、 クラス定義に関連付けられた変数、プロパティ、関数、およびイベント スクリプトに関する情報を提供したりするオブジェクト(TypeDefinition、 VariableDefinition、および ScriptDefinition などのオブジェクト)の階層 構造のメンバーです。 詳細については、ブラウザまたは『オブジェクトとコントロール』マ ニュアルを参照してください。 インスタンス化されたオブジェクトの定義 ClassDefinition プ ロ パテ ィ を 使うと、ClassDefinition オブジェクトを使って、各オブジェクトのイン スタンスから、オブジェクトの記述を取得できます。ClassDefinition オ ブジェクトは、変数の値などのオブジェクト インスタンスに関する情 報を提供しません。このような情報は、インスタンスから直接取得す る必要があります。 ライブラリでのオブジェクトの定義 クラス情報を取得するには、必ずし も オ ブ ジ ェ ク ト が イ ン ス タ ン ス 化 さ れ て い る 必 要 は あ り ま せ ん。 PowerBuilder ライブラリ内のオブジェクトの場合には、FindClassDefinition 関数を呼び出して、その ClassDefinition オブジェクトを取得できます。 パフォーマンス クラス定義オブジェクトを使用するとオーバーヘッ ドが大きくなるように思われますが、オーバーヘッドが生じるのは ClassDefinition オブジェクトを参照するときだけです。ClassDefinition オブジェクトがインスタンス化されるのは、FindClassDefinition を呼び 出すとき、および PowerBuilder オブジェクトの ClassDefinition プロパ ティにアクセスするときに限られます。同様に、ClassDefinition オブ ジェクトのプロパティ自身が ClassDefinition または VariableDefinition オブジェクトである場合には、オブジェクトがインスタンス化される のは、それらのプロパティを参照するときだけです。 用語 クラス情報には、オブジェクト間の関係についての情報が含まれます。 これらの定義は、情報の意味を理解するときに役立ちます。 オブジェクト インス タンス 58 オブジェクトを具現化したものです。インスタンスはメモリ内に存在 し、そのプロパティと変数には値が割り当てられています。オブジェ クト インスタンスが存在するのは、アプリケーションを実行するとき だけです。 PowerBuilder 第4章 PowerBuilder のクラス定義に関する情報の取得 クラス オブジェクトの定義であり、オブジェクト インスタンスを作成するた めのソース コードを含んでいます。PowerBuilder ペインタを使用して、 オブジェクトを PBL に保存するときには、オブジェクトのクラス定義 を作成していることになります。アプリケーションを実行する場合に は、クラスは、そのクラスに基づくオブジェクト インスタンスのデー タ型となります。PowerBuilder では、 「オブジェクト」という用語は一 般にオブジェクトのインスタンスを表します。場合によっては、オブ ジェクトのクラスを表すこともあります。 システム クラス PowerBuilder によって定義されるクラスです。ペインタで定義するオ ブジェクトは、たとえ定義するオブジェクトの継承を使用するよう明 示的に選択しない場合でも、システム クラスの子孫となります。 親 現行のオブジェクトを含むオブジェクト、または継承以外の方法でオ ブジェクトに接続されているオブジェクトです。次の表に、オブジェ クトのクラスと、そのオブジェクトの親になれるクラスを示します。 表 4-1: オブジェクトのクラスとその親 オブジェクト ウィンドウ 親 そのウィンドウを開いたウィンドウ メニュー項目 ウィンドウは親を持たないこともある。親は実行 時に決定され、クラス定義の一部ではない メニューにおける前のレベルのメニュー項目 ウィンドウ上のコント ロール ユーザ オブジェクト 上のコントロール タブ ページ リストビュー項目また はツリービュー項目 ビジュアル ユーザ オ ブジェクト メニュー バー上の項目は、関連するドロップダウ ン メニュー上のすべての項目の親となる ウィンドウ ユーザ オブジェクト タブ ページが定義されているか、または開かれた タブ コントロール リストビューまたはツリービュー コントロール ユーザ オブジェクトが置かれているウィンドウま たはユーザ オブジェクト 子 別の親クラスに含まれているクラスです。ネスティッド クラスとも呼 ばれます。親と子の関係を持つオブジェクトのタイプに関しては、 「親」 を参照してください。 先祖 その定義から別のオブジェクトが継承されるクラスです。 「子孫」も参 照してください。 アプリケーション テクニック 59 クラス定義情報の概要 子孫 別のオブジェクトから継承され、そのオブジェクトの特質(プロパ ティ、関数、イベント、および変数)を内蔵するオブジェクトです。 子孫は、これらの値を使用したり、新しい定義でこれらの値に上書き したりすることができます。ペインタで定義してライブラリに格納す るオブジェクトは、すべて PowerBuilder システム クラスの子孫です。 継承階層 オブジェクトおよびそのすべての先祖です。 折りたたまれた階層 オブジェクト クラス定義のビューであり、現行レベルの継承で定義さ れている項目に加えて、オブジェクトの継承ツリー内のすべての先祖 からの情報も含んでいます。 スカラ オブジェクトでも配列でもない、単純なデータ型です。たとえば、Integer、 Boolean、Date、Any、および String です。 インスタンス変数とプ ロパティ PowerBuilder システム オブジェクトに組み込まれた属性はプロパティ と呼ばれますが、クラス定義情報ではインスタンス変数として扱われ ます。 PowerBuilder クラス定義の使用について 多くのビジネス アプリケーションでは、クラス定義情報を使用する必 要はありません。クラス定義情報を使用するコードは、クラス ライブ ラリ、アプリケーション フレームワーク、および開発支援ツールを記 述するグループによって記述されます。 アプリケーションにはクラス定義情報を使用するコードが含まれてい ないかもしれませんが、デザイン、ドキュメンテーション、およびク ラス ライブラリに使用するツールには含まれている可能性がありま す。これらのツールは、アプリケーションの解析とフィードバックの 提供ができるよう、オブジェクトのクラス定義を調べます。 シナリオ 以下の開発を行う場合には、クラス情報を使用することがあ ります。 • カスタム オブジェクト ブラウザ • アプリケーションのオブジェクトとそれらの関係を知る必要のあ るツール 目的としては、アプリケーションを文書化したり、オブジェクト を選択および操作するための論理的な方法を提供したりすること が挙げられます。 • 60 PowerBuilder オブジェクトを分解し、ユーザによるデザイン変更と 再構築を可能にする CASE ツール PowerBuilder 第4章 PowerBuilder のクラス定義に関する情報の取得 再構築を行うために、CASE ツールは、PowerBuilder オブジェクト のソース コード構文の知識とクラス定義情報を必要とします。 • オブジェクトで、インスタンス化されたオブジェクトに関連付け られたクラスを決定する必要があるクラス ライブラリ。または、 スクリプトで、使用可能なメソッドと変数を想定するためにオブ ジェクトの先祖を知る必要があるクラス ライブラリ クラス定義の調査 この節では、クラス定義オブジェクトへのアクセス方法を説明します。 さらに、クラス定義オブジェクトのプロパティを調べて、クラス、そ のスクリプト、およびその変数に関する情報を取得する方法について も説明します。 クラス定義オブジェクトの取得 クラス情報を取り扱うには、クラス定義オブジェクトが必要となりま す。クラス定義情報を含む ClassDefinition オブジェクトを取得するに は、2 つの方法があります。 アプリケーション内で インスタンス化された オブジェクトの場合 オブジェクトの ClassDefinition プロパティを使用します。 たとえば、ボタン用のスクリプトでは、次のコードは、親ウィンドウ のクラス定義を取得します。 ClassDefinition cd_windef cd_windef = Parent.ClassDefinition PBL に格納されたオ ブジェクトの場合 FindClassDefinition を呼び出します。 たとえば、ボタン用のスクリプトでは、次のコードは、アプリケーショ ンのライブラリ リスト上のライブラリから w_genapp_frame ウィンド ウのクラス定義を取得します。 ClassDefinition cd_windef cd_windef = FindClassDefinition("w_genapp_frame") アプリケーション テクニック 61 クラス定義の調査 クラスに関する詳細情報の取得 この節に含まれるコード フラグメントでは、cd_windef という ClassDefinition オブジェクトから情報を取得する方法を説明します。 cd_windef に値を割り当てる例については、 「クラス定義オブジェクト の取得」を参照してください。 ライブラリ LibraryName プロパティは、クラスのロード元となったライブラリの名 前をレポートします。 s = cd_windef.LibraryName 先祖 Ancestor プロパティは、このクラスの継承元となったクラスの名前を レポートします。すべてのオブジェクトは PowerBuilder システム オブ ジェクトから継承されるので、Ancestor プロパティは、PowerBuilder ク ラスの ClassDefinition オブジェクトを保持できます。ClassDefinition が (継承階層の最上位にある)PowerObject 用である場合には、Ancestor プロパティには NULL オブジェクト参照があります。 次の例では、cd_windef によって表されるクラスの先祖の ClassDefinition オブジェクトを取得します。 ClassDefinition cd_ancestorwindef cd_ancestorwindef = cd_windef.Ancestor 次の例では先祖の名前を取得します。なお、cd_windef に PowerObject の定義が含まれている場合には、Ancestor プロパティが NULL となる ため、このコードを実行するとエラーになります。 ls_name = cd_windef.Ancestor.Name オブジェクトが NULL でないことをテストするには、IsValid 関数を使 用します。 次の例では、w_genapp_frame ウィンドウの継承階層を逆向きにたどっ て、その先祖のリストをマルチライン エディットに表示します。 string s, lineend ClassDefinition cd lineend = "~r~n" cd = cd_windef s = "Ancestor tree:"+ lineend DO WHILE IsValid(cd) s = s + cd.Name + lineend cd = cd.Ancestor LOOP 62 PowerBuilder 第4章 PowerBuilder のクラス定義に関する情報の取得 mle_1.Text = s 次のようなリストになります。 Ancestor tree: w_genapp_frame window graphicobject powerobject 親 ClassDefinition オブジェクトの ParentClass プロパティは、オブジェク トの定義に指定された親(コンテナ)をレポートします。 ClassDefinition cd_parentwindef cd_parentwindef = cd_windef.ParentClass クラスに親がない場合には、ParentClass は NULL オブジェクト参照と なります。次の例では、ParentClass が有効なオブジェクトであること をテストしてから、その Name プロパティをチェックします。 IF IsValid(cd_windef.ParentClass) THEN ls_name = cd_windef.ParentClass.Name END IF ネスティッド クラス または子クラス ClassDefinition オブジェクトの NestedClassList 配列には、そのオブジェ クトが含んでいるクラスがあります。 NestedClassList 配列には先祖と子孫があります。 NestedClassList 配列は先祖オブジェクトのクラスを含むことができま す。たとえば、先祖ウィンドウで定義され、子孫ウィンドウで修正さ れたコマンドボタンは、子孫ウィンドウの配列に 2 度現われます(つ まり、ウィンドウとその先祖に現われます)。 次のスクリプトでは、cd_windef で表されるウィンドウに定義されたコ ントロールと構造体のリストを作成します。 string s, lineend integer li lineend = "~r~n" s = s + "Nested classes:"+ lineend FOR li = 1 to UpperBound(cd_windef.NestedClassList) s = s + cd_windef.NestedClassList[li].Name & + lineend NEXT mle_1.Text = s アプリケーション テクニック 63 クラス定義の調査 次のスクリプトでは、ClassDefinition オブジェクト cd_windef にある NestedClassList 配列を検索して、入れ子のドロップダウン リストボッ クス コントロールを見つけ出します。 integer li ClassDefinition nested_cd FOR li = 1 to UpperBound(cd_windef.NestedClassList) IF cd_windef.NestedClassList[li].DataTypeOf & = "dropdownlistbox" THEN nested_cd = cd_windef.NestedClassList[li] EXIT END IF NEXT オブジェクト参照とは異なるオブジェクト インスタンスのクラス定義 先祖やネスティッド オブジェクトなど、インスタンス化されたオブ ジェクトの ClassDefinition オブジェクトを取得しても、親クラスまた は子クラスのインスタンスへの参照は行われません。インスタンス化 されたオブジェクトへの参照を取得および格納するには、標準の PowerBuilder プログラミング テクニックを使用します。 クラスのスクリプトに関する情報の取得 この節に含まれるコード フラグメントでは、cd_windef という ClassDefinition オブジェクトからスクリプト情報を取得する方法を説明 します。 cd_windef に値を割り当てる例については、61 ページの「クラス定義オ ブジェクトの取得」を参照してください。 スクリプトのリスト ScriptList 配列には、あるクラスに定義されているすべての関数とイベ ントの ScriptDefinition オブジェクトがあります。関数が多重定義され た場合には、その関数は異なる引数リストを付けて配列内に 1 回以上 現われます。関数またはイベントが階層構造内の複数のレベルにコー ドを持っている場合には、その関数またはイベントは、コーディング されたバージョンごとに配列に現れます。 次の例では、ScriptList 配列をループして、スクリプト名のリストを作 成します。すべてのオブジェクトが PowerObject から継承されるため、 すべてのオブジェクトには、ClassName や PostEvent など、いくつかの 標準関数があります。 64 PowerBuilder 第4章 PowerBuilder のクラス定義に関する情報の取得 string s, lineend integer li ScriptDefinition sd lineend = "~r~n" FOR li = 1 to UpperBound(cd_windef.ScriptList) sd = cd_windef.ScriptList[li] s = s + sd.Name + " " + lineend NEXT mle_1.Text = s 次の例では、前の例を拡張して、ScriptDefinition オブジェクト内のさ まざまなプロパティにアクセスします。この例では、スクリプトが関 数であるかイベントであるか、ローカルでスクリプト作成されたかど うか、戻りデータ型と引数の種類、および引数の渡し方をレポートし ます。 string s, lineend integer li, lis, li_bound ScriptDefinition sd lineend = "~r~n" FOR li = 1 to UpperBound(cd_windef.ScriptList) sd = cd_windef.ScriptList[li] s = s + sd.Name + " " CHOOSE CASE sd.Kind CASE ScriptEvent! // イベントには、コードの定義場所について // 関連するプロパティが 3 つあります。 s = s + "Event, " IF sd.IsScripted = TRUE then s = s + "scripted, " END If IF sd.IsLocallyScripted = TRUE THEN s = s + "local, " END IF IF sd.IsLocallyDefined = TRUE THEN s = s + "local def," END IF CASE ScriptFunction! // 関数には、コードの定義場所について // 関連するプロパティが 1 つあります。 s = s + "Function, " IF sd.IsLocallyScripted = TRUE THEN s = s + "local, " アプリケーション テクニック 65 クラス定義の調査 END IF END CHOOSE s = s + "returns " + & sd.ReturnType.DataTypeOf + "; " s = s + "Args: " li_bound = UpperBound(sd.ArgumentList) IF li_bound = 0 THEN s = s + "None" FOR lis = 1 to li_bound CHOOSE CASE sd.ArgumentList[lis]. & CallingConvention CASE ByReferenceArgument! s = s + "REF " CASE ByValueArgument! s = s + "VAL " CASE ReadOnlyArgument! s = s + "READONLY " CASE ELSE s = s + "BUILTIN " END CHOOSE s = s + sd.ArgumentList[lis].Name + ", " NEXT s = s + lineend NEXT mle_1.text = s 継承階層内のコードの位置 IsLocallyScripted プロパティをチェックすれ ば、スクリプトが継承階層内のクラス独自のレベルにコードを持って いるかどうかを確認できます。Ancestor プロパティを介して継承階層 を逆向きにたどると、スクリプトのコードがどこにあるかを見つける ことができます。 次の例では、まず ClassDefinition cd_windef に関連付けられたクラスの スクリプトを調べます。スクリプトのコードがこのレベルに定義され ていることがわかると、そのスクリプト名はドロップダウン リスト ボックスに追加されます。また、ScriptList 配列におけるスクリプトの 位置は、インスタンス変数 ii_localscript_idx に保存されます。ドロップ ダウン リストボックスはソートされないため、リスト内の位置と配列 内の位置は同期しています。 integer li_pos, li FOR li = 1 to UpperBound(cd_windef.ScriptList) 66 PowerBuilder 第4章 PowerBuilder のクラス定義に関する情報の取得 IF cd_windef.ScriptList[li].IsLocallyScripted & = TRUE THEN li_pos = ddlb_localscripts.AddItem( & cd_windef.ScriptList[li].Name) ii_localscript_idx[li_pos] = li END IF NEXT 関数シグネチャの照合 クラスに多重定義された関数がある場合には、FindMatchingFunction を 呼び出すことによって、特定の引数リストに対して呼び出される関数 を調べることができます。 一例として、『PowerScript リファレンス』マニュアルの FindMatchingFunction を参照してください。 変数に関する情報の取得 この節に含まれるコード フラグメントでは、cd_windef という ClassDefinition オブジェクトから変数に関する情報を取得する方法を説 明します。cd_windef に値を割り当てる例については、61 ページの「ク ラス定義オブジェクトの取得」を参照してください。 クラスに関連付けられた変数は、ClassDefinition オブ ジェクトの VariableList 配列に登録されます。この配列を調べると、明 示的に定義した変数に加えて、インスタンス変数である PowerBuilder オブジェクト プロパティとネスティッド オブジェクトも見つかりま す。 変数のリスト 次の例では、VariableList 配列をループして、変数名のリストを作成し ます。最初に PowerBuilder プロパティが現われ、続いてネスティッド オブジェクト、独自のインスタンス、および共有変数が現われます。 string s, lineend integer li VariableDefinition vard lineend = "~r~n" FOR li = 1 to UpperBound(cd_windef.VariableList) vard = cd_windef.VariableList[li] s = s + vard.Name + lineend NEXT mle_1.Text = s アプリケーション テクニック 67 クラス定義の調査 変数に関する詳細 次の例では、VariableList 配列に含まれる各変数のプロパティを調べて、 そのデータ型、基数、およびグローバル、共有、またはインスタンス の区別をレポートします。また、インスタンス変数が先祖宣言を上書 きするかどうかもチェックします。 string s integer li VariableDefinition vard lineend = "~r~n" FOR li = 1 to UpperBound(cd_windef.VariableList) vard = cd_windef.VariableList[li] s = s + vard.Name + ", " s = s + vard.TypeInfo.DataTypeOf CHOOSE CASE vard.Cardinality.Cardinality CASE ScalarType! s = s + ", scalar" CASE UnboundedArray!, BoundedArray! s = s + ", array" END CHOOSE CHOOSE CASE vard.Kind CASE VariableGlobal! s = s + ", global" CASE VariableShared! s = s + ", shared" CASE VariableInstance! s = s + ", instance" IF vard.OverridesAncestorValue = TRUE THEN s = s + ", override" END IF END CHOOSE s = s + lineend NEXT mle_1.text = s 68 PowerBuilder 第 3 部 ユーザ インタフェース テクニック 第 3 部では、PowerBuilder によるアプリケーション開発 において、ユーザ インタフェース機能を実現するための テクニックについて説明します。MDI アプリケーション の構築、ドラッグ アンド ドロップ機能の使い方、オンラ イン ヘルプ機能などについて説明します。 第 5 章 MDI アプリケーションの構築 この章について この章では、PowerBuilder におけるマルチ ドキュメント インタ フェース(MDI)アプリケーションの構築方法について説明しま す。 内容 項目 MDI について MDI フレーム ウィンドウの作成 シートの使い方 マイクロヘルプの提供 MDI アプリケーションにおけるツールバーの使い方 クライアント領域のサイズ設定 MDI アプリケーションにおけるキーボード操作について ページ 71 74 75 77 78 84 87 MDI について マルチ ドキュメント インタフェース(MDI)は、1 つのウィンド ウ内で複数の(シートと呼ばれる)ウィンドウを開いたり、シー ト間を自由に移動したりすることができるアプリケーション形式 です。MDI アプリケーションを構築する場合は、MDI フレームと いう種類のウィンドウを定義し、そのフレーム内でほかのウィン ドウをシートとして開きます。 大規模な Windows アプリケーションのほとんどは MDI 形式で作 成されています。たとえば、PowerBuilder も MDI アプリケーショ ンです。PowerBuilder ウィンドウがフレーム、ペインタがシート です。 エンド ユーザに複数のウィンドウを開かせたり、ウィンドウ間を 簡単に移動させたりしたい場合には、MDI 形式でアプリケーショ ンを構築します。 アプリケーション テクニック 71 MDI について テンプレート アプリケーション機能の使い方 新規のアプリケーションを作成した場合には、アプリケーション ウィ ザードを選択してから、SDI または MDI アプリケーションを作成する よう選択できます。MDI アプリケーションを選択した場合には、シー トを開くまたは閉じるなどのウィンドウ操作を行う関数をすべて備え た MDI フレーム、シート マネージャ オブジェクトといくつかのシー ト、バージョン情報ダイアログボックス、メニュー、ツールバー、お よびスクリプトを含む MDI アプリケーションのシェルが生成されま す。 MDI フレーム ウィン ドウ MDI フレーム ウィンドウは、メニュー バー、フレーム、クライアン ト領域、シートなどの複数の要素から構成されるウィンドウです。通 常、MDI フレーム ウィンドウの構成要素には上記のほかにステータス バーが含まれ、この領域にはマイクロヘルプ(現在選択しているメ ニュー項目や操作についての簡単な説明)が表示されます。 フレーム MDI フレームは、MDI ウィンドウの外枠領域で、クライアント領域を 含みます。MDI フレームには、以下の 2 種類があります。 72 • 標準フレーム • カスタム フレーム PowerBuilder 第5章 MDI アプリケーションの構築 標準 MDI フレーム ウィンドウには、メニュー バーと、 通常は、マイクロヘルプが表示されるステータス バーがあります。 シートが開かれていないときは、クライアント領域は空白になります。 シートは、独自のメニュー、または MDI フレームから継承したメ ニューを持つことができます。MDI アプリケーションのメニュー バー は、常にフレーム上に表示され、シート上に表示されることはありま せん。通常、メニュー バーには、現在開かれているすべてのウィンド ウをリスト表示するメニュー項目があり、それらのウィンドウを並べ て表示、カスケード表示、または重ねて表示できます。 標準フレーム カスタム フレーム 標準フレームと同様に、カスタム フレーム ウィン ドウにも、通常、メニュー バーとステータス バーがあります。標準フ レームとカスタム フレームの違いはクライアント領域にあります。標 準フレームの場合は、クライアント領域には開いているシートだけが 表示されますが、カスタム フレームの場合は、シートだけではなくボ タンやスタティック テキストなど、ほかのオブジェクトも表示できま す。たとえば、テキストが表示されたボタンをクライアント領域に配 置できます。 クライアント領域 標準フレーム ウィンドウでは、PowerBuilder が自動的にクライアント 領域のサイズを設定し、クライアント領域内でシートが開かれ表示さ れるようになっています。クライアント領域にオブジェクトがあるカ スタム フレーム ウィンドウでは、開発者自身がクライアント領域のサ イズを設定しなければなりません。クライアント領域のサイズが正し く設定されなかった場合、シートを開いても表示されないことがあり ます。 MDI_1 コントロール 開発者が MDI フレーム ウィンドウを作成する と、フレーム ウィンドウのクライアント領域を識別するために、MDI_1 という名前のコントロールが PowerBuilder によって作成されます。標 準フレームでは PowerBuilder が自動的に MDI_1 を管理します。カスタ ム フレームでは、開発者がフレームの Resize イベントに対してスクリ プトを記述し MDI_1 のサイズを設定します。 MDI_1 に関する情報の表示 MDI_1 のプロパティと関数をブラウザで参照できます。MDI 型のウィ ンドウを作成し、ブラウザで[ウィンドウ]タブを選択します。MDI フレーム ウィンドウを選択し、ポップアップ メニューから[この下を すべて表示]を選択します。すると、MDI_1 がウィンドウ コントロー ルとして表示されるため、そのプロパティや関数などをブラウザの右 側ペインで調べることができます。 アプリケーション テクニック 73 MDI フレーム ウィンドウの作成 MDI シート シートは、MDI フレームのクライアント領域で開くことができるウィ ンドウです。MDI フレーム以外のあらゆる種類のウィンドウが MDI ア プリケーションのシートとして使用できます。シートを開くには OpenSheet 関数か OpenSheetWithParm 関数を使用します。 ツールバー MDI アプリケーションにおいて、エンド ユーザにツールバーを提供し たいことがあります。PowerBuilder では、現行メニューを基にしたツー ルバーを自動的に作成し、管理できます。また、 (通常は、ユーザ オ ブジェクトとして)独自のカスタム ツールバーを作成し、クライアン ト領域のサイズを再設定することもできます。 ツールバーの提供については、 『ユーザーズ ガイド』マニュアルの「メ ニューとツールバーでの作業」の章を参照してください。クライアン ト領域のサイズ設定の詳細については、84 ページの「クライアント領 域のサイズ設定」を参照してください。 MDI フレーム ウィンドウの作成 PowerBuilder で新規のウィンドウを作成するとき、そのデフォルトの ウィンドウの種類はメインです。 [全般]プロパティ ページで、 [mdi!] または[mdihelp!]を選択して、ウィンドウを MDI フレーム ウィンド ウに変更します。 メニューの使い方 ウィンドウの種類を MDI に変更した場合には、メニューとフレームを 関連付ける必要があります。一般に、メニューを使用すれば、フレー ム内のシートを開いたり、すべてのシートが閉じられている場合には フレームを閉じたりすることができます。 メニューとシートについて シートごとに独自のメニューを持つことができますが、必ずしもそう する必要はありません。メニューを持たないシートが開かれると、フ レームのメニューが使用されます。 74 PowerBuilder 第5章 MDI アプリケーションの構築 シートの使い方 MDI フレーム ウィンドウでは、ユーザは複数のウィンドウ(または シート)を開いて作業を行うことができます。たとえば、電子メール システムの場合、MDI フレームは複数のシートを持ち、それぞれの シートにおいて、メッセージを作成して送信したり、メッセージを読 んで返答したりすることができます。すべてのシートを同時に開くこ とができ、ユーザはシート間を移動して各シートで異なる作業を行う ことができます。 メニューとシートについて シートごとに独自のメニューを持つことができますが、必ずしもそう する必要はありません。メニューを持たないシートが開かれると、フ レームのメニューが使用されます。 シートを開く MDI フレームのクライアント領域でシートを開くには、OpenSheet 関 数を使用します。OpenSheet 関数は、メニュー項目、別のシート、また はフレーム内の任意のオブジェクトのイベントに対するスクリプトで 呼び出します。 OpenSheet 関数の詳細については、 『PowerScript リファレンス』マニュ アルを参照してください。 ウィンドウのインスタンスを開く MDI アプリケーションでは、エンド ユーザは特定の Window 型のイン スタンスを複数開くことができます。たとえば、受発注情報を管理す るアプリケーションでは、複数の異なる受注情報を同時に見ることが できます。個々の受注情報は、それぞれ個別のウィンドウ(シート) に表示されます。 アプリケーション テクニック 75 シートの使い方 クライアント領域でシートを開くと、ドロップダウン メニューの一番 下にそのウィンドウ(シート)のタイトルを表示できます。以下の図 のメニューでは、開いている 2 つのシート名が表示されています。 開いているシートの一 覧表示 ❖ ドロップダウン メニューに開いているシート名を表示するには • 関数を呼び出した時に開いているシートを一覧したい メニュー バー項目の番号を指定します。通常、[ウィンドウ]メ ニューに開いているシート名を表示します。ファイル、編集、ウィ ンドウ、ヘルプの順番に 4 つの項目を持つメニュー バーでは、番 号 3 で[ウィンドウ]メニューを指定します。 OpenSheet 一度に 9 つ以上のシートが開いている場合、最初の 9 シートの名前は 表示されますが、10 番目以降は[その他のウィンドウ]と表示されま す。10 番目以降のシートを表示するには、 [その他のウィンドウ]を 選択します。 シートの整列 76 ArrangeSheets 関数を使用して、MDI フレーム内で開いてるシートの並 べ方を変更することができます。 PowerBuilder 第5章 MDI アプリケーションの構築 シートの並び方の変更 エンド ユーザがシートの並べ方を変更できるように、メニュー項目 (通常は[ウィンドウ]メニューのドロップダウンメニュー項目)を作 成します。エンド ユーザがメニュー項目を選択した時に、ArrangeSheets 関数を使用してシートを並べ替えます。 シートの最大表示 シートを閉じる MDI ウィンドウに開かれているシートがコントロール メニューを持 つ場合、エンド ユーザはそのシートを最大表示することができます。 アクティブなシートが最大表示された場合の動作は以下のようになり ます。 • ほかのシートがアクティブになると、そのアクティブになった シートが最大表示される。アクティブになったシートは、直前の シートの状態を継承する • 新しいシートを開くと、現行シートは直前のサイズに戻り、新し いシートはオリジナルのサイズのまま表示される アクティブなシート 〔Ctrl〕+〔F4〕を押すと、アクティブなウィンド ウ(シート)が閉じます。メニューの親ウィンドウ(シート)を閉じ るスクリプトをメニュー項目に記述することもできます。この場合、 メニューはフレームではなくシートに関連付けます。たとえば、次の ようにスクリプトを記述します。 Close(ParentWindow) すべてのシート 〔Alt〕+〔F4〕を押すと、すべてのシートを閉じてアプ リケーションを終了することができます。開いているシートを配列に 保持しておいて、ループによってすべてのシートを閉じるようにスク リプトを記述することもできます。 マイクロヘルプの提供 MDI では、フレームの底辺に位置するステータス バーにマイクロヘル プを用意して、エンド ユーザに対して情報を提供することができま す。たとえば、エンド ユーザがメニュー項目を選択するときに、ス テータス バーに選択されたメニュー項目の説明が表示されます。 開発者は、メニュー項目とカスタム フレーム ウィンドウ内のコント ロールに対してマイクロヘルプを定義できます。 アプリケーション テクニック 77 MDI アプリケーションにおけるツールバーの使い方 メニュー項目に対する マイクロヘルプ メニュー項目に関連付けるマイクロヘルプのテキストは、メニュー ペ インタの[マイクロヘルプ]テキストボックスで指定します。メニュー 項 目 の ス ク リ プ ト で マ イ ク ロ ヘ ル プ の テ キ ス ト を 変 更 す る に は、 SetMicroHelp 関数を使用します。 コントロールに対する マイクロヘルプ コントロールの Tag プロパティを使用して、カスタム フレーム ウィン ドウのコントロールにマイクロヘルプを関連付けることができます。 たとえば、クライアント領域に[印刷]ボタンを配置したとします。 こ の ボ タ ン に 対 す る マ イ ク ロ ヘ ル プ を 表 示 す る に は、ボ タ ン の GetFocus イベントに対してスクリプトを記述します。GetFocus イベン トにおいて、Tag プロパティにマイクロヘルプで表示したいテキスト を設定し、SetMicroHelp 関数を使用してそのテキストをマイクロヘルプ に表示します。たとえば、次のようになります。 cb_print.Tag=" 現行ジョブの情報を印刷します " w_genapp_frame.SetMicroHelp(This.Tag) コントロールのプロパティ シートでコントロールの Tag プロパティを 設定することもできます。 LoseFocus イベントで、マイクロヘルプの表示を元に戻します。 w_genapp_frame.SetMicroHelp("Ready") MDI アプリケーションにおけるツールバーの使い方 この節では、ツールバーの動作のカスタマイズ、ツールバーの設定の 保存と復元を行うためのテクニックについて説明します。メニューと ツールバー を定義して使用する方法については、 『ユーザーズ ガイド』 マニュアルを参照してください。 ツールバーの動作のカスタマイズ ツールバー ボタンの 使用不可 ツールバー ボタンを使用不可にするには、そのボタンに関連付けられ ているメニュー項目を使用不可にする必要があります。メニュー項目 を使用不可にすると、自動的にツールバー ボタンも使用不可になりま す。 メニュー項目を使用不可にするには、メニュー項目の Enabled プロパ ティに FALSE を設定します。 m_test.m_file.m_new.Enabled = FALSE 78 PowerBuilder 第5章 ツールバー ボタンの 非表示 MDI アプリケーションの構築 メニュー項目を非表示にするには、メニュー項目の Visible プロパティ に FALSE を設定します。 m_test.m_file.m_open.Visible = FALSE メニュー項目を非表示にしても、そのツールバー ボタンは非表示また は使用不可になりません。ツールバー ボタンを非表示にするには、メ ニュー項目の ToolbarItemVisible プロパティに FALSE を設定する必要 があります。 m_test.m_file.m_open.ToolBarItemVisible = FALSE ツールバー ボタンを非表示にしても、ドロップダウンまたはカスケー ドのメニュー項目における下位レベルのツールバー ボタンは、非表示 または使用不可にはなりません。下位レベルのボタンは、個別に非表 示または使用不可にする必要があります。 ドロップダウン ツー ルバーにおける現行の ボタンの設定 エンド ユーザがドロップダウン ツールバーのツールバー ボタンをク リックすると、PowerBuilder は選択されたボタンを現行のボタンとし ます。このようにすれば、エンド ユーザが繰り返しそのボタンを使用 す る の が 容 易 に な り ま す。さ ら に、MenuCascade オ ブ ジ ェ ク ト の CurrentItem プロパティを設定することによって、スクリプトで特定の ボタンを現行のボタンとすることができます。たとえば、[ファイル] メニューの[新規作成]メニュー項目に対応するツールバー ボタンを 現行のボタンとして設定するには、以下のスクリプトを実行します。 m_test.m_file.currentitem = m_test.m_file.m_new このスクリプトを正常に実行するためには、メニュー ペインタで、 [ファイル]メニューのオブジェクト データ型として MenuCascade を 指定する必要があります。 ツールバーの移動の確 認 ツールバーが MDI フレーム ウィンドウで移動すると、ウィンドウの ToolBarMoved イベントが起動されます。このイベントに対するスクリ プトでは、どのツールバーが移動したかを確認して、処理を実行する こ と が で き ま す。フ レ ー ム バ ー ま た は シ ー ト バ ー を 移 動 す る と、 ToolbarMoved イベントが起動されて、Message.WordParm プロパティと Message.LongParm プロパティにどのツールバーが移動したかを示す値 が設定されます。 アプリケーション テクニック 79 MDI アプリケーションにおけるツールバーの使い方 表 5-1: Message.WordParm プロパティと Message.LongParm プロパ ティの値 プロパティ Message.WordParm Message.LongParm 値 0 1 0 1 2 3 4 意味 フレームバーが移動された シートバーが移動された 左へ移動された 上へ移動された 右へ移動された 下へ移動された 浮動に設定された ツールバー設定の保存と復元 ツールバーの設定に関する情報を検索したり更新したりする関数を使 用すれば、現行のツールバーの設定の保存と復元ができます。 GetToolbar 関数と GetToolbarPos 関数を使用すれば、現行のツールバー の設定を取得できます。SetToolbar 関数と SetToolbarPos 関数を使用すれ ば、ツールバーの設定を変更できます。ツールバーの表示位置が浮動 か固定かによって、GetToolbarPos 関数と SetToolbarPos 関数は、使用す る構文が異なります。 浮動ツールバー 浮動ツールバーの表示位置は、その x 座標と y 座標によって決まりま す。浮動ツールバーのサイズは、その幅と高さによって決まります。 GetToolbarPos 関数と SetToolbarPos 関数を使用して、浮動ツールバーの 位置の取得と設定を行う場合は、x 座標、y 座標、幅、高さの引数が必 要です。 固定ツールバー 固定ツールバーの表示位置は、配置された行とその行の開始位置から のオフセットによって決まります。上端または下端に配置されたツー ルバーの場合、オフセットは左端から算出されます。左端または右端 に配置されたツールバーの場合、オフセットは上端から算出されます。 デフォルトでは、ツールバーが配置される行は、ツールバーのインデッ クスと同じ位置になります。ウィンドウと異なる枠線でツールバーを 配置する場合、その配置する位置によって、行は変更されることがあ ります。 GetToolbarPos 関数と SetToolbarPos 関数を使用して、固定ツールバーの 位置の取得と設定を行う場合は、行とオフセットの引数が必要です。 80 PowerBuilder 第5章 例 MDI アプリケーションの構築 以下の例では、ツールバーの設定を管理するカスタム ユーザ オブジェ クトの使用方法を示します。ユーザ オブジェクトには、2 つの関数が あります。1 つは現行の設定を保存するための関数、もう 1 つは後で 設定を復元するための関数です。ツールバーの設定の保存と復元をす るための処理は、ウィンドウではなくユーザ オブジェクトで行うの で、このユーザ オブジェクトを使用すればどのウィンドウにおいても 簡単にツールバーの設定の保存と復元ができます。 例では、固定ツールバーと浮動ツールバーの両方をサポートします。 ウィンドウの Open イベントに対するスクリプト ウィンドウが開かれる と、初期設定ファイル toolbar.ini からツールバーの設定を復元します。 設定を復元するため、カスタム ユーザ オブジェクト u_toolbar のインス タンスを作成し、ユーザ定義関数 Restore を呼び出します。 // ツールバー NVO を作成します。 u_toolbar = create u_toolbar // ツールバーの表示位置を復元します。 u_toolbar.Restore(this,"toolbar.ini", this.ClassName()) ウィンドウの Close イベントに対するスクリプト ウ ィ ン ド ウ が 閉 じ る と、ユーザ定義関数 Save を呼び出して、ツールバーの設定を保存しま す。設定を保存した後は、ユーザ オブジェクトのインスタンスを破棄 します。 // ツールバーの設定を保存します。 stateu_toolbar.Save(this, "toolbar.ini", ClassName()) // NVOdestroy u_toolber ツールバーを破棄します。 Save 関数のスクリプト Save 関数には、3 つの引数があります。 • Win – ウィンドウの参照 • File – 設定を保存するファイルの名前 • Section – 設定を保存するファイル内のセクション名 Save 関数では、GetToolbar 関数と GetToolbarPos 関数を使用して、現行 のツールバーの設定を取得します。初期設定ファイルに設定を記述す るには SetProfileString 関数を使用します。 Save 関数は、1 つのメニューにおける複数のツールバーを処理できま す。そのため、ツールバーのインデックスを使用して、各ツールバー の情報を管理します。 // ウィンドウのツールバーの設定を保存します。 integer index, row, offset, x, y, w, h boolean visible string visstring, alignstring, title toolbaralignment alignmentFOR index = 1 to 16 アプリケーション テクニック 81 MDI アプリケーションにおけるツールバーの使い方 // ツールバーの属性を取得します。 IF win.GetToolbar(index, visible, alignment, & title)= 1 THEN // 変数 visible の値を String 型に変換します。 CHOOSE CASE visible CASE true visstring = "true" CASE false visstring = "false" END CHOOSE // 変数 alignment の値を String 型に変換します。 CHOOSE CASE alignment CASE AlignAtLeft! alignstring = "left" CASE AlignAtTop! alignstring = "top" CASE AlignAtRight! alignstring = "right" CASE AlignAtBottom! alignstring = "bottom" CASE Floating! alignstring = "floating" END CHOOSE // 基本的な属性を保存します。 SetProfileString(file, section + & String(index), "visible", visstring) SetProfileString(file, section + & String(index), "alignment", alignstring) SetProfileString(file, section + & String(index), "title", title) // 固定ツールバーの表示位置を保存します。 win.GetToolbarPos(index, row, offset) SetProfileString(file, section + & String(index), "row", String(row)) SetProfileString(file, section + & String(index), "offset", String(offset)) // 浮動ツールバーの表示位置を保存します。 win.GetToolbarPos(index, x, y, w, h) SetProfileString(file, section + & String(index), "x", String(x)) SetProfileString(file, section + & String(index), "y", String(y)) SetProfileString(file, section + & 82 PowerBuilder 第5章 MDI アプリケーションの構築 String(index), "w", String(w)) SetProfileString(file, section + & String(index), "h", String(h)) END IF NEXT Restore 関数のスクリプト Restore 関数にも、Save 関数と同じ 3 つの引 数があります。Restore 関数は、初期設定ファイルからツールバーの設 定を取得するため、ProfileString 関数を使用します。設定を取得したら、 SetToolbar 関数と SetToolbarPos 関数を使用して、ツールバーの設定を復 元します。 Save 関数と同じように、Restore 関数も 1 つのメニューにおける複数の ツールバーを処理できます。そのため、ツールバーのインデックスを 使用して、各ツールバーの情報を管理します。 // ウィンドウのツールバーの設定を復元します。 integer index, row, offset, x, y, w, h boolean visible string visstring, alignstring, title toolbaralignment alignment FOR index = 1 to 16 // ツールバーの属性を取得します。 IF win.GetToolbar(index, visible, alignment, & title)= 1 THEN // .ini ファイルから // ツールバーの設定情報を取得します。 visstring = ProfileString(file, section + & String(index), "visible", "") IF visstring > "" THEN // ツールバーのすべての設定情報を取得します。 alignstring = ProfileString(file, section + & String(index), "alignment", "left") title = ProfileString(file, section + & String(index), "title", "(Untitled)") row = Integer(ProfileString(file, section + & String(index), "row", "1")) offset = Integer(ProfileString(file, & section + String(index), "offset", "0")) x = Integer(ProfileString(file, section + & String(index), "x", "0")) y = Integer(ProfileString(file, section + & String(index), "y", "0")) w = Integer(ProfileString(file, section + & String(index), "w", "0")) アプリケーション テクニック 83 クライアント領域のサイズ設定 h = Integer(ProfileString(file, section + String(index), "h", "0")) & // 変数 visstring の値を Boolean 型に変換します。 CHOOSE CASE visstring CASE "true" visible = true CASE "false" visible = false END CHOOSE // 変数 Alignstring の値を // toolbaralignment カタログ データ型に変換します。 CHOOSE CASE alignstring CASE "left" alignment = AlignAtLeft! CASE "top" alignment = AlignAtTop! CASE "right" alignment = AlignAtRight! CASE "bottom" alignment = AlignAtBottom! CASE "floating" alignment = Floating! END CHOOSE // 新しい表示位置を設定します。 win.SetToolbar(index, visible, alignment, title) win.SetToolbarPos(index, row, offset, false) win.SetToolbarPos(index, x, y, w, h) END IF END IF NEXT クライアント領域のサイズ設定 PowerBuilder は、自動的に標準 MDI フレーム ウィンドウのクライアン ト領域のサイズを設定し、クライアント領域内にシートを開いて表示 します。また、前節でも説明したように、メニュー項目に対してツー ルバーを定義した場合も、クライアント領域のサイズは自動的に再設 定されます。 84 PowerBuilder 第5章 MDI アプリケーションの構築 カスタム MDI フレーム ウィンドウでは、クライアント領域にはシー トが開かれるほかにコントロールが配置されますが、PowerBuilder は クライアント領域のサイズを設定しないので、開発者がサイズ設定を 行わなければなりません。クライアント領域のサイズが適切に設定さ れていないと、シートが開いても表示されなかったり、クライアント 領域からはみ出した部分が切り取られて表示されたりします。 カスタム MDI フレーム ウィンドウでツールバーを使用する場合は、ク ライアント領域に配置したコントロールが、クライアント領域の境界 から十分に離れていることを確認してください。ウィンドウを表示し たときに、ツールバーがコントロールの上に表示されないようにして ください。 表示されないシートがある場合に現われるスクロールバー ウィンドウを定義する際に HScrollBar プロパティと VScrollBar プロパ ティを設定すると、表示されないシートがある場合にスクロールバー が現れます。これはシート内のすべての情報が表示されるという意味 ではありません。エンド ユーザは、スクロールバーをスクロールして 情報を表示できます。 カスタム MDI フレーム ウィンドウを作成すると、MDI_1 という名前の コントロールが作成され、フレームのクライアント領域を識別するた めに使用されます。AutoScript を有効にした場合には、フレームのスク リプトを作成すると、オートスクリプト ポップアップ ウィンドウのオ ブジェクト リストに MDI_1 が表示されます。 ❖ フレームが開かれるとき、またはフレームのサイズが変更されるときに、ク ライアント領域のサイズを設定または変更するには • アプリケーション テクニック フレームの Open または Resize イベントに対してスクリプトを記 述します。 • フレームのサイズを決定する • クライアント領域(MDI_1)のサイズを適切に設定する 85 クライアント領域のサイズ設定 たとえば、以下のスクリプトは、フレーム w_genapp_frame のクライア ント領域のサイズを設定します。このフレームでは、メニューのすぐ 下にボタンが配置され、フレームの一番下にはマイクロヘルプが表示 されるものとします。 int li_width, li_height // フレームにおけるワークスペースの幅と高さを取得します。 // // MDI ツールバーを表示する場合は、 // WorkSpaceWidth 関数と WorkSpaceHeight 関数が返した // ワークスペースのサイズからツールバーの // サイズ分を差し引くことに注意してください。 // この調整方法については、後で説明します。 // li_width = w_genapp_frame.WorkSpaceWidth() li_height = w_genapp_frame.WorkSpaceHeight() // 次に、以下の処理を行うことによって、 // クライアント領域の高さを決めます。 // // 1) WorkSpaceHeight 値からコントロールの高さと // コントロールの y 座標を減算します。 // つまり、この値は、ツールバーがない場合の // フレームにおけるワークスペースの上端と // コントロールの上端との距離 // になります。 86 PowerBuilder 第5章 MDI アプリケーションの構築 // // 2) 次の減算を行います。 フレームのマイクロヘルプ バーが // ある場合は、その高さを減算します。 // // 3) 次の加算を行います。表示するツールバーの高さを加算します。 // 最初に WorkSpaceHeight 関数が返した値からは、 // ツールバーの高さが差し引かれているからです。 // 最終的にツールバーの高さは、WorkspaceY 関数が返す // Y 座標と同じになります。 li_height = li_height - (cb_print.y + cb_print.height) li_height = li_height - MDI_1.MicroHelpHeight li_height = li_height + WorkspaceY() // 次に、ワーク スペースのコントロールの真下からクライアント領 // 域が始まるように移動します。 mdi_1.Move (WorkspaceX (), cb_print.y + cb_print.height) & // 最後に、以前に計算した幅と高さに基づいて、 // クライアント領域のサイズを変更します。 mdi_1.Resize (li_width, li_height) MicroHelpHeight プロパティについて MicroHelpHeight プロパティは MDI_1 のプロパティで、ウィンドウの種 類に MDI フレームを選択したときに設定されます。MDI フレームを選 択した場合、マイクロヘルプは表示されず MicroHelpHeight プロパティ は 0 になります。マイクロヘルプ付き MDI フレームを選択した場合、 MicroHelpHeight プロパティの値はマイクロヘルプの高さになります。 MDI アプリケーションにおけるキーボード操作について PowerBuilder MDI アプリケーションでは、矢印キーとショートカット キーが自動的にサポートされます。 アプリケーション テクニック 87 MDI アプリケーションにおけるキーボード操作について 矢印キー MDI フレームでは、エンド ユーザが矢印キーを押したときのポインタ の動きは、キーが押されたときにフォーカスされていた場所によって 異なります。 表 5-2: 矢印キーによるフォーカスの移動 キー 〔←〕 フォーカスの位置 メニュー バー 〔→〕 最初(左端)のメニュー バー 項目 アクティブ シートのコント ロール メニュー フレームのコントロール メ ニュー メニュー バー 最後(右端)のメニュー バー 〔↓〕 〔↑〕 88 フレームのコントロール メ ニュー アクティブ シートのコント ロール メニュー ドロップダウン メニューまた はカスケード メニュー ドロップダウン メニューやカ スケード メニューの最後のメ ニュー項目 ドロップダウン メニューまた はカスケード メニュー ドロップダウン メニューやカ スケード メニューの最初のメ ニュー項目 フォーカスの移動先 フォーカスがあるメニュー項目 の左側のメニュー項目 アクティブ シートのコントロー ル メニュー フレームのコントロール メ ニュー 最後(右端)のメニュー バー フォーカスがあるメニュー項目 の右側のメニュー項目 フレームのコントロール メ ニュー アクティブ シートのコントロー ル メニュー メニュー バーの最初(左端)の 項目 現行の項目の下位のメニュー項 目 そのメニューの最初の項目 現行の項目の上位のメニュー項 目 そのメニューの最後の項目 PowerBuilder 第5章 ショートカット キー MDI アプリケーションの構築 PowerBuilder では、すべての MDI フレームに対して以下の 2 つの ショートカット キーが割り当てられています。 表 5-3: MDI フレームのショートカット キー キー 〔Ctrl〕+〔F4〕 〔Ctrl〕+〔F6〕 アプリケーション テクニック 機能 アクティブなシートを閉じ、次のシートをアクティブにし ます。次にアクティブになるのは、閉じられたシートの直 前にアクティブになっていたシートです。 直前にアクティブになっていたシートをアクティブにし ます。 89 MDI アプリケーションにおけるキーボード操作について 90 PowerBuilder 第 6 章 ウィンドウ インスタンスの管理 この章について この章では、同じウィンドウの複数のウィンドウ インスタンスを 管理する方法について説明します。 内容 項目 ウィンドウ インスタンスについて ウィンドウ インスタンスの宣言 ウィンドウ配列の使い方 子孫オブジェクトのエンティティの参照 ページ 91 93 94 97 ウィンドウ インスタンスについて アプリケーションを構築するとき、構造は同じで、データ値が異 なるウィンドウをいくつか表示したいことがあります。 たとえば、ウィンドウ w_employee の複数のコピー(インスタンス) を開いて、同時に複数の従業員情報を表示するという場合です。 これには、まず、PowerBuilder がどのようにウィンドウ定義を格 納するかを理解する必要があります。 PowerBuilder によるウィ ンドウ定義の格納方法 ウィンドウを保存するとき、PowerBuilder は、以下の 2 つのエン ティティをライブラリに生成します。 • 新しいデータ型 データ型名はウィンドウ名と同じ たとえば、w_employee という名前のウィンドウを保存すると、 PowerBuilder は内部的に w_employee という名前のデータ型を 作成します。 • 新しいデータ型のグローバル変数 グローバル変数名はウィンド ウ名と同じ たとえば、ウィンドウ w_employee を保存すると、w_employee 型 で w_employee という名前のグローバル変数も暗黙的に定義さ れます。 アプリケーション テクニック 91 ウィンドウ インスタンスについて 次のように宣言するのと同じです。 図 6-1: 変数宣言 データ型や変数の名前を複製することにより、PowerBuilder の新規 ユーザは、データ型のコンセプトを気にせずに、変数を使用してウィ ンドウに簡単にアクセスできます。 ウィンドウを開くとき に行われる処理 ウィンドウを開くには、次のように Open 関数を使用します。 Open(w_employee) これによって実際は、データ型 w_employee のインスタンスが作成さ れ、グローバル変数 w_employee への参照が割り当てられます。 すでに開いているウィンドウを開くと、PowerBuilder は単に既存の ウィンドウをアクティブにするだけで、新たにウィンドウを開きませ ん。たとえば、次のスクリプトをコマンドボタン コントロールの Clicked イベントに記述したとします。 Open(w_employee) このボタンを何回クリックしても、ウィンドウ w_employee は 1 つしか 開きません。このウィンドウは、グローバル変数 w_employee にポイン トされます。 ウィンドウの複数のインスタンスを開くには、そのウィンドウの種類 をデータ型として変数を宣言します。 92 PowerBuilder 第6章 ウィンドウ インスタンスの管理 ウィンドウ インスタンスの宣言 ウィンドウは、実際はデータ型であるため、Integer 型や String 型など の変数を宣言するのと同様に、ウィンドウの種類をデータ型として変 数を宣言できます。そうすれば、スクリプトでそれらの変数を参照で きます。 例 w_employee mywin w_employee 型の変数 mywin を宣言します。 変数の制限 ウィンドウ インスタンスを宣言すると、ほかのウィンドウから参照で きません。たとえば、3 つのウィンドウが開いている場合、2 番目と 3 番目のウィンドウから 1 番目のウィンドウを明示的に参照することが できません。参照変数を使用して開いたウィンドウのグローバル ハン ドルがありません。スクリプトを使用してウィンドウ インスタンスへ の参照を維持する方法については、94 ページの「ウィンドウ配列の使 い方」を参照してください。 インスタンスを開く ウィンドウ インスタンスを開くには、次のように、Open 関数でウィン ドウ変数を参照します。 w_employee mywin Open(mywin) この場合、Open 関数は、変数 mywin のデータ型を w_employee として ウィンドウ w_employee のインスタンスを作成し、変数 mywin への参照 を割り当てます。 このスクリプトをコマンドボタンの Clicked イベントに記述すると、ボ タンがクリックされるたびに、ウィンドウ w_employee の新しいインス タンスが作成されます。つまり、ボタンがクリックされるたびに、新 しいウィンドウが開きます。 したがって、ウィンドウ名をデータ型として変数を作成することで、 複数のウィンドウ インスタンスを開くことができます。これは簡単な 方法です。PowerBuilder は、ウィンドウを自動的に管理します。たと えば、開発者がウィンドウを閉じると、自動的にメモリを解放します。 インスタンスを閉じる 一般的に、ウィンドウのインスタンスを閉じるには、コマンドボタン の Clicked イベントに次のスクリプトを記述してウィンドウ内に配置 します。 Close(Parent) アプリケーション テクニック 93 ウィンドウ配列の使い方 このスクリプトは、コマンドボタンの親、つまりコマンドボタンが配 置されているウィンドウを閉じます。したがって、このスクリプトを 記 述 し た コ マ ン ド ボ タ ン を ウ ィ ン ド ウ w_employee に 配 置 す れ ば、 w_employee の 現 行 の ウ ィ ン ド ウ イ ン ス タ ン ス が 閉 じ ら れ ま す。 w_employee の mywin インスタンスにある CommandButton をクリック すると、mywin が閉じられます。 ウィンドウ配列の使い方 ウィンドウ配列を作成するには、ウィンドウのデータ型で配列を宣言 します。たとえば、次のステートメントでは、ウィンドウ w_employee のインスタンスを 5 つ含んだ配列 myarray を宣言します。 w_employee myarray[5] ウィンドウをいくつ開くのかコンパイル時にわからない場合は、可変 長のウィンドウ配列を作成できます。 配列を使用してインス タンスを開く 配列内のウィンドウのインスタンスを開くには、Open 関数に引数とし て配列のインデックスを渡します。上記の宣言に続き、以下のステー トメントでは、ウィンドウ w_employee の 1 番目と 2 番目のインスタン スを開きます。 Open(myarray[1]) Open(myarray[2]) // ウィンドウ w_employee の // 1 番目のインスタンスを開きます。 // 2 番目のインスタンスを開きます。 最初に開いたインスタンスの移動 上記のステートメントでは、1 番目のインスタンスと同じ位置に 2 番 目のインスタンスが開きます。2 番目の Open 関数を呼び出す前にスク リプトで Move 関数を呼び出して、最初に開いたインスタンスを別の位 置に移動する必要があります。 配列の操作 ウィンドウ配列を使用すると、配列のインデックスを指定して特定の ウィンドウ インスタンスを操作できます。たとえば、次のステートメ ントは、配列内の 2 番目のウィンドウを非表示にします。 myarray[2].Hide() また、次のように、配列のインデックスを使用してウィンドウ内のコ ントロールを参照できます。 myarray[2].st_count.text = "2" 94 PowerBuilder 第6章 ウィンドウ インスタンスの管理 複数のウィンドウを開く 多数のウィンドウ インスタンスを開いたり、閉じたりする場合は、メ イン ウィンドウのスクリプトに FOR...NEXT 文を記述してウィンドウ インスタンスを開いたり、閉じたりできます。たとえば、次のように スクリプトを記述します。 w_employee myarray[5] for i = 1 to 5 Open(myarray[i]) next 型が混在する配列の作 成 前述の例では、配列内のウィンドウはすべて同じ型でしたが、型が混 在する配列を作成することもできます。この方法を習得する前に、ま ず、ウィンドウの継承機能について詳しく知っておく必要があります。 定義するウィンドウは、実際はすべて、組み込みデータ型 window の 子孫ウィンドウです。 ゼロから定義されたウィンドウ w_employee と、w_employee から継承さ れたウィンドウ w_customer がある場合、継承階層は次のようになりま す。 図 6-2: ウィンドウの継承階層 window という名前のシステム定義オブジェクトは、PowerBuilder で定 義されるすべてのウィンドウの先祖オブジェクトです。組み込みオブ ジェクト window には、すべてのウィンドウで使用される、X、Y、タ イトルなどのプロパティが定義されています。 ユーザ定義ウィンドウはすべて window の子孫ウィンドウなので、 window 型の変数を定義すればアプリケーション内でどのような種類 のウィンドウでも参照できます。 次のスクリプトでは、3 つのウィンドウを含む配列 newarray を定義し ます。ユーザ定義ウィンドウはすべてデータ型 window から派生して いるので、配列はどのようなウィンドウでも参照できます。 アプリケーション テクニック 95 ウィンドウ配列の使い方 window newarray[3] string win[3] int iwin[1] = "w_employee" win[2] = "w_customer" win[3] = "w_sales" for i = 1 to 3 Open(newarray[i], win[i]) next このコードでは、次に示す書式の Open 関数を使用します。 Open ( windowVariable, windowType ) windowVariable は window 型の変数(子孫ウィンドウ)、windowType は ウィンドウの種類を指定する文字列です。 上記のスクリプトでは、ウィンドウ w_employee、w_customer、および w_sales のウィンドウ インスタンスを開きます。 配列の使い方と参照変 数の使い方 表 6-1 に、ウィンドウ インスタンスを操作するために参照変数を使用 する場合と配列を使用する場合を示します。 表 6-1: 配列と参照変数 項目 配列 長所 特定のウィンドウ イ ンスタンスが参照で きる 参照変数 使い方が簡単。 PowerBuilder が自動 的に処理を行う 短所 使い方が複雑。たとえば、配列内の 2 番 目のウィンドウを閉じた後で新しいウィ ンドウを開こうとする場合、 (必要以上に メモリを使用するが)配列の最後にウィ ンドウを追加するか、または既存の配列 内に新しいウィンドウ用の空スロットを 探すかどうかのスクリプトを記述する必 要がある 参照変数を使用して作成したウィンドウ の特定のインスタンスを操作できない w_employee を使用して、個々の従業員のデータを提供または修正する ものと仮定します。w_employee の 2 番目のインスタンスが同じ従業員 を開くことを禁止したり、w_employee のインスタンスをどの従業員に 対して開くかを決定したりすることもできます。このような管理を行 うには、配列を使用する必要があります。特定のウィンドウ インスタ ンスを管理する必要がない場合には、かわりに使いやすい参照変数を 使用してください。 96 PowerBuilder 第6章 ウィンドウ インスタンスの管理 子孫オブジェクトのエンティティの参照 データ型が window などオブジェクトの一種である変数を宣言すると、 その変数を使用して、子孫オブジェクトではなく先祖オブジェクトに 定義されているエンティティを参照できます。しかし、次の場合を考 えてみましょう。 w_customer mycust Open(mycust) // 次のステートメントは、ウィンドウ w_customer に // コントロール st_name があれば有効です。 mycust.st_name.text = "Joe" mycust は w_customer 型の変数として宣言されています。つまり、mycust はウィンドウ w_customer です。ウィンドウ w_customer に st_name とい う名前のスタティック テキスト コントロールが存在すれば、上記の最 後のステートメントは有効です。 しかし、次の場合を考えてみましょう。 window newwin string winname = "w_customer" Open(newwin, winname) // window 型のオブジェクトにスタティック テキスト コントロール // st_name がないので無効です。 newwin.st_name.text = "Joe" こ の 場 合、newwin は window 型 の 変 数 と し て 定 義 さ れ て い ま す。 PowerBuilder は、コンパイル時に厳密なデータ型チェックを行うため、 上記のステートメントは拒否されます。つまり、変数のコンパイル時 データ型に明示的に含まれていないオブジェクトのエンティティを参 照することはできません。 window 型のオブジェクトには st_name というコントロールは含まれて いないので、このステートメントは無効になります。下記のいずれか を行う必要があります。 • 次のように、newwin の宣言を、w_customer に、またはコントロー ル st_name を含む先祖ウィンドウに変更します。 w_customer newwin string winname = "w_customer" Open(newwin, winname) // 今度は有効です。 newwin.st_name.text = "Joe" アプリケーション テクニック 97 子孫オブジェクトのエンティティの参照 • 次のように、w_customer 型の別の変数を定義し、その変数を newwin に代入します。 window newwin w_customer custwin stringwinname = "w_customer" Open(newwin, winname) custwin = newwin // 今度は有効です。 custwin.st_name.text = "Joe" 98 PowerBuilder 第 7 章 ウィンドウにおけるタブ コント ロールの使い方 この章について この章では、アプリケーションでのタブ コントロールの使い方に ついて説明します。 内容 項目 タブ コントロールについて タブ ページの定義と管理 タブ コントロールのカスタマイズ スクリプトにおけるタブ コントロールの使い方 ページ 99 100 104 107 タブ コントロールについて タブ コントロールとは、ほかのコントロールを表示するタブ ペー ジのコンテナです。1 つのタブ ページは、タブ コントロールの表 示域を満たします。また、タブ ページには、インデックス カード を分割するようなタブがあります。ページを移動するには、タブ をクリックします。 アプリケーション テクニック 99 タブ ページの定義と管理 タブ コントロールを使用すれば、たくさんの情報を整理して、表示で きるようになります。ほかのコントロールと同様に、タブ コントロー ルの追加、サイズの変更、移動ができます。PowerBuilder の『ユーザー ズ ガイド』マニュアルでは、ウィンドウやカスタム ビジュアル ユー ザ オブジェクトにコントロールを追加する方法について説明してい ます。 タブ関連の用語 次の定義を知っておく必要があります。 ウィンドウまたはユーザ オブジェクトの中に配置 する、タブ ページを持つコントロールです。タブ コントロールは、タ ブとタブ ページで構成されます。残りのスペースはタブ ページそのも のが占めています。 タブ コントロール タブ ページ タブ ページはユーザ オブジェクトです。タブ ページ内 に、ほかのコントロールを配置することができます。タブ コントロー ルの中にあるすべてのタブ ページは、タブ コントロールと同じエリア を占めます。したがって、タブ ページは一度に 1 つのタブ ページしか 表示できません。アクティブなタブ ページが、ほかのタブ ページを覆 い隠してしまいます。 ペインタまたは実行時に、タブ コントロールの中にタブ ページを定義 できます。また、タブ ページをユーザ オブジェクトの中に定義して、 ペインタで、あるいは実行中にそのユーザ オブジェクトをタブ コント ロールに挿入することもできます。 タブ タブ ページのビジュアルなハンドルです。タブは、タブ ページ のラベルを表示します。タブ ページが表示されていない場合は、タブ をクリックして、そのタブ ページを前面に持ってきてアクティブにし ます。 タブ ページの定義と管理 タブ ページは、ユーザ オブジェクトです。 2 つの方法 タブ ページを定義するには、いくつかの方法があります。定義は、以 下のように行います。 • 100 埋め込みタブ ページ ペインタで、タブ コントロールにタブ ページ を挿入して、そのページにコントロールを追加します。埋め込み タブ ページは、UserObject クラスですが、再利用できません。 PowerBuilder 第7章 • ウィンドウにおけるタブ コントロールの使い方 独立したユーザ オブジェクト ユーザ オブジェクト ペインタで、カ スタム ビジュアル ユーザ オブジェクトを作成して、タブ ページ に表示されるコントロールを追加します。ユーザ オブジェクト ペ インタかスクリプトの中で OpenTab 関数を呼び出して、タブ コン トロール内のタブ ページとしてユーザ オブジェクトを使用でき ます。独立したユーザ オブジェクトとして定義されたタブ ページ は、再利用できます。 これら 2 つの方法は、同時に使用できます。つまり、1 つのタブ コン トロールに、埋め込みタブ ページと独立したユーザ オブジェクトの両 方を挿入できます。 新しいタブ コントロールを作成すると、埋め込みタブ ページが自動的 に 1 つ作成されます。そのタブ ページを使用することも、削除するこ ともできます。 タブ ページの作成方 法 ❖ ❖ ❖ タブ コントロール内に新しいタブ ページを作成するには 1 タブ コントロール内のタブエリアを右クリックします。タブ ペー ジをクリックしてはいけません。 2 ポップアップ メニューから[タブ ページの挿入]を選択します。 3 新しいタブ ページにコントロールを追加します。 タブ コントロールの独立したタブ ページを定義するには 1 新規作成 ダイアログボックスで、[PB オブジェクト]タブの[カ スタム ビジュアル]を選択します。 2 ユーザ オブジェクト ペインタで、使用するタブ コントロールの表 示領域のサイズに合わせて、ユーザ オブジェクトのサイズを設定 します。 3 タブ ページに表示されるコントロールをユーザ オブジェクトに 追加して、イベントに対するスクリプトを記述します。 4 ユーザ オブジェクトのプロパティ シートで、[タブ ページ]タブ をクリックして、タブ ページで使用される情報を設定します。 タブ コントロールに、タブ ページとしてユーザ オブジェクトを追加するには 1 タブ コントロール内のタブエリアを右クリックします。タブ ペー ジをクリックしてはいけません。 2 ポップアップ メニューから[ユーザ オブジェクトの挿入]を選択 します。 3 ユーザ オブジェクトを選択します。 アプリケーション テクニック 101 タブ ページの定義と管理 タブ ページは、選択したユーザ オブジェクトから継承されます。 タブ コントロール内のタブ ページを定義するのと同じように、継 承されたユーザ オブジェクトのタブ ページにプロパティを設定 し、スクリプトを記述できます。 タブ コントロール内のユーザ オブジェクトに配置されたコントロールの 編集 タブ コントロール内にあるユーザ オブジェクトの内容は編集で きません。ユーザ オブジェクト上のコントロールを編集したり、 スクリプトを記述したりする場合は、ウィンドウまたはタブ コン トロールがあるユーザ オブジェクトを閉じてから、ユーザ オブ ジェクト ペインタに戻って変更を行います 。 タブ コントロール上で、タブ ページの表示、表示順序の変更、削除が できます。 タブ ページの管理 ❖ 別のタブ ページを表示するには • タブ ページのタブをクリックします。 タブ ページは前面に表示され、アクティブなタブ ページとなりま す。タブは、設定したタブ順序に応じて再配置されます。 ❖ ❖ 102 タブ コントロール内のタブの表示順序を変更するには 1 タブ コントロールのプロパティ シートの[タブ順序]タブをクリッ クします。 2 表示したい位置にタブ ページの名前をドラッグします。 タブ コントロールからタブ ページを削除するには 1 タブ ページのタブをクリックします。 2 タブ ページを右クリックし、ポップアップ メニューから[切り取 り]または[削除]を選択します。 PowerBuilder 第7章 ウィンドウにおけるタブ コントロールの使い方 タブ コントロールとタブ ページの選択 タブ コントロール内のさまざまな領域をクリックしてみると、プロパ ティ ビューが変化して、タブ コントロール自身のプロパティ、タブ ページ、またはタブ ページ上のコントロールが表示されることがわか ります。ポップアップ メニューから[切り取り]などの項目を選択す る前に、正しいオブジェクトが選択されていることを確認してくださ い。 タブ コントロールのタブ領域のどこかをクリックすると、そのタブ コ ントロールが選択されます。特定ページのタブをクリックすると、そ のタブ ページはアクティブになりますが、選択されるオブジェクトは 依然としてタブ コントロールです。タブ ページを選択するには、その タブをクリックしてアクティブにしてから、タブ自身を除く、ページ の背景のどこかをクリックします。 タブ ページ上のコン トロール タブ コントロールの本来の目的は、タブ ページにほかのコントロール を表示させることです。タブ ページをウィンドウのミニチュア版とし て考えることができます。ウィンドウに対して行うように、タブ ペー ジにコントロールを追加します。 タブ コントロールで作業しているときは、タブ コントロール内に作成 されたタブ ページにしかコントロールを追加することができません。 タブ コントロール内のユーザ オブジェクトへのコントロールの追加 タブ コントロール内のユーザ オブジェクトにコントロールを追加す るには、ユーザ オブジェクト ペインタでそのユーザ オブジェクトを 開きます。 ❖ 埋め込みタブ ページにコントロールを追加するには • ウィンドウにコントロールを追加する場合と同様に、ツールバー または[挿入]メニューからコントロールを選択して、タブ ペー ジをクリックします。 タブ ページをクリックすると、そのタブ ページがコントロールの 親になります。 ❖ 1 つのタブ ページから別のタブ ページにコントロールを移動するには • アプリケーション テクニック コントロールを切り取るかコピーして、目的のタブ ページに貼り 付けます。 103 タブ コントロールのカスタマイズ 移動元のタブ ページと移動先のタブ ページは、両方とも埋め込みタブ ページでなければなりません。独立したユーザ オブジェクトであって はなりません。 ❖ タブ ページとそのタブ コントロールがあるウィンドウの間でコントロールを 移動するには • コントロールを切り取るかコピーして、目的のウィンドウかタブ ページに貼り付けます。 タブ コントロールの外のウィンドウに、コントロールをドラッグ することはできません。 タブ ページとウィンドウの間でコントロールを移動することは、コン トロールの親を変更することになります。したがって、コントロール を参照するスクリプトに影響を与えます。 タブ コントロールのカスタマイズ タブ コントロールには、タブの表示位置と表示形態を制御する設定が あります。それぞれのタブには、タブ自身のラベル、ピクチャ、背景 色があります。 すべてのタブは、タブのプロパティ シートの[フォント]タブ ページ で設定された、同じフォント設定を共有します。 タブ コントロールと タブ ページのための、 ポップアップ メ ニューとプロパティ シート タブ コントロールにはいくつかの要素があり、それぞれにポップアッ プ メニューとプロパティ シートがあります。プロパティ シートを開 くためには、ポップアップ メニュー上で[プロパティ]を選択します。 アクセスしたい要素の箇所でクリックします。 表 7-1: タブ コントロール要素へのアクセス 構成要素 タブ コントロール タブ ページ タブ ページ内のコントロー ル 104 方法 タブ コントロールのタブエリア内を右ク リックするか、ダブルクリックする タブ ページをアクティブにするためにタブ をクリックしてから、タブ ページ内でコント ロールがない部分をどこか右クリックする か、ダブルクリックする タブ ページをアクティブにするためにタブ をクリックしてから、コントロールを右ク リックするか、ダブルクリックする PowerBuilder 第7章 タブの表示位置とサイ ズ ウィンドウにおけるタブ コントロールの使い方 タブのプロパティ シートの[全般]タブ ページには、タブの表示位置 とサイズを制御するための、いくつかの設定があります。 表 7-2: タブのサイズと表示位置の制御 変更内容 変更する値 タブ コントロールのタブを表示する位置 [タブの位置] タブ コントロールの大きさに連動したタブの [幅合わせをしない]、 [複数 サイズ変更 行]、[均等なタブ幅] タブ コントロールの左右に連動したテキスト [テキストをタブに対して の向き。垂直テキストをサポートするのは 垂直に表示] True Type フォントのみであるため、この設定 には注意が必要 [均等なタブ幅]と[幅合わせをしない]チェックボックス [均等なタブ幅]をオンにすると、タブ幅は同じになります。[均等な タブ幅]をオンにすることと、 [幅合わせをしない]をオフにすること とは違います。 [幅合わせをしない]をオフにすると、タブ コントロー ルの縁にあわせて、タブが引き延ばされます。すべてのタブ ラベルの 長さが同じ場合はタブ幅も同じになりますが、長いラベルと短いラベ ルが混ざっている場合は、 [均等なタブ幅]をオンにしない限り、タブ 幅は、タブ ラベルの長さに応じて異なります。 以下のタブ コントロールは、いくつかの設定を組み合わせた結果を表 します。タブの位置は上端に設定してあります。 アプリケーション テクニック 105 タブ コントロールのカスタマイズ 次の例では、タブ コントロールは、住所録のように、タブが左側と右 側を行き来します。 [選択したテキストを太字]チェックボックスをオ ンにして、タブ位置を変更すれば、選択されたタブを見つけることが 容易になります。 タブ ラベル タブ コントロールとタブ シートの両方のプロパティ シートを使用し て、タブの外観を変更できます。 表 7-3: タブの外観の変更 プロパティ プロパティ シート ページ タブ コント [全般] ロール タブ ページ [全般] 設定 [ピクチャを右側に表 示]、 [ピクチャの表 示]、 [テキストの表示] [テキスト] [背景色] 、 タブ ページ [タブページ] [ピクチャ名] [タブの 、 文字の色]、 [タブの背 景色]、 [ピクチャのマ スク色] 作用対象 コントロール内の すべてのタブ タブ上のラベルとタ ブ ページの背景色 テキストの色、タブ 上のピクチャ、 (タ ブ ページではなく) タブ自身の背景色 タブ ページとして使用するユーザ オブジェクトをユーザ オブジェク ト ペインタで作成している場合、タブ ページのプロパティ シートで 作成できる、ユーザ オブジェクトのプロパティ シートの[タブ ペー ジ]で同じ設定ができます。 106 PowerBuilder 第7章 ウィンドウにおけるタブ コントロールの使い方 以下の例では、ピクチャとテキストがそれぞれのタブ ページに設定さ れています。タブは、それぞれ異なる背景色が設定されています。 [ピ クチャの表示]と[テキストの表示]の両チェックボックスの設定は、 どちらもオンです。 スクリプトでタブの表 示形態を変更 ペインタで行った、これらのプロパティの設定は、スクリプトでもで きます。スクリプトでプロパティを設定すれば、実行時に動的にタブ コントロールの表示形態を変更できます。 スクリプトにおけるタブ コントロールの使い方 この節では、以下のようなスクリプトにおけるタブの例について説明 します。 • スクリプトでのタブ ページの参照 • タブ ページにあるコントロールの参照 • タブ ページを開く、閉じる、非表示にする • タブ ページの履歴 • 必要なときだけタブ ページを生成 • タブ コントロールの各部分におけるイベント スクリプトでのタブ ページの参照 ドット(.)表記を使用して、個々のタブ ページとそのタブ ページに あるコントロールを参照できます。 • ウィンドウやユーザ オブジェクトは、その中にあるタブ コントロー ルの親です。 window.tabcontrol • タブ コントロールは、その中にあるタブ ページの親です。 window.tabcontrol.tabpageuo • タブ ページは、その中にあるコントロールの親です。 window.tabcontrol.tabpageuo.controlonpage アプリケーション テクニック 107 スクリプトにおけるタブ コントロールの使い方 たとえば、以下のステートメントは、ウィンドウ w_display 内のタブ コ ントロール tab_1 の PowerTips プロパティを設定します。 w_display.tab_1.PowerTips = TRUE 次の例では、タブ ページ tabpage_1 の PowerTipText プロパティを設定 します。 w_display.tab_1.tabpage_1.PowerTipText = & "Font settings" 以下の例では、タブ ページ tabpage_doit にあるコマンドボタン cb_OK を使用可能にします。 w_display.tab_1.tabpage_doit.cb_OK.Enabled = TRUE 汎用的なプログラミン グ スクリプトを汎用的に作成するには、Parent 代名詞と GetParent 関数を 使用します。 Parent 代名詞 どんなタブ ページのスクリプトにおいてもタブ コント ロールを参照するために、Parent 代名詞を使用できます。 Parent.SelectTab(This) GetParent 関数 タブ ページのイベントに対するスクリプトでは、タブ ページの親であるタブ コントロールを参照するために GetParent 関数 を呼び出すことができます。この関数を使用して、Tab データ型の変 数に親への参照を代入できます。 タブ ページとして使用されている、ユーザ オブジェクトのイベントに 対するスクリプトで、インスタンス変数にタブ ページの親であるタブ コントロールへの参照を代入するために、以下のスクリプトが使用で きます。 以下は、インスタンス変数の宣言です。このインスタンス変数は、ど んなタブ コントロールへの参照も代入できます。 tab itab_settings 以下は、インスタンス変数にタブ ページの親への参照を代入します。 // タブ コントロールへの参照を取得します。 // This 代名詞は、タブ ページのユーザ オブジェクトを参照します。 itab_settings = This.GetParent() タブ ページにあるコントロールのイベントに対するスクリプトでは、 タブ ページのユーザ オブジェクトとその親のタブ コントロールを参 照するために、GetParent 関数を 2 回呼び出します。 tab tab_mytab userobject tabpage_generic 108 PowerBuilder 第7章 ウィンドウにおけるタブ コントロールの使い方 tabpage_generic = This.GetParent() tab_mytab = tabpage_generic.GetParent() tabpage_generic.PowerTipText = & "Important property page" tab_mytab.PowerTips = TRUE tab_mytab.SelectTab(tabpage_generic) Tab データ型の変数の制限事項 PowerBuilder のシステム オブジェクト データ型である Tab 型の変数は、タブ コントロールにあるタブ ページ を認識できません。また、UserObject 型の変数は、タブ ページにある コントロールを認識できません。 以下のタブ ページのイベントに対するスクリプトで記述したローカ ル変数は、親であるタブ コントロールへの参照が代入されています。 Tab 型の変数 tab_settings はタブ コントロール内のページについて認識 できないので、特定なページを参照できません。ただし、タブ コント ロールの関数を呼び出して、タブ コントロールのプロパティを参照す ることはできます。 tab tab_settings tab_settings = This.GetParent() tab_settings.SelectTab(This) ユーザ オブジェクト変数 タブ ページが独立したユーザ オブジェクト の場合は、そのユーザ オブジェクトをデータ型として、タブ ページの 変数を定義できます。ユーザ オブジェクトは、挿入したタブ ページの 先祖です。宣言した変数は、ユーザ オブジェクトにあるコントロール が参照できます。 以下のタブ コントロールのイベントに対するスクリプトでは、引数 index は、タブ ページを参照して、Control プロパティ配列からユーザ オブジェクトへの参照を取得するために使用されます。例では、すべ てのタブ ページが同じユーザ オブジェクト uo_emprpt_page を使用し ているものとします。 uo_emprpt_page tabpage_current tabpage_current = This.Control[index] tabpage_current.dw_emp.Retrieve & (tabpage_current.st_name.Text) アプリケーション テクニック 109 スクリプトにおけるタブ コントロールの使い方 タブ コントロールの Control プロパティ配列 Control プロパティ配列には、埋め込みユーザ オブジェクトや独立した ユーザ オブジェクトなど、コントロール内のすべてのタブ ページへの 参照が含まれます。新しいタブ ページをペインタで挿入したり、スクリ プトで開いたりすると、それらのタブ ページが配列に追加されます。 タブ ページにあるコントロールの参照 別のウィンドウのタブ ページにあるコントロールを参照する場合は、 ウィンドウ レベルまでコントロールの名前を修飾しなければなりま せん。 次の例では、完全修飾してスタティック テキスト コントロールを参照 します。 w_activity_manager.tab_fyi.tabpage_today. & st_currlogon_time.Text = ls_current_logon_time PowerBuilder の Code Examples の以下の例は、ウィンドウにあるデータ ウィンドウ コントロールのサイズとタブ ページにあるデータウィン ドウ コントロールのサイズが一致するように設定します。すべてのタ ブ ページはペインタで挿入されているので、Control プロパティ配列は タブ ページのインデックス順に、タブ ページへの参照が保持されてい ます。すべてのタブ ページは、同じユーザ オブジェクト u_tab_dir が挿 入されたものです。 u_tab_dir luo_Tab luo_Tab = This.Control[newindex] luo_Tab.dw_dir.Height = dw_list.Height luo_Tab.dw_dir.Width = dw_list.Width タブ ページとして使用されるユーザ オブジェクトのスクリプトと関 数は、ユーザ オブジェクトにあるコントロールを認識します。した がって、コントロールへの参照を修飾する必要はありません。ユーザ オブジェクト u_tab_dir の関数である以下の例は、データウィンドウ コ ントロール dw_dir にデータを取得します。 IF NOT ib_Retrieved THEN dw_dir.SetTransObject(SQLCA) dw_dir.Retrieve(as_Parm) ib_Retrieved = TRUE END IF 110 PowerBuilder 第7章 ウィンドウにおけるタブ コントロールの使い方 RETURN dw_dir.RowCount() タブ ページを開く、閉じる、非表示にする スクリプトでタブ ページを開くことができます。スクリプトで開いた タブ ページを閉じることはできますが、ペインタで挿入したタブ ペー ジを閉じることはできません。ただし、どんなタブ ページも非表示に することはできます。 以下の例は、ユーザ オブジェクト tabpage_listbox をタブ ページとして 開いて、インスタンス変数 i_tabpage にユーザ オブジェクトへの参照 を代入します。OpenTab 関数の引数 0 は、そのタブ ページがタブ コン トロールで最後のページになることを指定します。後からタブ ページ を閉じるには、ユーザ オブジェクトへの参照を保持する必要がありま す。 以下は、タブ ページのユーザ オブジェクトへの参照のためのインスタ ンス変数宣言です。 userobject i_tabpage 以下のステートメントは、ユーザ オブジェクトをタブ ページとして開 きます。 li_rtn = tab_1.OpenTab & (i_tabpage, "tabpage_listbox", 0) 以下のステートメントは、タブ ページを閉じます。 tab_1.CloseTab(i_tabpage) タブ ページの履歴 タブ ページにあるコントロールを参照するには、タブ ページのイン デックスやユーザ オブジェクトへの参照が必要です。タブ ページの Control プロパティ配列を使用すると、すべてのタブ ページへの参照を 取得できます。 タブ ページの Control プロパティ配列 タブ コントロールの Control プロパティ配列は、ペインタで定義した タブ ページとスクリプトで追加したタブ ページへの参照を保持する 配列です。イベントに渡されるインデックスの値は、Control プロパ ティ配列の配列要素と一致します。 SelectedTab プロパティを使用して、選択したタブ ページのユーザ オブ ジェクトへの参照を取得できます。 アプリケーション テクニック 111 スクリプトにおけるタブ コントロールの使い方 userobject luo_tabpage luo_tabpage = tab_1.Control[tab_1.SelectedTab] タブ コントロールのイベントでは、SelectionChanged イベントのよう に、イベントに渡されたタブ ページのインデックスの値を使用して、 Control プロパティ配列からタブ ページへの参照を取得できます。 userobject tabpage_generic tabpage_generic = This.Control[newindex] 新しいタブ ページの 追加 OpenTab 関数を呼び出すと、Control プロパティ配列の要素が 1 つ増え ます。新しい要素は、新しく開いたタブ ページへの参照を保持します。 次のステートメントでは、タブ コントロールの 2 番目の位置に新しい タブを追加します。 tab_1.OpenTab(uo_newtab, 2) tab_1 の Control 配列内の 2 番目の要素が uo_newtab への参照を保持す るので、それ以降のタブ ページの Control 配列のインデックスが 1 つ ずつ加算されます。 タブ ページを閉じる CloseTab 関数を呼び出すと、配列のサイズが 1 つ減少し、ユーザ オブ ジェクトまたはページへの参照が破棄されます。配列の最後の要素以 外のタブを閉じた場合は、それ以降のタブ ページのインデックスが 1 つずつ減少します。 タブ ページの移動 MoveTab 関数は、タブ コントール内のページの順序を変更し、その順 序に合わせて Control 配列の要素の順序も変更します。 ユーザ オブジェクトの Control プロパティ配列 ユーザ オブジェクトの Control プロパティ配列の場合も同様に行いま す。 必要なときだけタブ ページを生成 エンド ユーザは、タブ コントロール内のすべてのタブ ページを参照 するとは限りません。タブ コントロールの[全般]プロパティ ページ で[現行タブ上のコントロールのみ生成]をチェックしておくか、 CreateOnDemand プロパティを TRUE に設定しておけば、すべてのタブ ページのコントロールのグラフィック表現を作成するオーバーヘッド を回避できます。 112 PowerBuilder 第7章 ウィンドウにおけるタブ コントロールの使い方 タブ コントロールを作成すると、タブ コントロール内のすべてのタブ ページのコントロールのインスタンスがいつも作成されます。ただし、 [現行タブ上のコントロールのみ生成]がチェックしてあれば、タブ ページのコントロールの Constructor イベントは発生せず、ユーザがそ のタブ ページを参照しない限り、コントロールのグラフィック表現は 作成されません。 選択したタブ ページの Constructor イベント タブ コントロールを作成すると、選択したタブ ページにあるコント ロールの Constructor イベントが常に発生します。 [現行タブ上のコント ロールのみ生成]オプ ションのトレードオフ タブ ページの生成 チェック コントロールが多くあるタブ ページのグラフィック表現の作成を遅 らせると、ウィンドウがよりすばやく開きます。しかし、タブ ページ の Constructor イベントが起動されてコントロールのグラフィック表現 が作成されるまでは、スクリプトでタブ ページのコントロールを参照 することはできません。[現行タブ上のコントロールのみ生成]が チェックされている場合は、表示されていないタブ ページのコント ロールをスクリプトで参照することはできません。 PageCreated 関数を使用して、 タブ ページが作成されたかどうかを確認 できます。作成されていない場合は、CreatePage 関数を使用してその タブ ページの Constructor イベントを発生させることができます。 IF tab_1.tabpage_3.PageCreated() = FALSE THEN tab_1.tabpage_3.CreatePage() END IF タブ ページにあるコントロールのハンドルがゼロでないかをチェッ クして、タブ ページのインスタンスが生成されたかを確認できます。 ハンドルがゼロでない場合は、コントロールのインスタンスは生成さ れています。 IF Handle(tab_1.tabpage_3.dw_list) > 0 THEN ... 実行時での CreateOnDemand プ ロパティの変更 スクリプトで CreateOnDemand プロパティを FALSE に設定すると、グ ラフィック表現が作成されていなかったタブ ページのグラフィック 表現がすぐに作成されます。 すべてのタブ ページのグラフィック表現が作成されている場合は、実 行時に CreateOnDemand プロパティを TRUE に変更しても、何も変わり ません。 アプリケーション テクニック 113 スクリプトにおけるタブ コントロールの使い方 タブ ページの動的な 作成 CreateOnDemand が FALSE である場合には、メッセージ オブジェクト に渡された OpenTabWithParm への引数を使用して、Constructor イベン トにおいて動的に作成されたタブ ページのラベルを設定できます。 CreateOnDemand が TRUE で ある 場 合 には、タブ が 選 択 され る ま で Constructor イベントは発生しないため、タブ ページがインスタンス化 されるときにラベルを設定する必要があります。ウィンドウの Open イ ベントからポストされたユーザ イベントに以下のスクリプトが含ま れる場合には、5 つのタブ ページが開かれ、インスタンス化されると きにタブごとのラベルが設定されます。 int li_ctr string is_title THIS.setredraw(false) FOR li_ctr = 1 to 5 is_title = "Tab#" + string(li_ctr) tab_test.opentabwithparm(iuo_tabpage[li_ctr], & is_title, 0) iuo_tabpage[li_ctr].text = is_title // タブ ラベルを設定 NEXT THIS.setredraw(true) RETURN 1 タブ コントロールの各部分におけるイベント タブ コントロールの各部分(タブ、タブ ページ、タブ ページにある コントロール)は、重なるエリアが多いため、イベントに対するスク リプトをどこに記述するかを知っておく必要があります。 表 7-4: タブ コントロール イベントに対するスクリプトの記述 イベントの起動対象となる箇所 タブに対するクリックやドラッグ を含む、タブ コントロールのタ ブ エリア タブ ページ(タブではない) タブ ページ内のコントロール 114 イベントに対するスクリプトの所属 タブ コントロール タブ ページ(埋め込みタブ ページの場 合)またはユーザ オブジェクト(独立 したタブ ページの場合) タブ ページ上のコントロール自身 PowerBuilder 第7章 ウィンドウにおけるタブ コントロールの使い方 たとえば、エンド ユーザがタブへドラッグして、タブに関連付けられ ているタブ ページに何かを行いたい場合、タブ ページではなくタブ コ ントロールの DragDrop イベントにスクリプトを記述する必要があり ます。 例 タブ コントロール tab_1 の DragDrop イベントの以下のスクリプトは、 エンド ユーザがタブの上に何かをドロップしたときに、ドロップ先の タブ ページを選択します。ドロップされたタブのインデックスが、 DragDrop イベントの引数となります。 This.SelectTab( index ) 次のスクリプトは、タブ コントロールの DragDrop イベントのもので す。エンド ユーザがデータウィンドウのデータをタブにドラッグする と、そのタブに関連付けられているタブ ページのリストに、そのデー タが挿入されます。 ListBox コントロール lb_list がある tabpage_listbox 型のユーザ オブジェ クトは、ユーザ オブジェクト ペインタで定義されています。タブ コン トロールには、tabpage_listbox 型の独立したタブ ページが複数ありま す。 Control プロパティ配列からタブ ページへの参照を取得するには、 DragDrop イベントの引数 index を使用します。ユーザ オブジェクトへ の参照により、スクリプトでタブ ページのコントロールにアクセスで きます。 タブ コントロールの以下のスクリプトの Parent 代名詞は、ウィンドウ を参照しています。 long ll_row string ls_name tabpage_listbox luo_tabpage IF TypeOf(source) = DataWindow!THEN l_row = Parent.dw_2.GetRow() ls_name = Parent.dw_2.Object.lname.Primary[ll_row] // Control プロパティ配列から参照を取得します。 luo_tabpage = This.Control[index] // タブ ページを選択します。 This.SelectTab(index) // ドラッグされたデータを挿入します。 luo_tabpage.lb_list.InsertItem(ls_name, 0) END IF アプリケーション テクニック 115 スクリプトにおけるタブ コントロールの使い方 タブ ページが作成されていない場合 タブ コントロールの CreateOnDemand プロパティが TRUE になってい る場合、タブ ページが選択されるまでは、タブ ページやそのコント ロールの Constructor イベントは発生しません。上記の例では、タブ ページを選択したことによって、Constructor イベントが発生していま す。CreatePage 関数を使用して、Constructor イベントを発生させるこ ともできます。 IF luo_tabpage.PageCreated() = FALSE THEN & luo_tabpage.CreatePage() 116 PowerBuilder 第 8 章 ツリービュー コントロールの使い方 この章について この章では、ツリービュー コントロールを使用して階層構造(分 岐型)のリストを表示する方法について説明します。 内容 項目 ツリービュー コントロールについて ツリービューの表示 ツリービューの項目の管理 ツリービュー ピクチャの管理 データウィンドウのデータのツリービューへの表示 ページ 117 121 127 136 139 ツリービュー コントロールについて ツリービュー コントロールによって、階層構造のリストを表示す ることができます。ツリービューは、階層を開いたり閉じたりす る標準インタフェースを提供します。 アプリケーション テクニック 117 ツリービュー コントロールについて ツリービューの用途 ツリービューは、ウィンドウとカスタム ビジュアル ユーザ オブジェ クトで使用します。同レベルの項目だけでなく、さまざまな項目で構 成された、より複雑なリストや、1 つの項目から多数の項目が分岐す るリストを表示する場合に、リストボックスやリストビューのかわり にツリービューを使用します。エンド ユーザが標準ツリービュー イン タフェースを使用してリストの分岐を表示する場合にも、データウィ ンドウ コントロールではなくツリービューを使用します。 階層構造のリスト リストビューのレポート ビューのような単一階層のリストでツリー ビューを使用してもかまいませんが、1 つの項目から多数の項目が分 岐し、複数の階層で構成されるリストでツリービューは威力を発揮し ます。たとえば、1 つまたは複数の親項目の下にそれぞれいくつかの 子項目が属するようなリストでツリービューを利用するとよいでしょ う。また、複数のレベルで段階的に分類されているリストにも有効で す。 ルート 項目 1 二次項目 1a 詳細項目 詳細項目 二次項目 1b 詳細項目 詳細項目 項目 2 二次項目 2a 詳細項目 レベルの数 分岐によって必要な階層の深さが異なる場合、分岐ごとのレベルの数 が一致しなくてもかまいません。ただし、同じレベルの項目が、ある 分岐では二次項目であり、ほかの分岐では詳細項目であるというよう にバラバラであるよりは、同じ種類の項目である方が、プログラミン グは容易になります。 たとえば、項目のレベルをテストして、適切なアクションを決めるス クリプトを考えてみましょう。この場合、SetLevelPictures 関数を呼び 出して、特定のレベルのすべての項目にピクチャを設定することがで きます。 ツリービューのデータ ソース 118 PowerBuilder のほとんどのリストでは、ペインタまたはスクリプトを 使用して項目を追加できますが、ツリービューではスクリプトを作成 しなければなりません。通常、ウィンドウを開くと、ツリービューの 第 1 レベル(ルート レベル)が表示されます。エンド ユーザが分岐を 表示したときに、ツリービューの ItemPopulate イベントに対するスク リプトによって、次のレベルの項目を追加できます。 PowerBuilder 第8章 ツリービュー コントロールの使い方 項目のデータはスクリプトでハードコード化できますが、エンド ユー ザの入力や、ツリービューの内容が登録されているデータベースを使 用する方が効率的です。1 つの項目から複数の子項目が分岐するので、 データベース内の複数のテーブルを使用してツリービューを表示でき ます。 データストアの使用例については、139 ページの「データウィンドウ のデータのツリービューへの表示」を参照してください。 項目のピクチャ ツリービューでは、各項目にピクチャが関連付けられています。コン トロールのピクチャ リストで使用するピクチャを選択してから、その ピクチャのインデックスを項目に関連付けます。一般的に、ピクチャ は各項目に固有のものではありません。ピクチャは、そのレベル内で 項目を分類したり識別したりするためのものです。以下のような方法 でピクチャを使用すると、エンド ユーザがデータを識別しやすくなり ます。 • 各レベルで異なるピクチャを使用する • 同一レベルで、項目の種類ごとに異なるピクチャを使用する • 特定のレベルのみピクチャを使用する • エンド ユーザが項目をクリックしたらピクチャを変更する ピクチャによってエンド ユーザに情報 を提示する必要がない場合は、ピクチャを使用しなくてもかまいませ ん。項目のラベルと階層のレベルだけで十分な場合もあります。 ピクチャを使用しなくてもよい ツリービューの外観 プロパティを使用してツリービューの外観を制御できます。全体的な 外観を変更するプロパティは表 8-1 のとおりです。 アプリケーション テクニック 119 ツリービュー コントロールについて 表 8-1: ツリービューのプロパティ プロパティ HasButtons HasLines と LinesAtRoot Checkboxes TrackSelect FullRowSelect SingleExpand Indent フォント プロパ ティ 各種ピクチャ プ ロパティ LayoutRTL と RightToLeft 効果 項目の前にプラス(+)やマイナス(-)ボタンがある場 合は子項目があり、そのボタンをクリックすることに よって分岐を開閉できることを示す 分岐内の項目や、ルート レベルの項目を接続する線を表 示する 状態ピクチャをチェック済みチェックボックスおよび 未チェック チェックボックスに置き換える マウスが上に移動したときに項目の外観を変更する 選択した項目の行全体をハイライト表示する 選択した項目を展開し、前に選択した項目を自動的に折 りたたむ 項目をインデントする量を指定する すべてのラベルのフォントを指定する ピクチャとそのサイズを制御する コントロール内の要素と文字を右から左に表示する これらのプロパティの詳細については、『オブジェクトとコントロー ル』マニュアルを参照してください。 ユーザ操作 開発者が特にスクリプトを作成しなくても、ツリービューの基本機能 を利用して、エンド ユーザがラベルの編集、項目の削除、分岐の開閉、 およびアルファベット順のソートを行うことができます。たとえば、 エンド ユーザが選択した項目をもう一度クリックすると、ラベルは編 集状態になります。また、〔Delete〕を押すと項目が削除されます。プ ロパティを設定して、このような操作を実行できないようにすること も可能です。 スクリプトを作成して、このような基本操作をカスタマイズすること ができます。基本操作にイベントを関連付けることにより、操作を実 行可能または実行不可にします。また、項目の追加、項目のドラッグ、 ソート指定のカスタマイズなど、そのほかの機能を実装することもで きます。 カスタム イベントの 使い方 120 PowerBuilder バージョン 7 以降では、リストビュー コントロールとツ リービュー コントロールに Microsoft のコントロールが使用されてい ます。右クリックしたときに呼び出されるイベントが、以前のリリー スとは異なります。 PowerBuilder 第8章 ツリービュー コントロールの使い方 マウスの右ボタンを放したときに、pbm_rbuttonup イベントは発生しま せん。このボタンが放されると、ツリービュー コントロールの組み込 み RightClicked! イベント pbm_tvnrclickedevent が発生します。 選択されていないツリービュー項目を右クリックした場合、その右ボ タンを放すと、以前選択されていた項目にフォーカスが戻ります。新 しい項目を選択するには、次のコードを pbm_tvnrclickedevent スクリプ トに挿入します。その後で、その項目に対する処理スクリプトを記述 します。 this.SelectItem(handle) マウスの右ボタンでダブルクリックすると、pbm_rbuttondblclk イベント のみ発生します。以前のリリースでは pbm_rbuttondblclk と pbm_tvnrdoubleclick の両方のイベントが発生していました。 ツリービューの表示 ツリービューに項目を追加するには、スクリプトを作成する必要があ ります。ほかのリスト コントロールのように、ペインタでアイテムを 追加することはできません。ツリービューのすべてのレベルを一度に 表示することもできますが、ツリービューのイベントを使用してエン ド ユーザが必要な分岐のみを表示した方が、不要な手間を省くことが できます。 通常、コントロールを表示したときに、ツリービューの第 1 レベルが 表示されます。このコードは、ウィンドウの Open イベント、Open イ ベ ン ト か ら 起 動 さ れ る ユ ー ザ イ ベ ン ト、ま た は ツ リ ー ビ ュ ー の Constructor イベントにあります。その後で、コントロールの ItemPopulate イベントに対するスクリプトによって、エンド ユーザが分岐を開いた ときに、その項目の子項目が挿入されます。 エンド ユーザが項目のプラス ボタンをクリックするか、項目をダブル クリックすると、その項目の Children プロパティが TRUE の場合のみ、 ItemPopulate イベントが起動されます。このため、子項目がある項目を 挿入する場合、Children プロパティを TRUE にして、エンド ユーザが 分岐を開いたときに子項目が表示されるようにしておかなければなり ません。 ItemPopulate イベント以外にも項目を追加する方法はあります。たとえ ば、エンド ユーザがリストボックスから項目をドラッグしたり、テキ ストボックスに入力することによって追加したりすることもできま す。 アプリケーション テクニック 121 ツリービューの表示 項目挿入関数 表 8-2 に、ツリービュー コントロールに項目を追加する関数を示しま す。 表 8-2: ツリービュー コントロールに項目を追加する関数 関数 InsertItem InsertItemFirst InsertItemLast InsertItemSort 挿入位置 指定した親項目の兄弟項目の後 兄弟項目がない場合は、別の挿入関数を使用しなければな らない 親項目の最初の子項目になる 親項目の最後の子項目になる 可能な場合は、子項目のアルファベット順で適切な位置に 挿入 すべての InsertItem 関数で、SortType プロパティを使用して項目を追加 する位置を指定できます。 追加した項目に関する情報を表示するには、プロパティを使用した以 下の 2 つの方法があります。 方法 1 : ラベルとピク チャ インデックスの み指定する 項目にピクチャ インデックスとラベルを付けて挿入します。そのほか のプロパティはすべて、デフォルト値を使用します。ハンドルを使用 して、必要であれば、後でそのほかのプロパティを設定できます。 以下の例は、現在選択されている項目の後に、同レベルの新規項 目を追加する場合です。最初に、現在選択されている項目とその親項 目のハンドルを取得し、その後現在選択されている項目の後に Hindemith というラベルの項目を挿入します。この項目のピクチャ インデックス は 2 です。 例 long ll_tvi, ll_tvparent ll_tvi = tv_list.FindItem(CurrentTreeItem!, 0) ll_tvparent = tv_list.FindItem(ParentTreeItem!, & ll_tvi) tv_list.InsertItem(ll_tvparent, ll_tvi, & "Hindemith", 2) 方法 2 :TreeViewItem 構造体で項目のプロパ ティを設定する 122 特定の値にプロパティを設定した TreeViewItem 構造体を使用して項目 を追加します。必要なプロパティはラベルだけです。表 8-3 に示され ているプロパティを設定できます。 PowerBuilder 第8章 ツリービュー コントロールの使い方 表 8-3: TreeViewItem プロパティ プロパティ Label PictureIndex SelectedPictureIndex StatePictureIndex Children Data 値 項目名を示すテキスト 標準ピクチャ リストの値 標準ピクチャ リストの値。その項目が選択されたとき のみ表示されるピクチャ。この値が 0 の場合、その項 目を選択してもピクチャは表示されない 状態ピクチャ リストの値。標準ピクチャの左側にその 状態ピクチャが表示される ダブルクリックによって ItemPopulate イベントを起動 する場合、この値が TRUE でなければならない。この イベント スクリプトによって子項目を挿入できる 項目に関連付けるデータ型の値(オプション)。ソー トの制御やデータベースのクエリで使用できる 以下の例では、ツリービュー コントロールに項目を追加する前に、 TreeViewItem 構造体ですべてのプロパティを設定します。この項目は、 現在の項目の子項目として追加されます。 例 treeviewitem tvi long h_item = 0, h_parent = 0 h_parent = tv_1.FindItem(CurrentTreeItem!, 0) tvi.Label = "Choral" tvi.PictureIndex = 1 tvi.SelectedPictureIndex = 2 tvi.Children = true tvi.StatePictureIndex = 0 h_item = tv_1.InsertItemSort(h_parent, tvi) ツリービュー コントロールに項目を挿入する方法の詳細については、 『PowerScript リファレンス』マニュアルを参照してください。 ルート レベルへの項目の挿入 最初に挿入した項目には兄弟項目がないので、InsertItem 関数を使用で きません。この場合、InsertItemFirst 関数か InsertItemLast 関数を使用す る必要があります。ルート レベルに項目を挿入する場合、親は 0 にな ります。 以下のサンプル コードは、ツリービューを表示するウィンドウの Open イベントから起動されたユーザ イベントのものです。ここでは、以下 に示す 2 つのインスタンス変数配列があるものとします。 アプリケーション テクニック 123 ツリービューの表示 • item_label という名前の文字列配列。ルート レベルに挿入されるす べての項目のラベル(ここでは作曲家名) • Data プロパティの値(ここでは作曲家の世紀)になる整数配列。 この数値を使用してユーザ定義のソートを行う int ct long h_item = 0 treeviewitem tvi FOR ct = 1 TO UpperBound(item_label) tvi.Label = item_label[ct] tvi.Data = item_data[ct] tvi.PictureIndex = 1 tvi.SelectedPictureIndex = 2 tvi.Children = TRUE tvi.StatePictureIndex = 0 tvi.DropHighlighted = TRUE h_item = tv_1.InsertItemSort(0, tvi) NEXT すべての項目を挿入した後で、以下のコードによってツリービューを 最初の項目までスクロールして戻し、最初の項目を現在の項目にしま す。 // 最初の項目までスクロール h_item = tv_1.FindItem(RootTreeItem!, 0) tv_1.SetFirstVisible(h_item) tv_1.SelectItem(h_item) ルート レベルの下への項目の挿入 エンド ユーザが子項目を表示するために最初に分岐を開いたときに、 その項目の Children プロパティが TRUE の場合のみ、ItemPopulate イベ ントが起動されます。ItemPopulate イベントで、現在開いているレベル に子項目を追加できます。 親項目の Children プロパティ 最初に分岐を開いたときに ItemPopulate イベントが起動されなかった 場合、その項目の Children プロパティが TRUE になっているかどうか を確認してください。子項目がある項目の Children プロパティはすべ て TRUE になっていなければなりません。 124 PowerBuilder 第8章 ツリービュー コントロールの使い方 ItemPopulate イベント以外の方法による挿入 ItemPopulate イベントを使 用すると、エンド ユーザが必要な項目のみを表示すればよいので、効 率的にプログラムを作成できますが、エンド ユーザが分岐を開くまで 待たなければなりません。ItemPopulate イベントが起動される前に挿入 したい場合は、ルート レベルに項目を挿入するように、スクリプトに よって子項目を追加することもできます。 たとえば、小さなツリービューの場合、ウィンドウを開いたときに全 体を表示し、ExpandAll 関数を使用して分岐がすべて開いた状態で項目 を表示することができます。 子項目を表示したかどうかの確認 その項目の ExpandedOnce プロパティ をチェックすることにより、エンド ユーザがその子項目を表示したか どうかを確認することができます。エンド ユーザが子項目を表示して いる場合、Expanded プロパティも TRUE になります。 以下のツリービューは、作曲家とその楽曲を分類したものです。 ItemPopulate イベントに対するスクリプトによって、現在開いている項 目が、レベル 1(作曲家)またはレベル 2(分類)のいずれに属するか をチェックします。レベル 3 の項目は開いていません。 例 レベル 1 の項目の下に、スクリプトによって 3 つの標準分類を追加し ます。レベル 2 の項目の下に、その分類に属する楽曲を追加します。 この場合、以下のような構造になります。 モーツァルト 管弦楽 交響曲第 33 番 魔笛への序曲 室内楽 ホルン五重奏曲 変ホ長調 アイネ クライネ ナハトムジーク 声楽 ドン ジョバンニ イドメネオ ItemPopulate イベントに対するスクリプトは以下のとおりです。 TreeViewItem tvi_current, tvi_child, tvi_root long hdl_root Integer ct string categ[] // 現在の項目は、新規項目の親項目です。 This.GetItem(handle, tvi_current) IF tvi_current.Level = 1 THEN // レベル 2 の標準分類を表示します。 アプリケーション テクニック 125 ツリービューの表示 categ[1] = " 管弦楽 " categ[2] = " 室内楽 " categ[3] = " 声楽 " tvi_child.StatePictureIndex = 0 tvi_child.PictureIndex = 3 tvi_child.SelectedPictureIndex = 4 tvi_child.OverlayPictureIndex = 0 tvi_child.Children = TRUE FOR ct = 1 to UpperBound(categ) tvi_child.Label = categ[ct] This.InsertItemLast(handle, tvi_child) NEXT END IF // レベル 3 の楽曲名を表示します。 IF tvi_current.Level = 2 THEN // 現在の項目の親項目を表示します。 // 現在の分岐のルートであり、 // 子項目を選択するキーの 1 つになります。 hdl_root = This.FindItem(ParentTreeItem!, handle) This.GetItem(hdl_root, tvi_root) FOR ct = 1 to 4 // このステートメントはラベルを構成します。テーブルや // データベースでデータを検索する場合や、エンド ユーザの // 入力を受け付ける際にラベルを使用すると便利です。 This.InsertItemLast(handle, & tvi_root.Label + " 音楽 " & + tvi_current.Label + String(ct), 3) NEXT END IF 126 PowerBuilder 第8章 ツリービュー コントロールの使い方 ツリービューの項目の管理 ツリービューの各項目が TreeViewItem 構造体になります。この構造体 で項目のプロパティを設定し、ツリービューに項目を挿入する方法に ついては、前節を参照してください。 以下のコードは、TreeViewItem 構造体を宣言し、一部のプロパティを 設定します。 TreeViewItem tvi_defined tvi_defined.Label = "Symphony No. 3 Eroica" tvi_defined.StatePictureIndex = 0 tvi_defined.PictureIndex = 3 tvi_defined.SelectedPictureIndex = 4 tvi_defined.OverlayPictureIndex = 0 tvi_defined.Children = TRUE ピクチャ プロパティについては、136 ページの「ツリービュー ピク チャの管理」を参照してください。 項目を挿入すると、挿入関数によってその項目に対するハンドルが戻 されます。TreeViewItem 構造体がツリービュー コントロールにコピー されるので、その項目のプロパティにアクセスする必要はありません。 itemhandle = This.InsertItemLast(parenthandle, & tvi_defined) 項目の取得、変更、設 定 ツリービュー項目のプロパティを変更したい場合には、以下の操作を 実行します。 1 その項目を取得し、TreeViewItem 構造体に割り当てます。 2 TreeViewItem プロパティを設定して変更します。 3 項目を設定し、ツリービューにコピーして戻します。 ツリービューに挿入された項目を処理する場合、そのハンドルを操作 します。大部分のツリービュー イベントでは、引数として 1 つまたは 2 つのハンドルを渡します。このハンドルによって、エンド ユーザが 処理している項目を識別します。 Clicked イベントに対する以下のコードは、エンド ユーザがクリックした 項目のハンドルを使用して、開発者がプロパティを変更した TreeViewItem 構造体にその項目をコピーして戻します。 treeviewitem tvi This.GetItem(handle, tvi) tvi.OverlayPictureIndex = 1 This.SetItem(handle, tvi) アプリケーション テクニック 127 ツリービューの項目の管理 重要 項目のプロパティを変更した後は、必ず SetItem 関数を呼び出してくだ さい。SetItem 関数を呼び出さないと、ツリービューの表示が変更され ません。 項目と階層 FindItem 関数と項目のハンドルを使用して、 ツリービューで構造体を調 べることができます。項目のプロパティでレベルはわかりますが、親 項目はわかりません。FindItem 関数によって、その項目がどの親項目の 下にあるかがわかります。 long h_parent h_parent = This.FindItem(ParentTreeItem!, handle) FindItem 関数を使用して子項目を探したり、 レベルに関係なく現在表示 されている項目の中から検索したりすることができます。 詳細については、 『PowerScript リファレンス』マニュアルの FindItem 関 数に関する節を参照してください。 スクリプトによるツ リービュー機能の制御 スクリプトを作成しなくても、ツリービューのプロパティを設定して、 項目の削除や名前の変更などのユーザ操作を使用可能 / 使用禁止にで きますが、関数を呼び出すことによってこれらのユーザ操作を制御す ることもできます。以下のことを行うことができます。 • 項目の削除 • 項目の名前の変更 • ドラッグ アンド ドロップによる項目の移動 • 項目のソート 項目の削除 エンド ユーザが項目を削除できるようにするためには、ツリービューの DeleteItems プロパティを使用可能にします。エンド ユーザが〔Delete〕 を押すと、選択した項目が削除され、DeleteItem イベントが起動され ます。子項目もすべて削除されます。 詳細項目のみ削除するなど、削除対象をより細かく指定したい場合は、 プ ロ パ テ ィ を 設 定 す る か わ り に DeleteItem 関 数 を 呼 び 出 し ま す。 DeleteItem 関数を呼び出した場合も、DeleteItem イベントが起動されま す。 128 PowerBuilder 第8章 例 ツリービュー コントロールの使い方 TreeView ユーザ イベントに対するスクリプトを以下に示します。イベ ント ID は pbm_keydown で、ツリービューにフォーカスがある場合に キーを押すと起動されます。このスクリプトによって、〔Delete〕が押 されたかどうか、また、選択された項目が詳細項目かどうかをチェッ クします。両方とも TRUE だった場合にその項目を削除します。 ツリービューの DeleteItems プロパティの値は FALSE にします。TRUE になっていると、コードの内容にかかわらず、エンド ユーザが任意の 項目を削除できます。 TreeViewItem tvi long h_item IF KeyDown(KeyDelete!)= TRUE THEN h_item = This.FindItem(CurrentTreeItem!, 0) This.GetItem(h_item, tvi) IF tvi.Level = 3 THEN This.DeleteItem(h_item) END IF END IF RETURN 0 項目の名前の変更 ツリービューの EditLabels プロパティが使用可能な場合、エンド ユー ザが項目のラベルを 2 回クリックすると、ラベルの編集状態になりま す。 イベント ラベルの編集には以下の 2 つのイベントが関連付けられています。 BeginLabelEdit イベントは、EditLabels プロパティが設定されている場 合、または EditLabel 関数を呼び出したときに、2 回目のクリックの後 で起動されます。戻り値が 1 の場合は編集できないようにすることが できます。 BeginLabelEdit イベントに対する以下のスクリプトでは、レベル 2 の項 目のラベルは変更できません。 TreeViewItem tvi This.GetItem(handle, tvi) IF tvi.Level = 2 THEN RETURN 1 ELSE RETURN 0 END IF アプリケーション テクニック 129 ツリービューの項目の管理 EndLabelEdit イベントは、エンド ユーザが、 〔Enter〕を押す、別の項 目をクリックする、別のコントロールのテキスト入力エリアをクリッ クする、のいずれかによって編集を終了したときに起動されます。 EndLabelEdit イベントに対するスクリプトを作成することにより、ユー ザの変更が適切かどうかを確認できます(たとえば、スペル チェッカー を起動できます)。 EditLabel 関数 エンド ユーザによるラベルの編集を制限するために、上記のような方 法で、BeginLabelEdit イベントを使用してラベルの編集を禁止すること ができます。ラベルを編集可能にしたい場合は、EditLabels プロパティ を FALSE に設定し、EditLabel 関数を呼び出します。 EditLabel 関数を呼び出すと、 編集を開始したときには BeginLabelEdit イ ベントが、エンド ユーザが〔Enter〕を押したとき、あるいは別の項目 をクリックしたときには EndLabelEdit イベントが起動されます。 CommandButton イベントに対する以下のコードによって、現在の項目 が編集モードになります。 long h_tvi h_tvi = tv_1.findItem(CurrentTreeItem!, 0) tv_1.EditLabel(h_tvi) ドラッグ アンド ドロップによる項目の移動 PowerBuilder では、ウィンドウ レベルでコントロールをほかのコント ロールにドラッグするための関数とプロパティが用意されています。 ツリービュー内でエンド ユーザが項目をほかの項目にドラッグでき るようにすることもできます。エンド ユーザは、項目をソートする、 別の分岐に移動する、親項目の下に子項目を配置する、などの場合に ドラッグを利用できます。 項目の移動方法としてドラッグ アンド ドロップを実装した場合、ド ラッグされた項目が兄弟項目になるのか子項目になるのか、移動する のかコピーするのか、また、子項目も一緒に移動するのかを指定しま す。 表 8-4 に、ドラッグ アンド ドロップを実装する際に指定するプロパ ティとイベントを示します。 130 PowerBuilder 第8章 ツリービュー コントロールの使い方 表 8-4: ドラッグ アンド ドロップのプロパティとイベント プロパティまたは イベント DragAuto プロパティ 設定と目的 TRUE または FALSE FALSE の場合、BeginDrag イベントで Drag 関数を呼 び出さなければならない DisableDragDrop プロ パティ DragIcon プロパティ BeginDrag イベント DragWithin イベント DragDrop イベント 例 FALSE 適切なアイコン または None!(ユーザがアイテムの画像をドラッグする) ドラッグされた項目のハンドルを保存し、オプショ ンで特定の項目をドラッグできないようにするスク リプト ドロップ先をハイライト表示するスクリプト ドラッグ操作の結果を実装するスクリプト ドラッグ アンド ドロップの実装が成功する鍵は、詳細項目にありま す。この節では、項目を移動する方法について説明します。以下の例 では、ドラッグされた項目はドロップ先の兄弟項目になり、ドロップ 先の項目の後に挿入されます。子項目も一緒に移動され、元の項目は 削除されます。 関数を繰り返し呼び出すことにより、レベルの数にかかわらず、すべ てのレベルの子項目が移動されます。無限ループを避けるため、項目 が自分自身の子項目になることはできません。すなわち、ドラッグす る項目の子項目にドロップすることはできません。 BeginDrag イベント 以下のスクリプトは、ドラッグする項目のハンド ルをインスタンス変数に保存します。 ll_dragged_tvi_handle = handle 特定のレベルの項目のような一部の項目をドラッグできないようにし たい場合、以下のようなコードを作成します。 TreeViewItem tvi This.GetItem(handle, tvi) IF tvi.Level = 3 THEN This.Drag(Cancel!) DragWithin イベント 以下のスクリプトは、エンド ユーザがドロップ 先を確認できるように、カーソル位置の項目をハイライト表示します。 ドロップ先の項目が制限される場合には、その項目がドロップ先とし て適切かどうかをチェックしてからハイライト表示します。以下の例 では、ドラッグする項目の親項目かどうかをチェックし、親項目でな い場合のみハイライト表示します。 アプリケーション テクニック 131 ツリービューの項目の管理 TreeViewItem tvi This.GetItem(handle, tvi) tvi.DropHighlighted = TRUE This.SetItem(handle, tvi) 以下のスクリプトによって移動処理を実行しま す。選択した位置にその項目を挿入できるかどうかをチェックして、 新しい位置に(ドロップ先の兄弟項目として)ドラッグされた項目を 挿入します。その後で、ドラッグされた項目の子項目も移動する関数 を呼び出します。 DragDrop イベント TreeViewItem tvi_src, tvi_child long h_parent, h_gparent, h_moved, h_child integer rtn // ドラッグされた項目の TreeViewItem を取得します。 This.GetItem(ll_dragged_tvi_handle, tvi_src) // その項目の分岐先には移動できません。 // すなわち、その項目の子項目にはなれません。 h_gparent = This.FindItem(ParentTreeItem!, handle) DO WHILE h_gparent <> -1 IF h_gparent = ll_dragged_tvi_handle THEN MessageBox(" ドラッグできません ", & " 子項目にすることはできません ") RETURN 0 END IF h_gparent=This.FindItem(ParentTreeItem!, h_gparent) LOOP // 挿入先の親項目を取得します。 h_parent = This.FindItem(ParentTreeItem!, handle) // ドロップ先がレベル 1 のため親項目がない場合は 0 を使用します。 IF h_parent = -1 THEN h_parent = 0 // ドロップ先の後に項目を挿入します。 h_moved = This.InsertItem(h_parent, handle, tvi_src) IF h_moved = -1 THEN MessageBox(" ドラッグできません ", " 項目は移動できません ") RETURN 0 ELSE // 引数 :old parent、new parent rtn = uf_movechildren(ll_dragged_tvi_handle, & h_moved) 132 PowerBuilder 第8章 ツリービュー コントロールの使い方 // すべての子項目の移動が完了したら、 // 元の項目を削除します。 IF rtn = 0 THEN This.DeleteItem(ll_dragged_tvi_handle) END IF END IF 上記の DragDrop イベントのスクリプトでは、uf_movechildren 関数を呼 び出します。この関数は、ドラッグされた項目のすべてのレベルの子 項目が移動されるまで、繰り返しその関数自身を呼び出します。 // // // // // // // // // 関数 :uf_movechildren 引数 : oldparent - 子項目が移動された 項目のハンドル。最初は、別の位置にある 項目(ドラッグされる項目) newparent - 子項目の移動先 項目のハンドル。最初は、別の位置にある 項目(ドラッグされる項目) long h_child, h_movedchild TreeViewItem tvi // 挿入が失敗した場合は戻り値 -1 // 子項目があるか? h_child = tv_2.FindItem(ChildTreeItem!, oldparent) IF h_child <> -1 THEN tv_2.GetItem(h_child, tvi) h_movedchild = tv_2.InsertItemLast(newparent, tvi) IF h_movedchild = -1 THEN RETURN -1 // 子項目の子がある場合は移動します。 uf_movechildren(h_child, h_movedchild) // 元のレベルで、ほかに子項目がないかどうかをチェックします。 h_child = tv_2.FindItem(NextTreeItem!, h_child) DO WHILE h_child <> -1 tv_2.GetItem(h_child, tvi) h_movedchild= tv_2.InsertItemLast(newparent,tvi) IF h_movedchild = -1 THEN RETURN -1 uf_movechildren(h_child, h_movedchild) // 元のレベルに子項目が残っているか ? h_child = tv_2.FindItem(NextTreeItem!, h_child) アプリケーション テクニック 133 ツリービューの項目の管理 LOOP END IF RETURN 0 // すべての子項目の移動完了 項目のソート ツリービューの機能を使用して自動的にソートするか、開発者が手動 でソートを制御することができます。手動ソートでは、ラベルをアル ファベット順にソートできるほか、ソート条件を定義してユーザ定義 のソートを実装することもできます。SortType プロパティでソート方 法を制御します。このプロパティの値は、カタログ データ型 grSortType です。 自動アルファベット順ソート テキスト ラベルをソートするには、SortType プロパティを Ascending! または Descending! に設定します。挿入された 項目が自動的にソートされます。 手動アルファベット順ソート ソート条件をより細かく指定するには、 SortType を Unsorted! に設定し、表 8-5 の関数を呼び出してソートを実 行します。 表 8-5: ツリービューのソート関数 使用する関数 InsertItemSort Sort SortAll 処理内容 可能な場合には、アルファベット順で適切な位置に項 目を挿入する その項目のすぐ下の子項目をソートする その項目の分岐をすべてソートする ユーザが項目をドラッグしてリストを作成した場合、ソートは使用禁 止にしておく必要があります。 ラベル以外によるソート ラベル以外で項目をソートするには、 UserDefinedSort! に SortType プロパティを設定して Sort イベントに対す るスクリプトを作成し、ユーザ定義のソートを実装します。そのスク リプトでソートする方法を指定します。 並べ替えを試みるたびに Sort イベントが起動されます。Sort スクリプ トは、どの項目がほかの項目より大きいかを示す値を戻します。この スクリプトによって、項目の種類ごとに異なる基準でソートすること ができます。たとえば、レベル 2 の項目を、レベル 3 の項目とは異な る基準でソートできます。項目を挿入すると常にツリービューがソー トされます。 134 PowerBuilder 第8章 Sort イベントの例 ツリービュー コントロールの使い方 以下のサンプル スクリプトでは、第 1 レベルを Data プロパティの値 で、それ以外のレベルをラベルのアルファベット順にソートします。 Data プロパティにはその作曲家の世紀が登録されているので、第 1 レ ベルでは作曲家が年代順に並べられます。 // 戻り値 //-1 handle 1 は handle 2 より古い // 0 handle 1 と handle 2 は同じ // 1 handle 1 は handle 2 より新しい TreeViewItem tvi1, tvi2 This.GetItem(handle1, tvi1) This.GetItem(handle2, tvi2) IF tvi1.Level = 1 THEN // Data プロパティに登録されている世紀を比較 IF tvi1.data > tvi2.Data THEN RETURN 1 ELSEIF tvi1.data = tvi2.Data THEN RETURN 0 ELSE RETURN -1 END IF ELSE // ほかのレベルをアルファベット順にソート IF tvi1.Label > tvi2.Label THEN RETURN 1 ELSEIF tvi1.Label = tvi2.Label THEN RETURN 0 ELSE RETURN -1 END IF END IF アプリケーション テクニック 135 ツリービュー ピクチャの管理 ツリービュー ピクチャの管理 ツリービューの画像は、以下の 3 つの画像リストに保存されます。 • ピクチャ リスト(ここでは標準ピクチャ リストと呼びます) • 状態ピクチャ リスト • オーバーレイ ピクチャ リスト これらのリストにピクチャを追加して、ツリービューの項目と関連付 けます。 項目のピクチャ ツリービューでピクチャを使用するにはいくつかの方法があります。 表 8-6 に示されている項目のピクチャ プロパティを設定することによ り、ピクチャ リストにあるピクチャを項目と関連付けます。 表 8-6: ツリービュー ピクチャ プロパティ プロパティ PictureIndex StatePictureIndex 目的 その項目に関連付けられている主ピクチャ。ラベルの 左横に表示される 標準ピクチャの左側に表示される状態ピクチャ。状態 ピクチャを表示するスペースだけ項目が右に移動さ れる。Checkboxes プロパティが TRUE である場合は、 状態ピクチャは一組のチェックボックスに置き換え られる 状態ピクチャによって項目の位置がずれるので、状態 ピクチャがある項目とない項目では位置が揃わない。 すべての項目を揃えるには、空白の状態ピクチャを使 用するとよい OverlayPictureIndex エンド ユーザが選択した項目の横にチェックマーク を付ける場合などに状態ピクチャを使用する 標準ピクチャの上に表示されるオーバーレイ ピク チャ オーバーレイ ピクチャ リストに標準ピクチャ リスト のピクチャを割り当てるスクリプトによってオー バーレイ ピクチャを設定する オーバーレイ ピクチャは標準ピクチャと同じサイズ だが、標準ピクチャ全体に重ならないように、一部を 使用する場合が多い。Windows のエクスプローラで ショートカット アイテムを示す矢印などがオーバー レイ ピクチャである 136 PowerBuilder 第8章 プロパティ SelectedPictureIndex ツリービュー コントロールの使い方 目的 標準ピクチャ リストから選択したピクチャ。その項 目が現在の項目であるときに、標準ピクチャのかわり に表示される。エンド ユーザが別の項目を選択する と、最初の項目にその標準ピクチャが割り当てられ、 新しい項目に選択したピクチャが表示される 現在の項目であるときにも異なるピクチャを使用する 必要がない場合は、SelectedPictureIndex を PictureIndex と同じ値に設定する ピクチャの設定方法 . SetLevelPictures 関数を使用して、特定のレベルに属 するすべての項目のピクチャを変更することができます。あるいは、 項目ごとにピクチャ プロパティを設定できます。 ピクチャが必要ない場合 ツリービューの項目に必ずピクチャを付ける 必要はありません。その項目のピクチャ インデックスが 0 の場合、ピ クチャは表示されません。ただし、ツリービューでは常に、標準ピク チャ用のスペースが用意されています。PictureWidth プロパティを 0 に 設定すると、このスペースが削除されます。 tv_2.DeletePictures() tv_2.PictureWidth = 0 ピクチャ リストの設定 ペインタを使用して、あるいは実行時に、標準ピクチャ リストと状態 ピクチャ リストにピクチャを追加できます。実行時には、標準ピク チャ リストのピクチャをオーバーレイ リストに割り当てることがで きます。 マスクの色 マスクの色とは、ピクチャで使用される色の 1 つで、ツリービューに ピクチャが表示されるときには透明になります。通常は、ピクチャを ツリービューの色と合成できるように、ピクチャの背景色を使用しま す。 ペインタまたはスクリプトでピクチャを追加する前に、そのピクチャ に合わせてマスクの色を設定できます。以下のステートメントでは、 ピクチャの背景色が白なので、マスクの色を白に設定します。 tv_1.PictureMaskColor = RGB(255, 255, 255) ピクチャにはそれぞれ独自のマスクの色があります。ピクチャを挿入 するときに、この色が表示されます。ピクチャのマスクの色を変更す るには、そのピクチャを削除して追加し直さなければなりません。 アプリケーション テクニック 137 ツリービュー ピクチャの管理 画像サイズ ペインタで、各ピクチャ タブの Height と Width プロパティを設定する ことにより、随時画像サイズを変更できます。リスト内のピクチャは すべて、指定したサイズに拡大されます。 実行時には、リストが空の場合のみ、ピクチャ リストの画像サイズを 変更できます。DeletePictures 関数と DeleteStatePictures 関数でリストを 消去できます。 例 以下のサンプル コードは、実行時にプロパティを変更して標準ピク チャ リストにピクチャを追加する方法を示すものです。状況ピクチャ の場合もこのコードを応用してください。 tv_list.DeletePictures() tv_list.PictureHeight = 32 tv_list.PictureWidth = 32 tv_list.PictureMaskColor = RGB(255.255.255) tv_list.AddPicture("c:\apps_pb\kelly.bmp") tv_list.PictureMaskColor = RGB(255,0,0) tv_list.AddPicture("Custom078!") tv_list.PictureMaskColor = RGB(128,128,128) tv_list.AddPicture("Custom044!") ピクチャの削除による 既存の項目への影響 ピクチャ リストからピクチャを削除したときに、表示されている項目 のピクチャに予期せぬ変化が起こる場合があります。ピクチャを削除 すると、リストの空白を埋めるために、リスト内の残りのピクチャが 移動されます。これにより、それらのピクチャには異なるインデック ス値が割り当てられます。つまり、これらのインデックスを使用する 項目に、従来とは異なる画像が関連付けられるということです。 オーバーレイ リストは独立したリストではなく、標準ピクチャをポイ ントしているだけなので、標準ピクチャ リストからピクチャを削除す ると、オーバーレイ リストにも影響があります。 このように項目のピクチャが変更されるのを防ぐには、その項目のピ クチャ インデックスを使用した後はピクチャを削除しない方がよい でしょう。 オーバーレイ ピクチャの使い方 オーバーレイ リストのピクチャは、標準ピクチャ リストに対応してい ます。まず、ペインタを使用して、または実行時に、標準リストにピ クチャを追加しなければなりません。次に、実行時にオーバーレイ ピ クチャ リストにピクチャを指定します。その後で、SetLevelPictures 関 数を使うか、個別にピクチャを項目に割り当てます。 138 PowerBuilder 第8章 ツリービュー コントロールの使い方 以下のコードでは、標準ピクチャ リストにピクチャを追加してから、 そのピクチャをオーバーレイ リストに割り当てます。 integer idx idx = tv_1.AddPicture("Custom085!") IF tv_1.SetOverlayPicture(1, idx) <> 1 THEN sle_get.Text = "Setting overlay picture failed" END IF Clicked イベントに対する以下のコードは、エンド ユーザがその項目を クリックするごとにオーバーレイ ピクチャの表示 / 非表示を切り替え ます。 treeviewitem tvi This.GetItem(handle, tvi) IF tvi.OverlayPictureIndex = 0 THEN tvi.OverlayPictureIndex = 1 ELSE tvi.OverlayPictureIndex = 0 END IF This.SetItem(handle, tvi) データウィンドウのデータのツリービューへの表示 データウィンドウから取り出したデータを使用して、ツリービュー コ ントロールを表示するのもよい方法です。このためには、アプリケー ションで以下の操作を実行しなければなりません。 • データストアを宣言してインスタンスを作成し、データウィンド ウ オブジェクトを割り当てる • 必要に応じてデータを取り出す • 取り出されたデータを使用してツリービューを表示する • 処理が完了したらデータストアのインスタンスを破棄する ツリービューでは異なるレベルで異なる種類のデータを表示できるの で、レベルごとに追加のデータウィンドウを定義できます。これらの データウィンドウは、通常異なるテーブル(関連するテーブル)を参 照します。分岐を開くと、その項目は子項目を取得するための検索引 数になります。 アプリケーション テクニック 139 データウィンドウのデータのツリービューへの表示 第 1 レベルの表示 以下の例では、作曲家リストのツリービューを表示します。ツリー ビューの第 2 レベルには、その作曲家の楽曲が表示されます。データ ベースには、作曲家名と、 (作曲家名を外部キーとする)楽曲名の 2 つ のテーブルがあります。 この例では、ツリービュー コントロールを表示するウィンドウ用に、 以下の 2 つのデータストア インスタンス変数を宣言します。 datastore ids_data, ids_info この例では、ツリービュー コントロールの Constructor イベントを使用 して以下の処理を行います。 • データストアのインスタンスを作成する • 作成したインスタンスをデータウィンドウに関連付け、データを 取り出す • 取り出されたデータを使用してツリービューのルート レベルを表 示する // tv_1 に対する Constructor イベント treeviewitem tvi1, tvi2 long ll_lev1, ll_lev2, ll_rowcount, ll_row // データストアのインスタンス変数を作成します。 ids_data = CREATE datastore ids_data.DataObject = "d_composers" ids_data.SetTransObject(SQLCA) ll_rowcount = ids_data.Retrieve() // ツリービューの第 1 レベルを作成します。 tvi1.PictureIndex = 1 tvi1.Children = TRUE // データストアから取り出されたデータで // ツリービューを表示します。 FOR ll_row = 1 to ll_rowcount tvi1.Label = ids_data.GetItemString(ll_row, & 'name') This.InsertItemLast(0, tvi1) NEXT 140 PowerBuilder 第8章 第 2 レベルの表示 ツリービュー コントロールの使い方 エンド ユーザがルート レベルの項目を開くと、ItemPopulate イベント が起動されます。このイベントに対するスクリプトで、以下の処理を 行います。 • 2 番目のデータストアのインスタンスを作成する そのデータウィンドウで、作曲家名を楽曲名テーブルの検索引数 として使用します。 • 選択した作曲家に楽曲名を子項目として挿入する ItemPopulate のハンドル引数は、新しい項目の親項目になります。 // tv_1 に対する ItemPopulate イベント TreeViewItem tvi1, tvi2 long ll_row, ll_rowcount // データストアのインスタンス変数を作成します。 ids_info = CREATE datastore ids_info.DataObject = "d_music" ids_info.SetTransObject(SQLCA) // 表示されている項目のラベルを // 検索引数として使用します。 This.GetItem(handle, tvi1) ll_rowcount = ids_info.Retrieve(tvi1.Label) // データベースから取り出されたデータを使用して // 開かれた項目を表示します。 FOR ll_row = 1 to ll_rowcount This.InsertItemLast(handle, & ids_info.GetItemString(ll_row, & music_title'), 2) NEXT データストア インス タンスの破棄 ツリービュー コントロールが表示されているウィンドウを閉じると きに、以下のコードでデータストアのインスタンスを破棄します。 // w_treeview に対する Close イベント DESTROY ids_data DESTROY ids_info アプリケーション テクニック 141 データウィンドウのデータのツリービューへの表示 142 PowerBuilder 第 9 章 ウィンドウでのリストの使い方 この章について この章では、アプリケーションにおいて情報を提示するリストの 使い方について説明します。 内容 項目 リストの提示について リストの使い方 ドロップダウン リストの使い方 リストビュー コントロールの使い方 ページ 143 144 149 152 リストの提示について アプリケーションでリストを提示する複数の方法があります。 アプリケーション テクニック • リストボックスとピクチャ リストボックスは、テキストの表 示とアクションの起動ができます。選択肢を表示して、エン ド ユーザに選択させます。 • ドロップダウン リストボックスとドロップダウン ピクチャ リ ストボックスも、選択肢を表示します。また、エンド ユーザ に表示しているテキストを編集させることもできます。ド ロップダウン リストボックスはテキストだけのリストです。 ドロップダウン ピクチャ リストボックスはテキストとピク チャを一緒に表示します。 • リストビュー コントロールは、ピクチャとテキストの両方を 一 緒 にリ ス ト に し て 提 示し ま す。エ ン ド ユ ー ザ に リス ト ビューの項目を追加、削除、編集、および再配置させること ができます。また、リストビューの項目を使用してアクショ ンを起動させることもできます。 143 リストの使い方 ツリービュー コントロール ツリービュー コントロールも、ピクチャとテキストを一緒にリストに 提示します。リストビュー コントロールとの違いは、ツリービュー コ ントロールは、ツリービュー項目間の階層的な関係を表示することで す。リストビュー コントロールと同じように、エンド ユーザにツリー ビュー項目を追加、削除、編集、および再配置させることができます。 また、アクションを起動させることもできます。 ツリービューの詳細については、第 8 章「ツリービュー コントロール の使い方」を参照してください。 リストの使い方 リストを使用して、エンド ユーザに、スクロールできる簡単なリスト で情報を提示できます。ピクチャ リストボックスは、テキストとピク チャの情報を提示できます。また、リストボックスは、テキストの情 報だけを提示できます。 アプリケーションの設計にもよりますが、エンド ユーザは、1 つまた はそれ以上のリスト項目を選択して、その選択に基づいたアクション を実行できます。 ウィンドウにリストボックス コントロールまたはピクチャ リスト ボックス コントロールを追加するには、ほかのコントロールを追加す るのと同様の方法で行います。つまり、 [挿入|コントロール]メニュー から[リストボックス]または[ピクチャ リストボックス]を選択し て、ウィンドウ上の配置したい位置でクリックします。 ペインタで追加 新規項目を追加するには、コントロールの[項目]プ リスト コントロール への項目の追加 ロパティ ページを使用します。 ❖ リストボックスまたはピクチャ リストボックスに項目を追加するには 1 コントロールのプロパティ ビューで[項目]タブを選択します。 2 リストボックスの項目名を入力します。さらに、ピクチャ リスト ボックスの場合は、項目にピクチャを関連付けるため、ピクチャ インデックスを[ピクチャ インデックス]ボックスに入力します。 ピクチャ リストボックスにピクチャを追加する方法については、 145 ページの「ピクチャ リストボックス コントロールへのピク チャの追加」を参照してください。 144 PowerBuilder 第9章 ウィンドウでのリストの使い方 スクリプトで追加 実行時に、リストボックスまたはピクチャ リスト ボックスに項目を動的に追加するには、AddItem 関数と InsertItem 関数 を使用します。AddItem 関数は、リストの最後に項目を追加します。し かし、リストがソートされると、その項目はソート順の該当する位置 に移動されます。リスト中で項目が挿入される位置を指定したい場合 は、InsertItem 関数を使用します。 表 9-1: InsertItem 関数と AddItem 関数の使用 関数 InsertItem 指定する内容 項目名 項目の挿入位置 AddItem (ピクチャ リストボックスの場合)ピクチャ インデックス 項目名 (ピクチャ リストボックスの場合)ピクチャ インデックス たとえば、以下のスクリプトでは、リストボックスに項目を追加します。 This.AddItem (" 小物 ") This.InsertItem (" ソフトウェア ",2) This.InsertItem (" ハードウェア ",2) This.InsertItem (" ドキュメント ",2) 以下のスクリプトでは、ピクチャ リストボックスに項目とピクチャを 追加します。 This.AddItem (" モニタ ",2) This.AddItem (" モデム ", 3) This.AddItem (" プリンタ ",4) This.InsertItem (" スキャナ ",5,1) Sort プロパティの使い方 リスト項目が常にアルファベットの昇順に並ぶようにするには、コン トロールの Sort プロパティに TRUE を設定するか、 [全般]プロパティ ページで[ソート]チェックボックスをオンにします。 ペインタで追加 ピクチャを追加するには、コントロールの[ピクチャ] プロパティ ページと[項目]プロパティ ページを使用します。 ピクチャ リストボッ クス コントロールへ のピクチャの追加 ❖ ピクチャ リストボックスにピクチャを追加するには 1 2 アプリケーション テクニック コントロールのプロパティ ビューで[ピクチャ]タブを選択します。 ドロップダウン リストボックスからピクチャを選択するか、参照 ([...])ボタンをクリックして、ビットマップ、ポインタ、または アイコン ピクチャを選択します。 145 リストの使い方 3 [ピクチャのマスク色]ドロップダウン リストボックスからピクチャ の色を選択します。 ピクチャ マスクに選択した色は、ピクチャ リストボックスでは透 明に見えます。 4 ピクチャの高さと幅を選択します。 これで、ピクチャ リストボックスのピクチャのサイズを調整します。 動的にピクチャ サイズを変更する スクリプトで、実行時にピクチャのサイズを変更できます。ピク チャ リストボックスにピクチャが 1 つも追加されていない場合だ け、PictureHeight プロパティと PictureWidth プロパティを設定でき ます。 PictureHeight プロパティと PictureWidth プロパティの詳細につい ては、 『PowerScript リファレンス』マニュアルを参照してください。 5 ピクチャ リストボックスで使用する各ピクチャに対して処理を繰 り返します。 6 [項目]タブを選択し、各項目の[ピクチャ インデックス]を適切 な数字に変更します。 スクリプトで追加 実行時に、ピクチャ リストボックスにピクチャを動 的に追加するには、AddPicture 関数を使用します。以下の例では、ピク チャのサイズを設定し、ピクチャ リストボックスにビットマップ ファ イルを追加して、ピクチャ リストボックスに項目を追加します。 This.PictureHeight = 75 This.PictureWidth = 75 This.AddPicture ("c:\ArtGal\bmps\butterfly.bmp") This.AddItem("Aine Minogue",8) ピクチャ リスト コン トロールからのピク チャの削除 ピクチャ リストボックスまたはドロップダウン ピクチャ リストボッ クスのいずれかからピクチャを削除するには、DeletePicture 関数と DeletePictures 関数を使用します。 DeletePicture 関数を使用する場合、削除したいピクチャのピクチャ イ ンデックスを指定する必要があります。 例 This.DeletePicture (1) コントロールから最初のピクチャを削除します。次に、 This.DeletePictures () 146 PowerBuilder 第9章 ウィンドウでのリストの使い方 コントロールからすべてのピクチャを削除します。 以下のウィンドウには、リストボックスとピクチャ リストボック スがあります。リストボックスの項目は 4 つあり、ピクチャ リスト ボックスの項目は 1 つあります。 例 エンド ユーザがリストボックスの項目をダブルクリックすると、スク リプトは以下を実行します。 • ピクチャ リストボックスからすべての項目を削除する • ダブルクリックされたリストボックスの項目に関連する項目を、 ピクチャ リストボックスに新しく追加する 以下は、リストボックスの DoubleClicked イベントに対するスクリプト です。 int li_count // ピクチャ リストボックスの // 項目数を取得します。 li_count = plb_1.totalItems() // // // // // アプリケーション テクニック どの項目がダブルクリックされたかを判別します。 次に * ピクチャ リストボックスからすべての項目を削除します。 * ダブルクリックされた項目に 関連する項目を追加します。 147 リストの使い方 CHOOSE CASE index CASE 1 DO WHILE plb_1.totalitems() > 0 plb_1.DeleteItem(plb_1.totalitems()) LOOP plb_1.AddItem(" モニタ ",2) plb_1.AddItem(" モデム ",3) plb_1.AddItem(" プリンタ ",4) plb_1.InsertItem(" スキャナ ",5,1) CASE 2 DO WHILE plb_1.totalitems() > 0 plb_1.DeleteItem(plb_1.totalitems()) LOOP plb_1.InsertItem(" グリーンバー ",6,1) plb_1.InsertItem(" レターヘッド ",7,1) plb_1.InsertItem(" コピー ",8,1) plb_1.InsertItem("50 lb.",9,1) CASE 3 DO WHILE plb_1.totalitems() > 0 plb_1.DeleteItem(plb_1.totalitems()) LOOP plb_1.InsertItem("SpreadIt!",10,1) plb_1.InsertItem("WriteOn!",11,1) plb_1.InsertItem("WebMaker!",12,1) plb_1.InsertItem("Chessaholic",13,1) CASE 4 DO WHILE plb_1.totalitems() > 0 plb_1.DeleteItem(plb_1.totalitems()) LOOP plb_1.InsertItem("AlnaWarehouse",14,1) plb_1.InsertItem("AlnaInfo",15,1) plb_1.InsertItem("Info9000",16,1) plb_1.InsertItem("AlnaThink",17,1) END CHOOSE 148 PowerBuilder 第9章 ウィンドウでのリストの使い方 ドロップダウン リストの使い方 ドロップダウン リストは、エンド ユーザに簡単なリストで情報を提示 できるもう 1 つの方法です。ドロップダウン リストボックスではテキ ストだけを提示したり、ドロップダウン ピクチャ リストボックスでは テキストとピクチャを提示したりできます。ドロップダウン リスト ボックスおよびドロップダウン ピクチャ リストボックス コントロー ルをウィンドウに追加する方法は、ほかのコントロールを追加する方 法と同じです。つまり、 [挿入|コントロール]メニューから[ドロッ プダウン リストボックス]または[ドロップダウン ピクチャ リスト ボックス]を選択して、ウィンドウ上の配置したい位置でクリックし ます。 項目を追加するには、コントロールの[項目]プロパ ティ ページを使用します。 ドロップダウン リス ト コントロールへの 項目の追加 ペインタで追加 ❖ ドロップダウン リストボックスまたはドロップダウン ピクチャ リストボッ クスに項目を追加するには 1 コントロールのプロパティ ビューで[項目]タブを選択します。 2 リストボックスの項目名を入力します。さらに、ピクチャ リスト ボックスの場合は、項目にピクチャを関連付けるため、ピクチャ インデックスを[ピクチャ インデックス]ボックスに入力します。 ドロップダウン ピクチャ リストボックスへのピクチャの追加方 法については、150 ページの「ドロップダウン ピクチャ リストボッ クス コントロールへのピクチャの追加」を参照してください。 実行時に、ドロップダウン リストボックスやドロップ ダウン ピクチャ リストボックスに動的に項目を追加するには、AddItem 関数や InsertItem 関数を使用します。 スクリプトで追加 AddItem 関数は、リストの最後に項目を追加します。しかし、リストが ソートされると、その項目はソート順の該当する位置に移動されます。 リスト中で項目が挿入される位置を指定したい場合は、InsertItem 関数 を使用します。 アプリケーション テクニック 149 ドロップダウン リストの使い方 表 9-2: InsertItem 関数と AddItem 関数の使用 関数 InsertItem AddItem 指定する内容 項目名 (ドロップダウン ピクチャ リストボックスの場合)ピクチャ インデックス 項目の挿入位置 項目名 (ドロップダウン ピクチャ リストボックスの場合)ピクチャ インデックス 以下の例では、ドロップダウン ピクチャ リストボックスの 1 番目、2 番 目、3 番目のそれぞれの位置に、項目を挿入します。 This.InsertItem ("Atropos", 2, 1) This.InsertItem ("Clotho", 2, 2) This.InsertItem ("Lachesis", 2, 3) 以下の例では、ドロップダウン ピクチャ リストボックスに 2 つの項目 を追加します。 this.AddItem ("Plasma", 2) this.AddItem ("Platelet", 2) Sort プロパティの使い方 リストの項目を常に昇順にソートするには、コントロールの Sort プロ パティに TRUE を設定します。 ペインタで追加 ピクチャを追加するには、リストビュー コントロール ドロップダウン ピク チャ リストボックス コントロールへのピク チャの追加 の[ピクチャ]と[項目]プロパティ ページを使用します。 ❖ ドロップダウン ピクチャ リストボックスにピクチャを追加するには 1 コントロールのプロパティ ビューで[ピクチャ]タブを選択しま す。 2 ドロップダウン リストボックスからピクチャを選択するか、参照 ([...])ボタンをクリックして、ビットマップ、ポインタ、または アイコン ピクチャを選択します。 3 [ピクチャのマスク色]ドロップダウン リストボックスからピクチャ の色を選択します。 ピクチャ マスクに選択した色は、ドロップダウン ピクチャ リスト ボックスでは透明に見えます。 150 PowerBuilder 第9章 4 ウィンドウでのリストの使い方 ピクチャの高さと幅をそれぞれ選択します。 これで、ドロップダウン ピクチャ リストボックスのピクチャのサ イズを調整します。 動的にピクチャ サイズを変更する ピクチャ サイズの変更を実行時に行うには、ドロップダウン ピク チ ャ リ ス ト ボ ッ ク ス の 作 成 時 に、PictureHeight プ ロ パ テ ィ と PictureWidth プロパティを設定してからピクチャを追加します。 PictureHeight プロパティと PictureWidth プロパティの詳細につい ては、 『PowerScript リファレンス』マニュアルを参照してください。 5 ドロップダウン ピクチャ リストボックスで使用する各ピクチャに対 して処理を繰り返します。 6 [項目]タブを選択し、各項目の[ピクチャ インデックス]を適切 な数字に変更します。 実行時に、ピクチャ リストボックスにピクチャを動 的に追加するには、AddPicture 関数を使用します。たとえば、以下の例 では、ピクチャ リストボックスに 2 つのビットマップ ファイルを追加 します。 スクリプトで追加 This.AddPicture ("c:\images\justify.bmp") This.AddPicture ("c:\images\center.bmp") ドロップダウン ピク チャ リストボックス コントロールからのピ クチャの削除 ドロップダウン ピクチャ リストボックス コントロールからのピクチャ の削除方法については、146 ページの「ピクチャ リスト コントロール からのピクチャの削除」を参照してください。 アプリケーション テクニック 151 リストビュー コントロールの使い方 リストビュー コントロールの使い方 リストビュー コントロールでは、いろいろな組み合わせでテキストと アイコンを表示できます。大きいアイコンや小さいアイコンをフリー フォーム形式で表示したり、一覧形式でリストを表示したりできます。 また、各リスト項目についての詳細情報を、リスト項目に関連する追 加カラムとしていっしょに表示できます。 リストビュー コントロールは、リストビュー項目で構成されます。そ れぞれのリストビュー項目は配列に格納されています。リストビュー 項目は、以下で構成されます。 リストビュー項目の名前 • ラベル • インデックス コントロールにおけるリストビュー項目の表示位置 • ピクチャ インデックス リストビュー項目に関連するピクチャの番 号 提示されるスタイルにもよりますが、大きいピクチャまたは小さ いピクチャは、リストビュー項目に関連付けることもできます。 • オーバーレイ ピクチャ インデックス リストビュー項目に関連付け るオーバーレイ ピクチャの番号 • 状態ピクチャ インデックス リストビュー項目に関連付ける状態ピ クチャの番号 リストビュー項目、ピクチャ インデックス、提示様式の詳細について は、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してくだ さい。 152 PowerBuilder 第9章 ウィンドウでのリストの使い方 リストビュー コント ロールの作成 ウィンドウにリストビュー コントロールを追加するには、ほかのコン トロールを追加するのと同様の方法で行います。つまり、 [挿入|コン トロール]メニューから[リストビュー]を選択して、ウィンドウ上 の配置したい位置でクリックします。 リストビュー項目の追 加 ペインタで追加 項目を追加するには、コントロールの[項目]プロパ ティ ページを使用します。 ❖ リストビューに項目を追加するには 1 コントロールのプロパティ ビューで[項目]タブを選択します。 2 リストビューに追加する項目のラベルとピクチャ インデックスを 入力します。 [項目]タブ ページのすべてのエントリを消去する 最初の項目のピクチャ インデックスをゼロに設定すると、タブ ページ上のすべての設定が消去されます。 リストビュー コントロールにピクチャを追加する方法の詳細につ いては、154 ページの「リストビュー コントロールへのピクチャ の追加」を参照してください。 スクリプトで追加 実行時に、リストビューに項目を動的に追加するに は、AddItem 関数と InsertItem 関数を使用します。リストビューに項目 を追加するために、AddItem 関数または InsertItem 関数を使用する場合 は、2 つの方法があります。 以下の例が示すように、ピクチャ インデックスとラベルを指定して、 項目を追加できます。 lv_1.AddItem("Item 1", 1) または、リストビュー、ラベル、およびピクチャ インデックスの項目 の表示位置を指定して、項目を挿入できます。 lv_1.InsertItem (1,"Item 2", 2) リストビュー項目を直接指定して追加することもできます。リスト ビューの DragDrop イベントに対する以下のスクリプトの例では、リス トビューにドラッグされたリストビュー項目を挿入します。 listviewitem lvi This.GetItem(index, lvi) lvi.label = "Test" lvi.pictureindex = 1 This.AddItem (lvi) アプリケーション テクニック 153 リストビュー コントロールの使い方 または、リストビューの表示位置とリストビュー項目を指定して、項 目を挿入できます。 listviewitem l_lvi //2 番目のリストビュー項目の情報を // 取得します。 lv_list.GetItem(2, l_lvi) // 項目のラベルを Entropy に変更します。 //5 番目の表示位置に 2 番目の項目を挿入します。 lv_list.InsertItem (5, l_lvi) lv_list.DeleteItem(2) PowerBuilder は 4 つのピクチャ リストに、リストビューのピクチャを 保持します。 リストビュー コント ロールへのピクチャの 追加 • 小さいピクチャ インデックス • 大きいピクチャ インデックス • 状態ピクチャ インデックス • オーバーレイ ピクチャ インデックス ペインタを使用するか、または実行時に AddItem 関数と InsertItem 関数 を使用してリストビューを作成した場合、上記のピクチャをリスト ビュー項目に関連付けることができます。 しかし、リストビュー項目にピクチャを関連付けるには、リストビュー コントロールにリストビュー項目が追加されていなければなりませ ん。 ペインタで追加 ピクチャを追加するには、リストビュー コントロール の[ピクチャ]と[項目]プロパティ ページを使用します。 ❖ リストビュー コントロールにピクチャを追加するには 1 コントロールのプロパティ ビューで、 [大きいピクチャ]、 [小さい ピクチャ]、または [状態]タブのいずれかを選択します。 オーバーレイ ピクチャ スクリプトでのみ、リストビュー コントロールにオーバーレイ ピ クチャを追加できます。 2 ドロップダウン リストボックスからピクチャを選択するか、参照 ([...])ボタンをクリックして、ビットマップ、ポインタ、または アイコン ピクチャを選択します。 3 [ピクチャのマスク色]ドロップダウン リストボックスからピクチャ の色を選択します。 154 PowerBuilder 第9章 ウィンドウでのリストの使い方 ピクチャ マスクに選択した色は、リストビューでは透明に見えま す。 ピクチャの高さと幅をそれぞれ選択します。 4 これで、リストビューのピクチャのサイズを調整します。 動的にピクチャ サイズを変更する ピクチャ サイズの変更を実行時に行うには、リストビューの作成 時に、PictureHeight プロパティと PictureWidth プロパティを設定 してからピクチャを追加します。PictureHeight プロパティと PictureWidth プロパティの詳細については、『PowerScript リファレ ンス』マニュアルを参照してください。 以下に対して処理を繰り返します。 5 • リストビューで使用するピクチャの種類(大きい、小さい、状 態)の数 • リストビューで使用する各ピクチャの種類に対応したピク チャの数 リストビューのピクチャリストにピクチャを追加す るには、表 9-3 に示されている関数を使用します。 スクリプトで追加 表 9-3: リストビュー ピクチャリストにピクチャを追加する関数 関数 AddLargePicture AddSmallPicture AddStatePicture ピクチャリストに追加するピクチャ 大きいピクチャ 小さいピクチャ 状態ピクチャ 大きいピクチャと小さいピクチャの追加 以下の例では、大きいピクチャ と小さいピクチャの高さと幅を設定して、大きいピクチャのピクチャ リストと小さいピクチャのピクチャ リストに 3 つのピクチャを追加し ます。 // 大きいピクチャの高さと幅を設定します。 lv_1.LargePictureHeight=32 lv_1.LargePictureWidth=32 // 大きいピクチャを追加します。 lv_1.AddLargePicture("c:\ArtGal\bmps\celtic.bmp") lv_1.AddLargePicture("c:\ArtGal\bmps\list.ico") lv_1.AddLargePicture("Custom044!") // 小さいピクチャの高さと幅を設定します。 アプリケーション テクニック 155 リストビュー コントロールの使い方 lv_1.SmallPictureHeight=16 lv_1.SmallPictureWidth=16 // 小さいピクチャを追加します。 lv_1.AddSmallPicture("c:\ArtGal\bmps\celtic.bmp") lv_1.AddSmallPicture("c:\ArtGal\bmps\list.ico") lv_1.AddSmallPicture("Custom044!") // リストビューに項目を追加します。 lv_1.AddItem("Item 1", 1) lv_1.AddItem("Item 2", 1) lv_1.AddItem("Item 3", 1) 項目のオーバーレイとして、大きいピク チャや小さいピクチャを使用するには、SetOverLayPicture 関数を使用し ます。以下の例では、リストビューに大きいピクチャを追加して、リ ストビュー項目のオーバーレイ ピクチャとして、大きいピクチャを使 用します。 オーバーレイ ピクチャの追加 listviewitem lvi_1 int li_index // リストビューに大きいピクチャを追加します。 li_index = lv_list.AddLargePicture & ("c:\ArtGal\bmps\dil2.ico") // 追加した大きいピクチャを // オーバーレイ ピクチャとして設定します。 lv_list.SetOverlayPicture (3, li_index) // リストビュー項目とともにオーバーレイ ピクチャを使用します。 lv_list.GetItem(lv_list.SelectedIndex (), lvi_1) lvi_1.OverlayPictureIndex = 3 lv_list.SetItem(lv_list.SelectedIndex (), lvi_1) 状態ピクチャの追加 以下の例では、選択されたリストビュー項目に状 態ピクチャを設定するために、項目の StatePictureIndex プロパティを使 用します。 listviewitem lvi_1 lv_list.GetItem(lv_list.SelectedIndex (), lvi_1) lvi_1.StatePictureIndex = 2 lv_list.SetItem(lv_list.SelectedIndex (), lvi_1) 156 PowerBuilder 第9章 リストビューの項目と ピクチャの削除 ウィンドウでのリストの使い方 DeleteItem 関数で、リストビューから項目を 1 つずつ削除できます。 DeleteItems 関数は、リストビューからすべての項目を削除します。同 様に、DeleteLargePicture 関数、DeleteSmallPicture 関数、DeleteStatePicture 関数で、特定の種類のピクチャを 1 つずつ削除できます。 DeleteLargePictures 関数、DeleteSmallPictures 関数、DeleteStatePictures 関 数は、特定の種類のピクチャをすべて削除します。 以下の例では、リストビューから、1 つの項目とすべての小さいピク チャを削除します。 int li_index li_index = This.SelectedIndex() This.DeleteItem (li_index) This.DeleteSmallPictures () ホット トラッキング とシングルまたはダブ ル クリックによるア クティブ化 ホット トラッキングでは、リストビュー コントロール内の項目の上に マウスが移動するとその項目の外観が変化し、マウスが一時停止する と、カーソルの下にある項目が自動選択されます。ホット トラッキン グを有効にするには、TrackSelect プロパティに TRUE を設定します。 また、OneClickActivate または TwoClickActivate に TRUE を設定しても、 ホット トラッキングが有効になります。OneClickActivate が TRUE の場 合には、UnderlineHot プロパティまたは UnderlineCold プロパティを設 定することによって、選択した項目または選択しない項目に下線を付 けるよう指定できます。これらすべてのプロパティは、コントロール の[全般]プロパティ ページまたはスクリプトで設定できます。 表 9-4 に示されている OneClickActivate と TwoClickActivate の設定は、 ItemActivate イベントが発生したときに作用します。 表 9-4: OneClickActivate と TwoClickActivate の設定 カスタム イベントの 使い方 ItemActivate が発生する タイミング OneClickActivate TwoClickActivate TRUE TRUE または FALSE 任意の項目をクリック FALSE TRUE FALSE FALSE 選択した項目をクリック 任意の項目をダブルクリック PowerBuilder バージョン 7 以降のリリースでは、リストビュー コント ロールとツリービュー コントロールに Microsoft のコントロールが使 用されており、右クリックしたときに発生するイベントが以前のバー ジョンとは異なります。以下に、リストビュー コントロール内で右ク リックしたときに発生するイベントを示します。 アプリケーション テクニック 157 リストビュー コントロールの使い方 表 9-5: 右クリックで発生するリストビュー コントロールのイベント 場所 リストビュー 項目 リストビュー 内の空白領域 動作内容 マウスの右ボタ ンを押す マウスの右ボタ ンを放す マウスの右ボタ ンを押す マウスの右ボタ ンを放す 発生するイベント pbm_rbuttondown pbm_lvnrclicked(組み込み RightClicked! イベント) pbm_contextmenu pbm_rbuttondown pbm_lvnrclicked(組み込み RightClicked! イベント) pbm_contextmenu pbm_rbuttonup pbm_contextmenu 詳細表示の使い方 リストビューの詳細表示は、大きいアイコン表示、小さいアイコン表 示、そして一覧表示より多くの情報を必要とします。リストビュー コ ントロールで詳細表示するには、AddColumn 関数と SetColumn 関数でカ ラムを設定するスクリプトを記述し、SetItem 関数を使用してカラムの 値を設定します。 カラム値の設定 リストビューでカラムを作成するには、AddColumn 関数を使用します。 AddColumn 関数を使用するときは、以下の指定をします。 カラム ヘッダで表示される名前 • カラム ラベル • カラム配置 テキストの左詰め、右詰め、または中央揃え • カラムのサイズ PowerBuilder 単位系でのカラムの幅 以下の例では、リストビューに 3 つのカラムを作成します。 This.AddColumn("Name", Left!, 1000) This.AddColumn("Size", Left!, 400) This.AddColumn("Date", Left!, 300) カラムの設定 カラム番号、名前、配置、サイズを設定するには、SetColumn 関数を使 用します。 This.SetColumn (1, "Composition", Left!, 860) This.SetColumn (2, "Album", Left!, 610) This.SetColumn (3, "Artist", Left!, 710") 158 PowerBuilder 第9章 カラム項目の設定 ウィンドウでのリストの使い方 リストビューのカラムに値を設定するには SetItem 関数を使用します。 This.SetItem This.SetItem This.SetItem This.SetItem This.SetItem This.SetItem This.SetItem This.SetItem This.SetItem (1, (1, (1, (2, (2, (2, (3, (3, (3, 1, 2, 3, 1, 2, 3, 1, 2, 3, "St.Thomas") "Saxophone Colossus") "Sonny Rollins") "So What") "Kind of Blue") "Miles Davis") "Good-bye, Porkpie Hat") "Mingus-ah-um") "Charles Mingus") リストビュー コントロールへのカラムの追加の詳細については、 『PowerScript リファレンス』マニュアルを参照してください。 アプリケーション テクニック 159 リストビュー コントロールの使い方 160 PowerBuilder 第 1 0 章 ドラッグ アンド ドロップ機能の 使い方 この章について この章では、ドラッグ アンド ドロップ機能を使用して、アプリ ケーションをグラフィカルに操作する方法について説明します。 内容 項目 ドラッグ アンド ドロップ機能について ドラッグ アンド ドロップのプロパティ、イベント、および関 数 ドラッグされたコントロールの識別 ページ 161 162 164 ドラッグ アンド ドロップ機能について ドラッグ アンド ドロップ機能とは、コントロールをドラッグし、 ほかのコントロール上にドロップすることで、アクションを起動 する機能のことです。この機能を用いると、アプリケーションが グラフィカルで操作しやすくなります。たとえば、製造用のアプ リケーションで、部品のピクチャをドラッグし、完成した組み立 て品のピクチャにドロップすることで、組み立て作業を行えるよ うにできます。 ドラッグ アンド ドロップ操作には、ドラッグされるコントロール (ドラッグ コントロール)とドラッグ先のコントロール(ターゲッ ト) の少なくとも 2 つのコントロールが必要となります。 PowerBuilder では、描画オブジェクト(線、楕円、長方形、丸長方形)を除く すべてのコントロールをドラッグすることができます。 自動ドラッグ モード アプリケーション テクニック コントロールは、ドラッグされるとドラッグ モードになります。 コントロールに Clicked イベントが発生したときに自動的にド ラッグ モードになるように、コントロールを定義することができ ます。また、ウィンドウやアプリケーションで、あるイベントが 発生したときにコントロールがドラッグ モードになるようにスク リプトを記述することもできます。 161 ドラッグ アンド ドロップのプロパティ、イベント、および関数 ドラッグ アイコン ドラッグ可能なコントロールのスタイルをウィンドウ ペインタで定 義する際に、ドラッグ アイコンを指定することができます。ドラッグ アイコンは、そのコントロールが有効なドロップ領域(コントロール をドロップできる領域)上にドラッグされると表示されます。ドラッ グ アイコンを指定していない場合は、そのコントロールのサイズの長 方形が表示されます。 ドラッグ イベント 描画オブジェクトを除くすべてのコントロールとウィンドウ オブ ジェクトは、ドラッグ ターゲットになったときに特別なイベントを持 つことができます。ドラッグされたコントロールがターゲット内に 入ったりターゲット上にドロップされたりすると、該当するイベント のスクリプトが実行されます。ドラッグ コントロールがターゲットに 入るとき、ターゲット内にドラッグされているとき、ターゲットから 離れるとき、ターゲット上にドロップされるとき、それぞれのタイミ ングでどのような処理を行うかをスクリプトで指定します。 ドラッグ アンド ドロップのプロパティ、イベント、および 関数 PowerBuilder の各コントロールは、以下の 2 つのドラッグ アンド ド ロップのプロパティを持ちます。 ドラッグ アンド ド ロップのプロパティ • DragAuto • DragIcon DragAuto プロパティ DragAuto は、Boolean 型のプロパティです。 表 10-1: DragAuto プロパティ値 値 TRUE FALSE ❖ 意味 オブジェクトがクリックされると、コントロールは自動的にド ラッグ モードになる オブジェクトがクリックされても、コントロールは自動的には ドラッグ モードにならない。ドラッグ モードにするには、スク リプトで Drag 関数を使用しなければならない ウィンドウ ペインタでコントロールに対する自動ドラッグ モードを指定する には 1 コントロールのプロパティ ビューで[その他]プロパティ ページ を選択します。 2 [自動ドラッグモード]チェックボックスをオンにします。 162 PowerBuilder 第 10 章 ドラッグ アンド ドロップ機能の使い方 DragIcon プロパティ DragIcon プロパティを使用して、コントロールが ドラッグ モードになったときのアイコンを指定します。DragIcon プロ パティは、組み込みアイコン名か、アイコン ファイル(ICO ファイル) 名です。デフォルトのドラッグ アイコンは、コントロールと同じサイ ズの長方形です。 コントロールをドラッグすると、そのコントロールがドロップできる 領域(有効ドロップ領域)上にあるときに、ドラッグ アイコンが表示 されます。コントロールをドロップできない領域(たとえば、ウィン ドウのスクロールバー)ではドロップ禁止アイコンが表示されます。 ❖ ドラッグ アイコンを指定するには 1 コントロールのプロパティ ビューで[その他]プロパティ ページ を選択します。 2 組み込みアイコンのリストから使用するアイコンを選択するか、 参照( [...])ボタンをクリックして ICO ファイルを選択し、 [OK] ボタンをクリックします。 アイコンの作成 アイコンは、Microsoft Windows の ICO ファイル形式で保存可能な描画 アプリケーションを利用して作成します。 ドラッグ アンド ド ロップのイベント ドラッグ アンド ドロップのイベントには、以下の 6 種類があります。 表 10-2: ドラッグ アンド ドロップのイベント イベント BeginDrag BeginRightDrag DragDrop DragEnter DragLeave DragWithin アプリケーション テクニック 発生する状況 リストビューまたはツリービュー コントロール上で、マ ウスの左ボタンを押してドラッグを開始するとき リストビューまたはツリービュー コントロール上で、マ ウスの右ボタンを押してドラッグを開始するとき ドラッグ アイコンのホット スポット(通常は中央)が ターゲット(ドラッグ先の PowerBuilder コントロールや ウィンドウ)上にあり、マウス ボタンが放されたとき ドラッグ アイコンのホット スポットがターゲットの境 界内に入るとき ドラッグ アイコンのホット スポットがターゲットの境 界外に出るとき ドラッグ アイコンのホット スポットがターゲットの境 界内で移動するとき 163 ドラッグされたコントロールの識別 ドラッグ アンド ド ロップの関数 PowerBuilder の各コントロールでは、ドラッグ アンド ドロップのイベ ントに対するスクリプトを記述するために、以下の 2 種類の関数が用 意されています。 表 10-3: ドラッグ アンド ドロップ イベントの関数 関数 Drag DraggedObject 動作内容 コントロールのドラッグを開始または終了する 現在ドラッグされているコントロールを取得する これらのイベントおよび関数の詳細については、 『PowerScript リファ レンス』マニュアルを参照してください。 ドラッグされたコントロールの識別 ドロップされたコントロールの種類を識別するには、DragDrop イベン トの source 引数を使用します。 以下のスクリプトは、ピクチャ内の DragDrop イベントに対するスクリ プトです。ここでは 2 種類の変数を宣言してから、ドロップされたオ ブジェクトの種類を特定しています。 CommandButton lcb_button StaticText lst_info IF source.TypeOf() = CommandButton!THEN lcb_button = source lcb_button.Text = "You dropped a Button!" ELSEIF source.TypeOf() = StaticText!THEN lst_info = source lst_info.Text = "You dropped the text!" END IF CHOOSE CASE 文の使用 ウィンドウにドロップ可能なコントロールが数多くあるときは、 CHOOSE CASE 文を使用します。 164 PowerBuilder 第 11 章 オンライン ヘルプの提供 この章について この章では、Windows 上でほかの開発者およびエンド ユーザに対 してオンライン ヘルプを提供する方法について説明します。 内容 項目 ヘルプ ファイルの作成 開発者に対するオンライン ヘルプの提供 エンド ユーザに対するオンライン ヘルプの提供 ページ 165 167 169 ヘルプ ファイルの作成 ヘルプ オーサリング ツー ルについて Windows でオンライン ヘルプ ファイルを作成する際には、多数の オーサリング ツールと関連製品を使用できます。RTF ベースのヘ ルプ ファイルを作成するすべてのオーサリング ツールは、Microsoft ヘルプ コンパイラを使用して、一連のソース ファイルを完成した ヘルプ ファイルにコンパイルします。 組み込まれる内容 一般に、ヘルプ システム用のソース ファイルには以下の要素が組 み込まれています。 アプリケーション テクニック • トピック ファイル(RTF): トピックの識別に役立ち、ナビ ゲーションなどの機能を提供するコマンドと脚注コードに加 えて、ヘルプ システムのテキストも含む • グラフィック ファイル : 一般的にはビットマップ(BMP)で、 特定のトピックに関連付けられている • プロジェクト ファイル(HPJ): 完成したヘルプ システムには 組み込まれないが、コンパイラ用の命令が含まれており、そ のうちのいくつかは、指定したヘルプ ウィンドウの外観と機 能に影響を与える • コンテンツ ファイル(CNT): 完成したヘルプ ファイルには 組み込まれないが、ヘルプ システム全体の一部としてヘルプ ファイルとともに配布される 165 ヘルプ ファイルの作成 コンテンツ ファイルは、ヘルプ トピック ダイアログボックスの [目次]タブに表示するエントリを提供する。また、ヘルプ システ ムの動作全体に影響を及ぼすことのあるそのほかの情報も提供す る 処理方法 多機能なヘルプ オーサリング ツールを使用している場合には、その指 示に従って、必要なソース ファイルを作成し、コンパイルすることが できます。 Microsoft SDK に添付の Microsoft ヘルプ ワークショップを使用してい る場合には、このツールを使用してプロジェクト ファイルとコンテン ツ ファイルを作成し、完成したヘルプ ファイルをコンパイルすること ができます。しかし、Microsoft Word で直接ヘルプ トピックを記述す る必要があります。Microsoft ヘルプ ワークショップ用のオンライン ヘ ルプでは、ヘルプ コンパイラ、WinHelp マクロ、および WinHelp API によって識別されるさまざまな脚注コードの使い方に関する指示をは じめとして、ヘルプ作成に関する多くの情報を提供しています。 サンプル プロジェク ト ファイル 参考用にサンプルのプロジェクト ファイルが、PowerBuilder とともに インストールされる PBUSR110.HLP ファイルのトピックにあります。 テキストの取り出し方法を以下に示します。 1 PowerBuilder ヘルプを開いて、 [ユーザ]ボタンをクリックします。 2 ユーザ定義ヘルプの下で、トピックの検索 ダイアログボックスの [目次]タブから「ヘルプ プロジェクト ファイルのサンプル」項 目に移動します。 3 ヘルプ トピックを Windows のクリップボードにコピーします。 4 メモ帳などのテキスト エディタを開いて、クリップボードのテキ ストを空のドキュメントに貼り付けます。 5 そのドキュメントを PBUSR110.HPJ としてテキスト形式で保存し ます。 ソース ファイル名やディレクトリ パス名など、ヘルプ開発環境の細部 を反映させるには、プロジェクト ファイルを編集する必要がありま す。そのためには、テキスト エディタを使用したり、ヘルプ ワーク ショップまたはそのほかのヘルプ オーサリング ツールでプロジェク ト ファイルを開いて編集したりすることができます。 166 PowerBuilder 第 11 章 オンライン ヘルプの提供 開発者に対するオンライン ヘルプの提供 ヘルプを提供する 2 つの方法 ユーザ定義関数、ユーザ イベント、およびユーザ オブジェクトのオン ライン ヘルプを PowerBuilder の開発環境に統合するには、2 つの方法 があります。 • • ユーザ定義関数の状況 依存ヘルプの機能 PowerBuilder メイン ヘルプ ウィンドウの[ユー ザ]ボタンをハードコード化して、PBUSR110.HLP というファイ ルを起動します。 [ユーザ]ボタン 状況依存ヘルプ スクリプト ビューで関数名を選択して(または カーソルを関数名に置いて) 〔Shift〕+〔F1〕を押すと、ユーザ定 義関数の状況依存ヘルプを表示できます。 スクリプト ビューで関数の名前を選択するか関数名にカーソルを置 いて、 〔Shift〕+〔F1〕を押すと、以下の動作が行われます。 1 PowerBuilder は、関数名の中から標準の接頭辞(デフォルトは uf_) を探します。 2 標準の接頭辞が見つかった場合には、PowerBuilder は(自身のメイ ン ヘルプ ファイルである PBHLP110.HLP を調べるかわりに)ユー ザ定義関数のヘルプ トピックを含んでいるヘルプ ファイルから ヘルプ トピックを探します。ユーザ定義関数のヘルプのデフォル ト ファイル名は PBUSR110.HLP です。 PowerBuilder は、PB.INI 内の UserHelpFile 変数を読み取ることに よって、調べるヘルプ ファイルの名前を判別します。この変数の 値を変更する方法については、168 ページの「高度な手順」を参照 してください。 3 最も簡単な方法 PowerBuilder が変数を見つけ出した場合には、指定したヘルプ ファ イルから選択した関数の名前を探します。PB.INI に UserHelpFile 変 数が存在しない場合には、PowerBuilder は、PowerBuilder Help ディ レクトリの PBUSR110.HLP ファイルからキーワードを探します。 PowerBuilder のデフォルトを使用する場合には、以下の操作が必要に なります。 • アプリケーション テクニック ユーザ定義関数、ユーザ イベント、およびユーザ オブジェクトの すべてのオンライン ヘルプを、PBUSR110.HLP という 1 つのファ イルにコンパイルします。 167 開発者に対するオンライン ヘルプの提供 オプションでコンテンツ ファイルを提供できます。その名前は PBUSR110.CNT とする必要があります。 • 基本的な手順 作成する各ユーザ定義関数の名前の前に uf_ を付けます(たとえ ば、uf_calculate)。 次に、オンライン ヘルプを PowerBuilder 環境に組み込む方法について 説明します。 ❖ [ユーザ]ボタンから PowerBuilder 開発者用のオンライン ヘルプを起動す るには 1 Microsoft Word および Microsoft ヘルプ ワークショップまたはその ほかのヘルプ オーサリング ツールを使用して、オンライン ヘルプ ファイルを作成します。 2 PowerBuilder とともにインストールされた PBUSR110.HLP と PBUSR110.CNT のファイル名を変更します。独自のコンテンツ ファイルを提供しない場合でも、オリジナルの PBUSR110.CNT ファイルの名前は変更してください。 3 コンパイルしたヘルプ ファイルとオプションのコンテンツ ファ イルを、PowerBuilder の Help ディレクトリに保存します。ヘルプ ファイルの名前は PBUSR110.HLP、コンテンツ ファイルの名前は PBUSR110.CNT とします。 [ユーザ]ボタンをクリックすると、ヘルプ ファイルが表示されま す。 ❖ ユーザ定義関数の状況依存ヘルプを作成するには 1 ユーザ定義関数を作成した場合には、関数の名前には標準の接頭辞 を付けます。 デフォルトの接頭辞は uf_ です(たとえば、uf_calculate)。 2 ユーザ定義関数のヘルプ トピックごとに、関数名と同じ検索キー ワード(脚注として K を使用)を割り当てます。 たとえば、ユーザ定義関数 uf_CutBait のヘルプ項目には、検索キー ワード uf_CutBait を設定します。PowerBuilder は、このキーワード を使用して、ヘルプ ウィンドウに適切なトピックを呼び出します。 3 高度な手順 168 ヘルプ ファイルをコンパイルし、PowerBuilder Help ディレクトリ に保存します。 状況依存ヘルプに別のファイル名を指定するには、PB.INI ファイルの UserHelpFile 変数の値を変更します。この変数を使用するには、ヘル プ ファイルが PowerBuilder Help ディレクトリに存在する必要があり ます。 PowerBuilder 第 11 章 ❖ オンライン ヘルプの提供 状況依存ヘルプに別のファイル名を指定するには 1 テキスト エディタで PB.INI ファイルを開きます。 2 [PB]セクションで、UserHelpFile 変数を追加して、状況依存トピッ クを含むヘルプ ファイルの名前を指定します。変数の書式は次の とおりです。 UserHelpFile = helpfile.hlp ファイル名だけを指定します。絶対パスで指定しても認識されま せん。 ユーザ定義関数には、デフォルトの uf_ 接頭辞以外の標準の接頭辞を 付けることができます。使用したい接頭辞を定義するには、PB.INI ファ イルに UserHelpPrefix 変数を記述します。 ❖ ユーザ定義関数に別の接頭辞を使用するには 1 テキスト エディタで PB.INI ファイルを開きます。 2 [PB]セクションで、UserHelpPrefix 変数を追加して、接頭辞の値 を指定します。次の書式を使用します。 UserHelpPrefix = yourprefix_ 指定する接頭辞の最後は、アンダースコア文字にする必要があり ます。 エンド ユーザに対するオンライン ヘルプの提供 アプリケーションから ヘルプを呼び出す 2 つの方法 ShowHelp の使い方 PowerBuilder は、PowerBuilder アプリケーションからオンライン ヘル プ ファイルを呼び出すために 2 つの方法を提供しています。 • アプリケーション スクリプトで ShowHelp および ShowPopupHelp 関数を使用して、ヘルプ トピックを呼び出す • WinHelp API を外部関数として宣言し、アプリケーション スクリ プトで WinHelp 関数を使用してヘルプ トピックを呼び出す ShowHelp の実装は、WinHelp API の場合よりも簡単です。ShowHelp 関 数を使用すれば、ヘルプ コンテキスト ID またはキーワードによって、 あるいはヘルプ ファイルのコンテンツ トピック(プロジェクト ファ イルにヘルプ コンテンツ トピックとして定義されたトピック)にアク セスすることによって、ヘルプ トピックを検索できます。ShowHelp 関 数は、コンパイル済みの HTML(.chm)ファイルでも使用できます。 アプリケーション テクニック 169 エンド ユーザに対するオンライン ヘルプの提供 ShowPopupHelp 関数は、コントロールのポップアップ ヘルプを表示し ます。通常、ShowPopupHelp 関数は、Context Help プロパティを有効に した状態で、レスポンス ウィンドウの Help イベントで使用します。ま た、コントロール上でのカーソルの動きに応じて発生するイベントや、 コントロールまたはオブジェクトをドラッグしたときに発生するイベ ントは、ShowPopupHelp によって呼び出されます。 ShowHelp 関数、ShowPopupHelp 関数、および Help イベントの詳細につ いては、 『PowerScript リファレンス』マニュアルを参照してください。 WinHelp API を使用すると、WinHelp 関数の全域に渡るアクセスが可能 となります。これらの関数の多くは、ShowHelp では使用できません。 たとえば、WinHelp 関数を使用すれば、ヘルプ トピックを提示するウィ ンドウの種類またはウィンドウ名を簡単に指定できます。 WinHelp API の使い方 ❖ 外部関数として WinHelp API を宣言するには 1 2 スクリプト ペインタの最初のドロップダウン リストボックスから [(Declare)]を、2 番目のドロップダウン リストボックスから[Global External Functions]を選択します。 関数宣言をスクリプト ビューに入力します。 次の例では、WinHelp API を宣言します。 FUNCTION boolean WinHelpW(long hWndMain, & string lpszHelp, long uCommand, & long dwData) & LIBRARY "USER32.DLL" WinHelp API の詳細については、Microsoft ヘルプ ワークショップのオ ンライン ヘルプまたはご使用のヘルプ オーサリング ツールの資料を 参照してください。グローバル外部関数の宣言と使用の詳細について は、『PowerScript リファレンス』マニュアルおよび 467 ページの「外 部関数の使い方」を参照してください。 170 PowerBuilder 第 4 部 データ アクセス テクニック 第 4 部では、PowerBuilder によるアプリケーション開発 において、データ アクセス機能を実現するためのテク ニックについて説明します。トランザクション オブジェ クトの使い方、XML の処理、グラフの操作、リッチテキ ストの作成方法、データ ソース間のデータ転送などにつ いて説明します。データウィンドウ オブジェクトおよび データストアでのデータ アクセスの使い方については 『データウィンドウ プログラマーズ ガイド』マニュアル を参照してください。 第 1 2 章 トランザクション オブジェクトの 使い方 この章について この章では、トランザクション オブジェクトと PowerBuilder アプ リケーションにおけるそれらの使い方について説明します。 内容 項目 トランザクション オブジェクトについて トランザクション オブジェクトの使い方 ストアド プロシージャを呼び出すためのトランザクション オブジェクトの使い方 ストアド プロシージャを呼び出すときサポートされている DBMS の機能 ページ 173 178 190 199 トランザクション オブジェクトについて PowerBuilder で行うデータベース接続は、トランザクション オブ ジェクトと呼ばれる、PowerBuilder アプリケーションとデータベー スとの通信領域として機能する非ビジュアル オブジェクトを使用し ます。PowerBuilder がデータベースに接続するためには、トランザ クション オブジェクトにパラメータを指定します。なお、トラン ザクション オブジェクトは、図 12-1 に示すように、アプリケー ションからデータベースにアクセスする前に、あらかじめ設定し なければなりません。 図 12-1: データベースにアクセスするためのトランザクション オブジェクト アプリケーション テクニック 173 トランザクション オブジェクトについて PowerBuilder アプリケーションにおいて、データを表示したり、操作 したりするためには、データベースと通信する必要があります。 データベースとの通信 ❖ PowerBuilder アプリケーションからデータベースと通信するには 1 トランザクション オブジェクトに適切な値を設定します。 2 データベースに接続します。 3 トランザクション オブジェクトをデータウィンドウ コントロー ルに関連付けます。 4 データベース処理を行います。 5 データベースとの接続を解除します。 データウィンドウ コントロール用のトランザクション オブジェクト の設定方法、およびデータウィンドウを使用して検索と更新を行う方 法についての詳細は、『データウィンドウ プログラマーズ ガイド』マ ニュアルを参照してください。 デフォルト トランザ クション オブジェク ト アプリケーションの実行を開始するときに、PowerBuilder は SQLCA (SQL Communications Area)という名前のグローバルなデフォルト ト ランザクション オブジェクトのインスタンスを作成します。アプリ ケーションでは、このデフォルト トランザクション オブジェクトを使 用できます。また、アプリケーションが複数のデータベースに接続す る場合は、ほかのトランザクション オブジェクトを作成して使用でき ます。 トランザクション オ ブジェクトのプロパ ティ トランザクション オブジェクトには、以下の 15 種類のプロパティが あります。 • 10 種類のプロパティは、データベースに接続するために使用され ます。 • 5 種類のプロパティは、実行された SQL 文の成否についてのステー タス情報をデータベースから受け取るために使用されます。これ らのエラーをチェックするプロパティ名は、5 種類ともすべて SQL から始まります。 トランザクション オブジェクトのプロパティ 表 12-1 に、トランザクション オブジェクトのプロパティを示します。 接続のための 10 種類のプロパティには、それぞれのプロパティに対応 する DB プロファイル設定 ダイアログボックスのフィールドを示しま す。DB プロファイル設定 ダイアログボックスは、PowerBuilder の開 発環境でデータベース プロファイルを作成します。 174 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 PoweBuilder データベース インタフェースにおけるトランザクション オブ ジェクトのプロパティ PowerBuilder データベース インタフェースで使用できるトランザク ション オブジェクトのプロパティについては、177 ページの「トラン ザクション オブジェクトのプロパティと PowerBuilder データベース インタフェースのサポート」を参照してください。 接続のための 10 種類のプロパティに設定する値については、『データ ベースとの接続』マニュアルの該当する PowerBuilder データベース イ ンタフェースの節を参照してください。 表 12-1: トランザクション オブジェクトのプロパティ プロパティ DBMS データ型 String Database String UserID DBPass Lock String String String LogID String LogPass String ServerName String アプリケーション テクニック DB プロファイ ル設定の フィールド DBMS 説明 接続のための PowerBuilder の DBMS 識別子。サポート されているデータベース インタフェースの識別子の一 覧については、オンライン ヘルプを参照 接続するデータベースの名前 [データソー ス] データベースに接続するユーザの名前または ID [ユーザ ID] データベースに接続するときに使用するパスワード [パスワード] Lock の値と分離レベルの使用をサポートする DBMS の [分離レベル] 場合、データベースに接続するときの分離レベル。ご使 用の DBMS に設定できる Lock の値については、オンラ イン ヘルプの Lock DBParm パラメータの記述を参照 データベース サーバにログインするユーザの名前また [ログイン ID] は ID データベース サーバにログインするときに使用するパ [パスワード] スワード データベースが常駐するサーバの名前 [サーバ」 175 トランザクション オブジェクトについて プロパティ AutoCommit データ型 Boolean DBParm String SQLReturnData String SQLCode Long SQLNRows Long SQLDBCode Long SQLErrText String 176 DB プロファイ ル設定の 説明 フィールド AutoCommit をサポートする DBMS のために、 PowerBuilder [自動コミット が SQL 文をトランザクションのスコープ外またはス モード] コープ内のどちらで発行するかを指定する。設定できる 値は、以下のとおり • True SQL 文は、トランザクションのスコープ外で 発行される。つまり、ステートメントは、論理的な作 業単位(LUW)の一部ではない。SQL 文の実行が成 功した場合、DBMS は、COMMIT 文が発行されたかの ように、データベースをただちに更新する • False (デフォルト)SQL 文は、トランザクションの スコープ内で発行される。PowerBuilder は、接続を開 始するときに BEGIN TRANSACTION 文を発行する。さ らに、COMMIT 文や ROLLBACK 文が発行された後に、 BEGIN TRANSACTION 文を発行する 詳細については、オンライン ヘルプの AutoCommit に関 する記述を参照 DBMS 固有の接続パラメータ。特定の DBMS 機能をサ [ドライバ固有 ポート。PowerBuilder がサポートする各 DBParm パラ のパラメータ] メータの記述については、『データベースとの接続』マ ニュアルの追加の「接続パラメータの設定」についての 章を参照 DBMS 固有の情報。たとえば、Informix データベースに — 接続し、埋め込み SQL の INSERT 文を実行すると、 SQLReturnData プロパティには、テーブルに挿入した行 のシリアル番号が入る 直前に実行した SQL 文の成否コード。詳細については、 — 188 ページの「SQL 文実行後のエラー処理」を参照 直前に実行した SQL 文によって影響を受けた行の数。こ — の行数はデータベースが返すので、その意味は DBMS に よって異なる データベース ベンダのエラーコード。詳細については、 — 188 ページの「SQL 文実行後のエラー処理」を参照 データベース ベンダのエラー コードに対応するエラー — メッセージのテキスト。詳細については、188 ページの 「SQL 文実行後のエラー処理」を参照 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 トランザクション オブジェクトのプロパティと PowerBuilder データ ベース インタフェースのサポート データベースに接続するために必要なトランザクション オブジェク トのプロパティは、PowerBuilder データベース インタフェースによっ て異なります。SQLReturnData プロパティを除き、SQL 文の成否につ いてのステータス情報を返すプロパティは、すべての PowerBuilder データベース インタフェースに適用します。 サポートする PowerBuilder データベース インタフェースとトランザク ション オブジェクトのプロパティを、表 12-2 に示します。 表 12-2: PowerBuilder データベース インタフェース データベース インタフェース Informix JDBC トランザクション オブジェクト のプロパティ DBMS UserID DBPass Database ServerName DBParm Lock AutoCommit SQLReturnData SQLCode SQLNRows SQLDBCode SQLErrText DBMS LogID LogPass DBParm Lock DBMS Database ServerName LogID LogPass DBParm Lock AutoCommit SQLCode SQLNRows SQLDBCode SQLErrText ODBC DBMS #UserID +LogID +LogPass DBParm Lock OLE DB DBMS LogID LogPass DBParm AutoCommit SQLReturnData SQLCode SQLNRows SQLDBCode SQLErrText AutoCommit SQLCode SQLNRows SQLDBCode SQLErrText Microsoft SQL Server アプリケーション テクニック AutoCommit SQLCode SQLNRows SQLDBCode SQLErrText 177 トランザクション オブジェクトの使い方 データベース インタフェース Oracle Sybase Adaptive Server Enterprise トランザクション オブジェクト のプロパティ DBMS ServerName LogID LogPass DBParm DBMS Database ServerName LogID LogPass DBParm Lock SQLReturnData SQLCode SQLNRows SQLDBCode SQLErrText AutoCommit SQLCode SQLNRows SQLDBCode SQLErrText # ODBC に対するオプション(UserID プロパティを指定するときは、ODBC の SQLGetInfo 関数呼び出しによって返される UserName プロパティを上書きするので、 注意してください)。 + ご使用の ODBC ドライバが ODBC SQL ドライバの Connect 関数呼び出しをサポート していない場合に限り、PowerBuilder は LogID プロパティと LogPass プロパティを使 用します。 トランザクション オブジェクトの使い方 PowerBuilder は、論理的な作業単位(LUW)と呼ばれるデータベース トランザクション処理の基本的なコンセプトを使用しています。LUW は、トランザクションの同意語です。トランザクションは、LUW を形 成する 1 つまたは複数の SQL 文のセットです。トランザクション内の すべての SQL 文は、1 つの論理的な単位として処理されます。 PowerScript のトランザクション管理文には、以下の 4 つのステートメ ントがあります。 178 • COMMIT • CONNECT • DISCONNECT • ROLLBACK PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 トランザクションの基礎 CONNECT 文と DISCONNECT 文 CONNECT 文が正常に実行されるとトランザクションが開始され、 DISCONNECT 文によってそのトランザクションが終了します。CONNECT 文と DISCONNECT 文の間で実行される SQL 文はすべて、そのトランザ クションに属します。 CONNECT 文を実行する前に、トランザクション オブジェクトは存在 しなければなりません。また、DBMS に接続するためには、トランザ クション オブジェクトの必要なプロパティに値を設定しなければな りません。 COMMIT 文と ROLLBACK 文 COMMIT 文が実行されると、現行のトランザクションが開始(または、 最後に実行された COMMIT 文や ROLLBACK 文)後にデータベースに対 して行われたすべての変更が確定され、新しいトランザクションが開 始されます。ROLLBACK 文が実行されると、現行のトランザクション が開始以降のすべての変更は取り消され、新しいトランザクションが 開始されます。 トランザクション型コンポーネントが EAServer、COM+、または別の アプリケーション サーバに配布された場合、TransactionServer コンテ キスト オブジェクトを使用して、トランザクションをコントロールで きます。180 ページの「トランザクション サーバの配布」を参照して ください。 AutoCommit プロパ ティの設定 COMMIT 文と ROLLBACK 文が実行できるのは、トランザクション オブ ジェクトの AutoCommit プロパティの値が False(デフォルト)で、埋 め込み SQL を使用したトランザクションをまだ開始していないとき だけです。 AutoCommit プロパティについての詳細は、174 ページの「トランザク ション オブジェクトのプロパティ」を参照してください。 接続が解除されたときの自動コミット トランザクションの接続が解除されたときに、COMMIT 文が発行され ます。 アプリケーション テクニック 179 トランザクション オブジェクトの使い方 トランザクション プール トランザクション プールを使用して、データベースの処理を最適化で きます。 詳細については、189 ページの「データベース トランザクションのプー ル」を参照してください。 トランザクション サーバの配布 PowerBuilder で開発したコンポーネントは、EAServer、COM+、または 別のアプリケーション サーバのトランザクションに関与できます。コ ンポーネントにマークを付けることによって、トランザクション サ ポートを提供するコンポーネントを判別できます。コンポーネントが トランザクション サポートを提供する場合、トランザクション サーバ は、コンポーネントのデータベース操作がトランザクションの一部と して実行され、しかも関与しているコンポーネントによって行われた データベース変更はすべてコミットまたはロールバックされるように します。トランザクションを使用するコンポーネントを定義すれば、 トランザクションに関与するコンポーネントによって実行されるすべ ての作業は意図したとおりに行われることを保証できます。 PowerBuilder は、TransactionServer というトランザクション サービス コンテキスト オブジェクトを提供します。このオブジェクトは、トラ ンザクション サーバが現行のトランザクションをコミットするか中 止するかの判断に影響を与える、トランザクション状態プリミティブ へのアクセス権を与えます。COM+ クライアントは、OleTxnObject オ ブジェクトを使用して、トランザクションを制御することもできます。 TransactionServer コンテキスト オブジェクトを使用し、 UseContextObject DBParm パラメータに Yes を設定した場合、トランザクション オブジェ クト内で COMMIT 文と ROLLBACK 文を呼び出すとデータベース エラー になります。 デフォルトでは、TransactionServer コンテキスト オブジェクトは使用 されません。そのかわりに、COMMIT 文と ROLLBACK 文を使用してト ランザクションを管理できます。この場合には、COMMIT は SetComplete 関数と解釈され、ROLLBACK は SetAbort 関数と解釈されます。 詳細については、EAServer の場合は 516 ページの「トランザクション のサポート」、COM+ の場合は 632 ページの「トランザクションのサ ポート」を参照してください。 デフォルト トランザクション オブジェクト SQLCA 180 たいていのアプリケーションは 1 つのデータベースにだけアクセスす るので、PowerBuilder は、SQLCA と呼ばれるグローバルなデフォルト トランザクション オブジェクトを用意しています。SQLCA は、SQL 通信領域(SQL Communication Area)を意味します。 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 PowerBuilder は、アプリケーションの Open イベントに対するスクリプ トを実行する前に、SQLCA オブジェクトを作成します。SQLCA とそ の プ ロ パ テ ィ は、ア プ リ ケ ー シ ョ ン 内 の ど の ス ク リ プ ト か ら も、 PowerScript のドット(.)表記によって参照できます。 トランザクション オブジェクトは、 (一度に複数のデータベースに接 続する場合などに)必要であれば独自に作成できます。ただし、通常 は必要となるトランザクション オブジェクトは SQLCA だけで済みま す。 例 デフォルト ト ランザクショ ン オブジェク ト SQLCA を使用して、 Sample という名前の ODBC データ ソースに接続し、さらにその接続 を解除する簡単な例を以下に示します。 // デフォルト トランザクション オブジェクトのプロパティを設定しま す。 SQLCA.DBMS="ODBC" SQLCA.DBParm="ConnectString='DSN=Sample'" // データベースに接続します。 CONNECT USING SQLCA; IF SQLCA.SQLCode < 0 THEN & MessageBox(" 接続エラー ", SQLCA.SQLErrText,& Exclamation!) ... // データベースとの接続を解除します。 DISCONNECT USING SQLCA; IF SQLCA.SQLCode < 0 THEN & MessageBox(" 接続解除エラー ", SQLCA.SQLErrText,& Exclamation!) SQL 文の区切り子はセミコロン PowerBuilder のスクリプト内で埋め込み SQL を使用する場合、SQL 文 は必ずセミコロン(;)で終了しなければなりません。なお、複数行に わたる SQL 文に対して、継続行文字を使用する必要はありません。 トランザクション オブジェクトのプロパティ値の設定 デフォルト トランザクション オブジェクト(SQLCA)や独自に作成 したトランザクション オブジェクトを使用する前に、トランザクショ ン オブジェクトのプロパティに値を設定する必要があります。値を設 定するには、PowerScript のドット(.)表記を使用します。 アプリケーション テクニック 181 トランザクション オブジェクトの使い方 例 以下の PowerScript 文では、SQLCA のプロパティに値を割り当てます。 これは、PowerBuilder Adaptive Server Enterprise データベース インタ フェースを通じて Sybase Adaptive Server Enterprise データベースに接続 するために必要です。 sqlca.DBMS="SYC" sqlca.database="testdb" sqlca.LogId="CKent" sqlca.LogPass="superman" sqlca.ServerName="Dill" 外部ファイルからの値の読み込み 外部ファイルの使い方 トランザクション オブジェクトのプロパティの値は、外部ファイルか ら読み込んで設定できます。トランザクション オブジェクトの設定に 使用する外部ファイルには、アプリケーションの開発時に使用する PowerBuilder の初期設定ファイルや、アプリケーションを配布する際 に指定する初期設定ファイルなどがあります。 ProfileString 関数 設定する値は、PowerScript の ProfileString 関数を使用して、初期設定 ファイルから読み込むことができます。初期設定ファイルは、Windows の INI ファイルと同様に、変数値の代入式が集まった複数のセクショ ンで構成されています。PowerBuilder の初期設定(INI)ファイルも初 期設定ファイルの 1 つであり、PB、Application、Database などのセク ションから構成されています。 [PB] 変数とその変数値 ... [Application] 変数とその変数値 ... [Database] 変数とその変数値 ... ProfileString 関数の構文は以下のとおりです。 ProfileString ( file, section, key, default) 例 182 次のスクリプトでは、初期設定ファイルから値を読み取って、トラン ザクション オブジェクトをデータベースに接続するよう設定します。 条件付きコードでは、プラットフォームごとに適切な値を変数 startupfile に設定します。 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 sqlca.DBMS = ProfileString(startupfile, "database",& "dbms", "") sqlca.database = ProfileString(startupfile,& "database", "database", "") sqlca.userid = ProfileString(startupfile, "database",& "userid", "") sqlca.dbpass = ProfileString(startupfile, "database",& "dbpass", "") sqlca.logid = ProfileString(startupfile, "database",& "logid", "") sqlca.logpass = ProfileString(startupfile, "database",& "LogPassWord","") sqlca.servername = ProfileString(startupfile,& "database", "servername","") sqlca.dbparm = ProfileString(startupfile, "database",& "dbparm", "") データベースへの接続 トランザクション オブジェクトのプロパティに値を設定したら、SQL の CONNECT 文を使用して、データベースに接続できます。 // トランザクション オブジェクトの値は設定されています。 CONNECT; CONNECT 文は、PowerScript 文ではなく SQL 文なので、文の末尾にセ ミコロン(;)が必要です。 SQLCA 以外のトランザクション オブジェクトを使用している場合は、 SQL 構文に USING TransactionObject 句が必要です。 CONNECT USING TransactionObject; 例 CONNECT USING ASETrans; PowerBuilder アプリケーションで接続するための[プレビュー]タブ の使い方 DB プロファイル設定 ダイアログボックスの[プレビュー]タブを使っ て、開発時に PowerBuilder アプリケーションのスクリプトで使用する PowerScript 接続構文を、正確かつ簡単に作成できます。 アプリケーション テクニック 183 トランザクション オブジェクトの使い方 DB プロファイル設定 ダイアログボックスで必要な項目を指定する と、[プレビュー]タブに、選択したオプションに対応する正しい PowerScript 接続構文が表示されます。対応する DBParm パラメータ、 または SQLCA プロパティ名が各オプションに割り当てられ、必要に 応じて、引用符、カンマ、セミコロンなどの文字が挿入されます。こ の構文は、[プレビュー]タブからスクリプトに直接コピーできます。 ❖ PowerBuilder アプリケーションで接続するための[プレビュー]タブを使 用するには 1 接続用の DB プロファイル設定 ダイアログボックスで、データベー ス インタフェースの指示に従って、[接続]タブの基本オプショ ン、ほかのタブの DBParm パラメータと SQLCA プロパティに値を 代入します。 インタフェースの接続パラメータと指定する値については、ヘル プを参照してください。 2 [更新]を選択して、DB プロファイル設定ダイアログボックスを 閉じないで、設定を保存します。 3 [プレビュー]タブを選択します。 選択したオプションに対する適切な PowerScript 接続構文が、 [プ レビュー]タブの[DB 接続構文]ボックスに表示されます。 4 [DB 接続構文]ボックスで 1 行以上のテキスト行を選択し、[コ ピー]を選択します。 選択したテキストがクリップボードにコピーされます。次に、こ の構文をスクリプトに貼り付け、必要であれば、デフォルトのト ランザクション オブジェクト名(SQLCA)を修正します。 5 [OK]をクリックします。 データベースとの接続の解除 データベースの処理が終了したら、SQL の DISCONNECT 文を使用し て、データベースとの接続を解除します。 DISCONNECT; SQLCA 以外のトランザクション オブジェクトを使用している場合は、 SQL 構文に USING TransactionObject 句が必要です。 DISCONNECT USING TransactionObject; 184 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 例 DISCONNECT USING ASETrans; 接続が解除されたときの自動コミット デフォルトでは、トランザクションの接続が解除されたときに、COMMIT 文が実行されます。 複数のデータベース接続におけるトランザクション オブジェクトの定義 接続ごとに 1 つのト ランザクション オブ ジェクトを使用する 同時に複数のデータベースに対する処理を行うときは、複数のトラン ザクション オブジェクトをデータベースの接続ごとに 1 つずつ使用し ます。独自に定義するトランザクション オブジェクトを参照するとき には、その前にオブジェクトを宣言して作成する必要があります。ま た、そのオブジェクトが不要になったら破棄するようにします。 注意 PowerBuilder は、SQLCA を自動的に作成し、破棄します。したがって、 スクリプトで SQLCA の作成や破棄は行わないでください。 SQLCA 以外のトラン ザクション オブジェ クトの作成 SQLCA 以外のトランザクション オブジェクトを作成するには、 Transaction 型の変数を宣言します。 transaction TransactionObjectName 次に、トランザクション オブジェクトのインスタンスを作成します。 TransactionObjectName = CREATE transaction たとえば、DBTrans という名前のトランザクション オブジェクトを作 成する場合は、以下のように記述します。 transaction DBTrans DBTrans = CREATE transaction // これで、DBTrans のプロパティに値を設定できます。 DBTrans.DBMS = "ODBC" ... プロパティ値の設定 スクリプトで宣言して作成したトランザクション オブジェクトのプ ロパティに値を設定するときは、以下のように、プロパティの値を一 度に 1 つずつ設定しなければなりません。 // 以下の記述は、正しい結果となります。 transaction ASETrans アプリケーション テクニック 185 トランザクション オブジェクトの使い方 ASETrans = CREATE TRANSACTION ASETrans.DBMS = "Sybase" ASETrans.Database = "Personnel" 次のように、デフォルト以外のトランザクション オブジェクトで SQLCA と同じオブジェクトを設定して、値を代入することはできませ ん。 // 以下の記述は正しい結果になりません。 transaction ASETrans ASETrans = CREATE TRANSACTION ASETrans = SQLCA // エラー ! SQL 文の実行にトランザクション オブジェクトが必要となる場合は、 特に指定しない限り、デフォルト トランザクション オブジェクト SQLCA が使用されます。したがって、以下の 2 つの CONNECT 文は同 一です。 SQL 文に対するトラ ンザクション オブ ジェクトの指定 CONNECT; CONNECT USING SQLCA; SQLCA 以外のトランザクション オブジェクトを使用する場合は、表 12-3 の SQL 文において、USING TransactionObject 句を使用して、トラ ンザクション オブジェクトを指定する必要があります。 表 12-3: USING TransactionObject 句を必要とする SQL 文 ❖ COMMIT INSERT CONNECT PREPARE(動的 SQL) DELETE ROLLBACK DECLARE Cursor SELECT DECLARE Procedure SELECTBLOB DISCONNECT UPDATEBLOB EXECUTE(動的 SQL) UPDATE SQL 文にユーザ定義のトランザクション オブジェクトを指定するには • SQL 文の終わりに以下の句を追加します。 USING TransactionObject たとえば、以下のステートメントでは、ASETrans という名前のト ランザクション オブジェクトを使用して、データベースに接続し ます。 CONNECT USING ASETrans; 186 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 トランザクション オブジェクトのスクリプト記述の推奨 SQL 文における USING TransactionObject 句の指定は、SQLCA を使用す るときはオプションで、独自のトランザクション オブジェクトを使用 するときは必須です。しかし、SQLCA を含むすべてのトランザクショ ン オブジェクトに対して、USING TransactionObject 句を記述しておけ ば、複数のトランザクション オブジェクトを使用する場合などは、SQL 文で使用するトランザクション オブジェクトが明確になります。ま た、USING TransactionObject 句が必要な場合に必ず指定することができ ます。 例 以下のステートメントでは、デフォルト トランザクション オブジェク ト(SQLCA)を使用して SQL Anywhere データベースに接続します。 また、ASETrans という独自に作成したトランザクション オブジェクト を使用して、Adaptive Server Enterprise データベースに接続します。 // デフォルト トランザクション オブジェクトのプロパティを設定します。 SQLCA.DBMS = "ODBC" SQLCA.DBParm = "ConnectString='DSN=Sample'" // SQL Anywhere データベースに接続します。 CONNECT USING SQLCA; // ASE トランザクション オブジェクトを宣言します。 transaction ASETrans // ASE トランザクション オブジェクトを作成します。 ASETrans = CREATE TRANSACTION // ASE トランザクション オブジェクトのプロパティを設定します。 ASETrans.DBMS = "Sybase" ASETrans.Database = "Personnel" ASETrans.LogID = "JPL" ASETrans.LogPass = "JPLPASS" ASETrans.ServerName = "SERVER2" // ASE データベースに接続します。 CONNECT USING ASETrans; // SQL Anywhere データベースに行を挿入します。 INSERT INTO CUSTOMER VALUES ( 'CUST789', 'BOSTON' ) USING SQLCA; // ASE データベースに行を挿入します。 INSERT INTO EMPLOYEE VALUES ( "Peter Smith", "New York" ) USING ASETrans; // SQL Anywhere データベースとの接続を解除します。 アプリケーション テクニック 187 トランザクション オブジェクトの使い方 DISCONNECT USING SQLCA; // ASE データベースとの接続を解除します。 DISCONNECT USING ASETrans; // ASE トランザクション オブジェクトを破棄します。 DESTROY ASETrans エラー チェックの使い方 実際のスクリプトでは、CONNECT 文、INSERT 文、DISCONNECT 文の 後にエラー チェックのスクリプトを記述します。 詳細については、次の「SQL 文実行後のエラー処理」を参照してくだ さい。 SQL 文実行後のエラー処理 エラー チェックのタ イミング スクリプトで以下のステートメントを実行した後は、その成否コード (トランザクション オブジェクトの SQLCode プロパティ)を確認する 必要があります。 • トランザクション管理文(CONNECT 文、COMMIT 文、DISCONNECT 文など) • 埋め込み SQL 文や動的 SQL データウィンドウでのエラー チェック このようなエラー チェックは、データウィンドウで検索や更新を行っ た後には使用しないでください。 データウィンドウでのエラー処理についての詳細は、 『データウィンド ウ プログラマーズガイド』マニュアルを参照してください。 SQLCode の戻り値 表 12-4 に SQLCode の戻り値を示します。 表 12-4: SQLCode の戻り値 値 0 100 -1 意味 正常終了 取得しようとした行が見つからない エラー(ステートメントの実行に失敗) SQLErrText プロパティや SQLDBCode プロパティの値を使用し て詳細を参照。 188 PowerBuilder 第 12 章 SQLErrText プロパ ティと SQLDBCode プロパティの使い方 トランザクション オブジェクトの使い方 トランザクション オブジェクトの String 型の SQLErrText プロパティ には、データベースから提供されるエラーメッセージが保持されてい ます。トランザクション オブジェクトの Long 型の SQLDBCode プロ パティには、データベースから提供されるステータス コードが保持さ れています。これらの変数は、スクリプトで参照できます。 例 接続が失敗した場合に、メッセージボックスで DBMS のエラー番 号とメッセージを表示するには、以下のように記述します。 CONNECT USING SQLCA; IF SQLCA.SQLCode = -1 THEN MessageBox("SQL error " + String(SQLCA.SQLDBCode),& SQLCA.SQLErrText ) END IF データベース トランザクションのプール トランザクション プール アプリケーションは、データベース トランザクションをプールするこ とによって、データベースの処理を最適化できます。トランザクショ ンをプールすると、データベースに接続できる数を制御しながら、デー タベースの処理のスループットを上げることができます。トランザク ション プールを設定する場合は、アプリケーションは、同じデータ ベースに対する接続を再利用できます。 動作 トランザクション プールを使用しないでアプリケーションがデータ ベースに接続する場合、PowerBuilder は DISCONNECT 文が実行された データベース トランザクションを物理的に終了させます。 トランザクション プールが有効な場合、PowerBuilder は論理的にデー タベースとの接続を解除して、データベースに対する変更をコミット します。しかし、データベースとの接続は物理的に解除されません。 そのかわり、データベースへの接続はトランザクション プールで開い たまま保たれ、ほかのデータベース操作のために再利用することがで きます。 効果 同じデータベースに対して短いトランザクションを数多く処理するア プリケーションは、トランザクション プールを使用して、パフォーマ ンスを向上させることができます。 使い方 トランザクション プールを設定するには、SetTransPool 関数を使用し ま す。ア プ リ ケ ー シ ョ ン が デ ー タ ベ ー ス に 接 続 す る 前 な ら ば、 SetTransPool 関数はアプリケーションのスクリプトのどこにでも記述 できます。SetTransPool 関数は通常、アプリケーション オブジェクト の Open イベントで呼び出します。 アプリケーション テクニック 189 ストアド プロシージャを呼び出すためのトランザクション オブジェクトの使い方 例 以下のステートメントは、SetTransPool 関数を使用して、データベース に接続できるトランザクションの数に 16 を指定します。また、一度 データベースに接続したら、DISCONNECT 文を実行してもデータベー スとの接続を物理的に解除しないトランザクションの数に 12 を指定 します。接続の数が最大数に到達した場合は、次からの接続要求は、 トランザクション プールに接続が保持できるようになるまで 10 秒間 待ちます。10 秒間経過すると、アプリケーションはエラーを返します。 myapp.SetTransPool (12,16,10) 詳細情報 SetTransPool 関数についての詳細は、 『PowerScript リファレンス』マ ニュアルを参照してください。 ストアド プロシージャを呼び出すためのトランザクション オブジェクトの使い方 SQLCA は、すべての PowerBuilder アプリケーションで使用される Transaction 型の組み込みグローバル変数です。アプリケーションに よっては、データに特定の処理や計算を行わせるために、SQLCA をカ スタマイズして使用したいことがあります。 ご使用のデータベースがストアド プロシージャをサポートしている 場合は、ストアド プロシージャを処理するためのリモート ストアド プ ロシージャがすでに定義されていることがあります。アプリケーショ ンにおいて、データベースのストアド プロシージャを呼び出すため に、トランザクション オブジェクトをカスタマイズして、リモート プ ロシージャ コール(RPC)を使用することができます。 結果集合 RPC テクニックを使用して、ストアド プロシージャが返す結果集合に アクセスすることはできません。ストアド プロシージャが 1 つまたは 複数の結果集合を返す場合は、PowerBuilder は結果集合を無視して、出 力パラメータと戻り値を返します。ストアド プロシージャが結果集合 を返す場合は、埋め込み SQL の DECLARE Procedure 文を使用します。 DECLARE Procedure 文についての詳細は、 『PowerScript リファレンス』 マニュアルの「SQL 文」を参照してください。 190 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 PowerBuilder アプリケーションからデータベースのストアド プロシー ジャを呼び出すには、そのストアド プロシージャを呼び出すようにト ランザクション オブジェクトをカスタマイズして、PowerScript のドッ ト表記(object.function)を使用します。 RPC プロシージャの 概要 ❖ アプリケーションにおいてデータベースのストアド プロシージャを呼び出す には 1 新規作成 ダイアログボックスの[PB オブジェクト]タブにおい て、組み込みトランザクション オブジェクトから継承した標準ク ラス ユーザ オブジェクトを定義します。 2 ユーザ オブジェクト ペインタのスクリプト ビューで、RPCFUNC キーワードを使用して、ストアド プロシージャをユーザ オブジェ クトの外部関数またはサブルーチンとして宣言します。 3 ユーザ オブジェクトを保存します。 4 アプリケーション ペインタで、定義済みのユーザ オブジェクトを SQLCA のかわりにデフォルト グローバル変数として指定します。 5 PowerBuilder アプリケーションでそのユーザ オブジェクトを使用 します。 PowerBuilder におけるユーザ オブジェクト、アプリケーション ペイン タ、およびスクリプト ビューの使い方についての詳細は、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください。 カスタム トランザク ション オブジェクト の例 u_trans_database ユーザ オブジェクト この節では、アプリケーション でストアド プロシージャを呼び出すために、カスタム トランザクショ ン オブジェクトの使い方を解説します。例では、u_trans_database とい う、標準クラス ユーザ オブジェクトの定義と使い方を示します。 u_trans_database ユーザ オブジェクトは、 組み込みトランザクション オ ブジェクト SQLCA から継承した子孫オブジェクトです。子孫オブジェ クトとは、先祖オブジェクトのプロパティ、変数、関数、イベントに 対するスクリプトを継承しているオブジェクトです。子孫オブジェク トは、サブクラスとも呼ばれます。 GIVE_RAISE ストアド プロシージャ u_trans_database ユーザ オブジェク トは、GIVE_RAISE という Oracle データベースのストアド プロシージャ を使用して、現行の給料の 5 % の昇給を計算するのに使用します。以 下に、GIVE_RAISE ストアド プロシージャを作成するための Oracle の 構文を示します。 アプリケーション テクニック 191 ストアド プロシージャを呼び出すためのトランザクション オブジェクトの使い方 SQL 文の区切り子 Oracle のストアド プロシージャを作成するための構文では、バック クォーテーション(`)記号を SQL 文の区切り子として使っています。 // Oracle の GIVE_RAISE 関数を作成します。 // SQL 文の区切り子は、`(バッククォーテーション)です。 CREATE OR REPLACE FUNCTION give_raise (salary IN OUT NUMBER) return NUMBER IS rv NUMBER; BEGIN salary := salary * 1.05; rv := salary; return rv; END; ` // 変更内容を保存します。 COMMIT WORK` // エラーをチェックします。 SELECT * FROM all_errors` ステップ 1: 標準クラス ユーザ オブジェクトの定義 ❖ 標準クラス ユーザ オブジェクトを定義するには 1 PowerBuilder を起動します。 2 ストアド プロシージャをサポートするデータベースに接続します。 この例では、データベース サーバ上にリモート ストアド プロシー ジャを持っている Oracle データベースに接続するものとします。 PowerBuilder における Oracle データベースとの接続および Oracle のストアド プロシージャの使い方についての詳細は、 『データベー スとの接続』マニュアルを参照してください。 3 パワーバーの[新規作成]ボタンをクリックするか、メニューバー から[ファイル|新規作成]を選択します。 新規作成 ダイアログボックスが表示されます。 4 [PB オブジェクト]タブで、[標準クラス]アイコンを選択し、 [OK]ボタンをクリックして新規の標準クラス ユーザ オブジェク トを定義します。 192 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 標準クラス データ型の選択 ダイアログボックスが表示されます。 5 ユーザ オブジェクトを継承したい組み込みシステムのデータ型と して、 [データ型]ボックスから[transaction]を選択し、 [OK]ボ タンをクリックします。 ユーザ オブジェクト ペインタのワークスペースが表示され、ユー ザ オブジェクトにプロパティ(インスタンス変数)と関数を設定 することができます。 ステップ 2: 外部関数としてのストアド プロシージャの宣言 FUNCTION または SUBROUTINE 宣言 PowerBuilder アプリケーションで、外部関数または外部サブルーチン として結果集合のないデータベースのストアド プロシージャを宣言 できます。ストアド プロシージャに戻り値がある場合は、 (FUNCTION キーワードを使用して)関数として宣言します。ストアド プロシー ジャに戻り値がないか VOID を返す場合は、(SUBROUTINE キーワード を使用して)サブルーチンとして宣言します。 RPCFUNC と ALIAS FOR キーワード 外部関数が DLL ではなく、データベースのストアド プロシージャの ためにリモート プロシージャ コール(RPC)であることを示す、外部 関数や外部サブルーチンの宣言で RPCFUNC キーワードを必ず使用し なければなりません。データベースのストアド プロシージャの名前と 異なる名前をスクリプトで使用したい場合は、ALIAS FOR "spname" 句 を使用して、ストアド プロシージャに名前を与えることができます。 ストアド プロシージャをリモート プロシージャ コールとして宣言す るための構文についての詳細は、『PowerScript リファレンス』マニュ アルの「関数とイベントの呼び出し」の章を参照してください。 アプリケーション テクニック 193 ストアド プロシージャを呼び出すためのトランザクション オブジェクトの使い方 ❖ ストアド プロシージャをユーザ オブジェクトの外部関数として宣言するには 1 ユーザ オブジェクト ペインタのスクリプト ビューで、最初のリス トから「Declare」を選択し、2 番目のリストから「Local External Funcions」を選択します。 2 カーソルをローカル外部関数の宣言ビューに置きます。ポップ アップ メニューまたは[編集]メニューから、 [形式を指定して貼 り付け| SQL |リモート ストアド プロシージャ]を選択します。 データベースからストアド プロシージャがロードされ、リモート ストアド プロシージャ ダイアログボックスが表示されます。ダイ アログボックスには、現行のデータベースにあるストアド プロ シージャ名のリストが表示されます。 3 ユーザ オブジェクトの関数として宣言するストアド プロシージャ を 1 つまたは複数選択し、[OK]ボタンをクリックします。 PowerBuilder は、データベースからストアド プロシージャの宣言 を取り出し、各宣言をビューに貼り付けます。 たとえば、sp_addlanguage を選択した場合には、1 行に表示される 宣言は次のようになります。 function long sp_addlanguage() RPCFUNC ALIAS FOR "dbo.sp_addlanguage" 4 必要であれば、アプリケーションに対するストアド プロシージャ の宣言を編集することができます。 外部関数または外部サブルーチンとして、データベースのリモー ト プロシージャ コール(RPC)を宣言する場合は、以下の構文の いずれかを使用します(構文についての詳細は、『PowerScript リ ファレンス』マニュアルを参照してください)。 194 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 FUNCTION rtndatatype functionname ( { { REF } datatype1 arg1, ..., { REF } datatypen argn } ) RPCFUNC { ALIAS FOR "spname" } SUBROUTINE functionname ( { { REF } datatype1 arg1 , ..., { REF } datatypen argn } ) RPCFUNC { ALIAS FOR "spname" } 以下に、sp_addlanguage に対する RPC 関数の宣言を編集したもの を示します。 FUNCTION long sp_addlanguage() RPCFUNC ALIAS FOR "addlanguage_proc" ステップ 3: ユーザ オブジェクトの保存 ❖ ユーザ オブジェクトを保存するには 1 ユーザ オブジェクト ペインタで、[保存]ボタンをクリックする か、メニューバーから [ファイル|名前を付けて保存]を選択し ます。 ユーザ オブジェクトの保存 ダイアログボックスが表示されます。 2 ユーザ オブジェクトの名前を指定し、そのユーザ オブジェクトに ついてのコメントを記述し、ユーザ オブジェクトを保存するライ ブラリを指定します。 3 [OK]ボタンをクリックして、ユーザ オブジェクトを保存します。 ユーザ オブジェクトは、指定した名前で選択したライブラリに保 存されます。 ステップ 4: SQLCA に対するデフォルトのグローバル変数の型の指定 ア プ リ ケ ー シ ョ ン ペ イ ン タ で、定 義 し た ユ ー ザ オ ブ ジ ェ ク ト を SQLCA に対するデフォルト グローバル変数の型として指定しなけれ ばなりません。これにより、アプリケーションを実行すると、組み込 みシステム トランザクション オブジェクトのかわりにその標準クラ ス ユーザ オブジェクトがデフォルト トランザクション オブジェクト として使用されます。 アプリケーション テクニック 195 ストアド プロシージャを呼び出すためのトランザクション オブジェクトの使い方 SQLCA のかわりに独自のトランザクション オブジェクトを使用 このプロシージャでは、アプリケーションでデフォルト トランザク ション オブジェクト SQLCA を使用するものとしていますが、独自の トランザクション オブジェクトのインスタンスを宣言して作成し、そ の後、ユーザ オブジェクトをトランザクション オブジェクトのプロパ ティとして呼び出すことも可能です。詳細については、PowerBuilder の『ユーザーズ ガイド』マニュアルの「ユーザ オブジェクト」の章を 参照してください。 ❖ SQLCA に対するデフォルト グローバル変数の型を指定するには 1 パワーバーの[開く]ボタンをクリックするか、メニューバーか ら[ファイル|開く]を選択します。 開く ダイアログボックスが表示されます。 2 [オブジェクトの種類]ドロップダウン リストボックスから[アプ リケーション]を選択します。新規のユーザ オブジェクトを使用 したいアプリケーションを選択して、 [OK]ボタンをクリックし ます。 アプリケーション ペインタ ワークスペースが表示されます。 3 プロパティ ビューで[全般]タブを選択します。 [付加的なプロパ ティ]ボタンをクリックします。 アプリケーション ダイアログボックスが表示されます。 4 [変数の型]タブを選択して、[変数の型]プロパティ ページを表 示します。 196 PowerBuilder 第 12 章 5 トランザクション オブジェクトの使い方 テキストボックスに、ステップ 1 から 3 までで定義した標準クラ ス ユーザ オブジェクトの名前を指定します。 6 [OK]ボタンか、[更新]ボタンをクリックします。 アプリケーションを実行すると、組み込みシステム オブジェクト のかわりに、そのシステム オブジェクトを継承した標準クラス ユーザ オブジェクトが使用されます。 ステップ 5: アプリケーションでユーザ オブジェクトを使用する これまでに行ったこと 先の操作手順では、標準クラス ユーザ オブジェ クト u_trans_database の外部関数としてリモート ストアド プロシー ジャ GIVE_RAISE を定義しました。次に、SQLCA に対するデフォルト グローバル変数の型として、u_trans_database を指定しました。これで、 PowerBuilder アプリケーションは、ユーザ オブジェクト内にカプセル 化されたプロパティと関数にアクセスできます。 次は、このユーザ オブジェクトにストアド プロシー ジャを実行させるスクリプトを記述する必要があります。 この後に行うこと アプリケーション テクニック 197 ストアド プロシージャを呼び出すためのトランザクション オブジェクトの使い方 アプリケーションのスクリプトで、ユーザ オブジェクトで定義したス トアド プロシージャ関数を呼び出すには、ほかの PowerBuilder オブ ジェクトと同様に SQLCA に対して、PowerScript のドット(.)表記を 使用します。ドット(.)表記の構文は以下のとおりです。 object.function ( arguments ) たとえば、以下の記述で、GIVE_RAISE ストアド プロシージャを呼び出 すことができます。 SQLCA.give_raise(salary) ❖ アプリケーションでユーザ オブジェクトを使用するには 1 スクリプトを記述するオブジェクトまたはコントロールを選択し ます。 2 スクリプトを記述したいイベントを選択します。 スクリプト ビューの使い方については、PowerBuilder の『ユーザー ズ ガイド』マニュアルを参照してください。 3 アプリケーションでストアド プロシージャによる処理を行うため に、ユーザ オブジェクトを用いたスクリプトを記述します。 以下の例は、Oracle データベースに接続し、GIVE_RAISE ストアド プロシージャを呼び出して、昇給額を計算し、昇給後の給料をメッ セージボックスに表示してから、データベースとの接続を解除し ます。 // トランザクション オブジェクトのプロパティを設定します。 SQLCA.DBMS="OR7" SQLCA.LogID="scott" SQLCA.LogPass="xxyyzz" SQLCA.ServerName="@t:oracle:testdb" SQLCA.DBParm="sqlcache=24,pbdbms=1" // Oracle データベースに接続します。 CONNECT USING SQLCA; // エラーをチェックします。 IF SQLCA.sqlcode <> 0 THEN MessageBox (" 接続エラー ",SQLCA.SQLErrText) return END IF // 現在の給料として 2,000,000 を設定します。 DOUBLE val = 2000000 DOUBLE rv 198 PowerBuilder 第 12 章 // // // // rv トランザクション オブジェクトの使い方 GIVE_RAISE ストアド プロシージャを 呼び出し、昇給額を計算します。 ストアド プロシージャを呼び出すのにドット(.)表記を 使用します。 = SQLCA.give_raise(val) // メッセージボックスに昇給後の給料を表示します。 MessageBox(" 新しい給与額は ",string(rv)) // Oracle データベースとの接続を解除します。 DISCONNECT USING SQLCA; 4 スクリプトをコンパイルして、変更内容を保存します。 エラー チェックの使い方 実際のスクリプトでは、CONNECT 文や DISCONNECT 文の実行後と GIVE_RAISE プロシージャを呼び出した後に、エラーのチェックをする べきです。詳細については、188 ページの「SQL 文実行後のエラー処 理」を参照してください。 ストアド プロシージャを呼び出すときサポートされている DBMS の機能 アプリケーションで、リモート ストアド プロシージャを呼び出すため に、カスタム トランザクション オブジェクトを定義して使用する場 合、アプリケーションが接続する DBMS によってサポートされる機能 が異なります。 この節では、PowerBuilder からアクセスできる DBMS に応じてサポー トされている機能の違いを解説します。PowerBuilder アプリケーショ ンで RPC テクニックを使用する場合は、使用している DBMS に関す る項目を参照して、できることとできないことを確認してください。 アプリケーション テクニック 199 ストアド プロシージャを呼び出すときサポートされている DBMS の機能 結果集合 リモート ストアド プロシージャを呼び出して、ストアド プロシージャ が返す結果集合にアクセスすることはできません。ストアド プロシー ジャが 1 つ以上の結果集合を返す場合、PowerBuilder は結果集合を無 視して、出力パラメータと戻り値を返します。 ストアド プロシージャが結果集合を返す場合は、埋め込み SQL の DECLARE Procedure 文を使用します。DECLARE Procedure 文についての 詳細は、『PowerScript リファレンス』マニュアルの「SQL 文」を参照 してください。 Informix ODBC アプリケーションが Informix データベースに接続する場合は、配列以 外のデータ型が使用できます。なお、Blob(Binary Large Object)型は 使用できません。 アプリケーションが ODBC データ ソースに接続する場合は、ODBC ド ライバがサポートしていれば、以下の ODBC の機能が使用できます (詳細については、使用している ODBC ドライバのマニュアルを参照 してください)。 • 表 12-5 に IN、OUT、IN OUT の各パラメータを示します。 表 12-5: ODBC の IN、OUT、IN OUT の各パラメータ パラメータ IN(入力) 結果 IN 変数は値によって渡される。プロシージャには値が 渡される OUT(出力) OUT 変数は参照によって渡される。プロシージャは、 渡された PowerScript 変数の内容を変更できる。このパ ラメータには、PowerScript の REF キーワードを指定す る IN OUT IN OUT 変数は参照によって渡される。プロシージャは (入力 / 出力) 渡された値の参照と、PowerScript 変数の内容の変更が できる。このパラメータには、PowerScript の REF キー ワードを指定する Oracle • パラメータとしての Blob データ。Blob データは、32,512 バイトま で使用できます。 • Integer 型のリターン コード アプリケーションが Oracle データベースに接続する場合は、以下の Oracle PL/SQL の機能が使用できます。 • 200 表 12-6 に IN、OUT、IN OUT の各パラメータを示します。 PowerBuilder 第 12 章 トランザクション オブジェクトの使い方 表 12-6: Oracle の IN、OUT、IN OUT の各パラメータ パラメータ IN(入力) 結果 IN 変数は値によって渡される。プロシージャには値が 渡される OUT(出力) OUT 変数は参照によって渡される。プロシージャは、 渡された PowerScript 変数の内容を変更できる。このパ ラメータには、PowerScript の REF キーワードを指定す る IN OUT IN OUT 変数は参照によって渡される。プロシージャは (入力 / 出力) 渡された値の参照と、PowerScript 変数の内容の変更が できる。このパラメータには、PowerScript の REF キー ワードを指定する Microsoft SQL Server または Sybase Adaptive Server Enterprise • パラメータとしての Blob データ。Blob データは、32,512 バイトま で使用できます。 • パラメータとしての PL/SQL テーブル。PowerScript の配列が使用 できます。 • 関数のリターン コード アプリケーションが Microsoft SQL Server または Sybase Adaptive Server Enterprise のデータベースに接続された場合には、以下の Transact-SQL 機能を使用できます。 表 12-7 に IN、OUT、IN OUT の各パラメータを示します。 • 表 12-7: Adaptive Server Enterprise および Microsoft SQL Server の IN、 OUT、IN OUT の各パラメータ パラメータ IN(入力) 結果 IN 変数は値によって渡される。プロシージャには値が 渡される OUT(出力) OUT 変数は参照によって渡される。プロシージャは、 渡された PowerScript 変数の内容を変更できる。このパ ラメータには、PowerScript の REF キーワードを指定す る IN OUT IN OUT 変数は参照によって渡される。プロシージャは (入力 / 出力) 渡された値の参照と、PowerScript 変数の内容の変更が できる。このパラメータには、PowerScript の REF キー ワードを指定する • パラメータとしての Blob データ。Blob データは、32,512 バイトま で使用できます。 • Integer 型のリターン コード アプリケーション テクニック 201 ストアド プロシージャを呼び出すときサポートされている DBMS の機能 SQL Anywhere アプリケーションが SQL Anywhere のデータベースに接続された場合 には、以下の SQL Anywhere 機能を使用できます。 • 表 12-8 に IN、OUT、IN OUT の各パラメータを示します。 表 12-8: SQL Anywhere の IN、OUT、IN OUT の各パラメータ パラメータ IN(入力) 結果 IN 変数は値によって渡される。プロシージャには値が 渡される OUT(出力) OUT 変数は参照によって渡される。プロシージャは、 渡された PowerScript 変数の内容を変更できる。このパ ラメータには、PowerScript の REF キーワードを指定す る IN OUT IN OUT 変数は参照によって渡される。プロシージャは (入力 / 出力) 渡された値の参照と、PowerScript 変数の内容の変更が できる。このパラメータには、PowerScript の REF キー ワードを指定する • 202 パラメータとしての Blob データ。Blob データは、32,512 バイトま で使用できます。 PowerBuilder 第 1 3 章 MobiLink 同期の使い方 この章について この章では、 『ユーザーズ ガイド』マニュアルの「データベース管 理」の章で説明した、MobiLink 同期の概要を補足します。同期プ ロセスの詳細なバックグラウンド、MobiLink 同期ウィザードで生 成されたオブジェクトの使用方法について説明します。さらに、 ウィザードを使用しないで同期オブジェクトを作成する方法につ いても説明します。 内容 項目 MobiLink 同期について 同期の動作方法 PowerBuilder 同期オブジェクトの使い方 統合データベースの準備 リモート データベースの作成 同期のテクニック ページ 203 208 210 222 231 237 MobiLink 同期について MobiLink は、統合データベースと呼ばれるメイン データベースと 多数のリモート データベース間の双方向の同期を実現できる、 セッションベースの同期システムです。 この節では、MobiLink の用語およびコンセプトの一部について説 明します。 参照先 MobiLink 同期の詳細については、『MobiLink - クイック・スター ト』、 『MobiLink - クライアント管理』 、 『Mobilink - サーバ管理』の 各マニュアルを参照してください。 これらのマニュアルは、SQL Anywhere 製品マニュアル のサイト http://www.ianywhere.com/developer/product_manuals/sqlanywhere/ で入 手できます。 アプリケーション テクニック 203 MobiLink 同期について すでに MobiLink について理解している場合は、210 ページの 「PowerBuilder 同期オブジェクトの使い方」の PowerBuilder と MobiLink との統合についての説明に進んでください。 データの移動と同期 データの移動が行われるのは、共有データが複数のノードにある複数 のデータベース上に分散している場合に、あるデータベースのデータ に行われた変更が別のデータベースの対応するデータに適用されると きです。データは、複製または同期によって移動できます。 データの複製では、すべてのトランザクションが一方のデータベース から他方のデータベースに移動されます。データの同期では、トラン ザクションの最終結果だけが移動されます。どちらの方法も、トラン ザクション ログ ファイルをスキャンすることで情報を取得しますが、 同期の場合はログ ファイル全体ではなく、更新されたログ ファイル セ グメントだけを使用するので、データをより高速かつ効率的に移動で きます。 同期の場合は、データをローカルで利用でき、サーバに接続しなくて も変更できます。MobiLink 同期は、ゆるやかな一貫性方式を使用しま す。このモデルは、すべての変更が一貫した方法で徐々に各サイトと 同期を取りますが、特定のタイミングで別のサイトが異なるコピーを 保持している可能性があることを意味します。同期が取られるのは、 成功したトランザクションだけです。 統合データベースとリ モート データベース 統合データベースは、SQL Anywhere、Sybase Adaptive Server Enterprise、 Oracle、 IBM DB2 UDB、または Microsoft SQL Server などのような ODBC 準拠のデータベースであり、すべてのデータのマスタ コピーを保持し ます。 リモート データベースには、統合データのサブセットが含まれていま す。MobiLink は、SQL Anywhere および UltraLite データベースと同期 を取ることができますが、PowerBuilder 11.0 アプリケーションの場合、 リモート データベースは SQL Anywhere データベースでなければなり ません。 MobiLink 同期サーバ MobiLink 同期サーバ mlsrv10 は、同期プロセスを管理し、リモート デー タベースと統合データベース サーバ間のインタフェースを提供しま す。MobiLink 同期サーバと統合データベース間の通信はすべて ODBC 接続を介して行われます。統合データベースと同期サーバは、一般に 同一マシン上は配置されますが、別のマシン上でもかまいません。 同期プロセスを開始する前に、MobiLink サーバを起動しておく必要が あります。データベース ペインタのオブジェクト ビューの[Utilities] フォルダから MobiLink 同期サーバを起動できます。 204 PowerBuilder 第 13 章 MobiLink 同期の使い方 コマンド ラインからサーバを起動する方法については、オンラインの 『MobiLink - サーバ管理』マニュアルの「Mobile Link サーバの実行」を 参照してください。 MobiLink 階層構造 MobiLink は、一般に階層構造の設定を使用します。階層構造内のノー ドは、サーバ、デスクトップ コンピュータ、およびハンドヘルド デバ イスまたは埋め込みデバイスに配置できます。単純な階層構造は、サー バ上の統合データベースと、モバイル デバイス上の複数のリモート データベースで構成できます。もう少し複雑な階層構造には、複数の レベルがあり、各レベルでいくつかのサイトがリモート データベース と統合データベースの両方として機能します。PowerBuilder アプリ ケーションでは、リモート データベースとしても機能する統合データ ベースは、SQL Anywhere データベースでなければなりません。 たとえば、リモート サイト A1、A2、A3 がローカル サーバ上の統合 データベース A と同期を取り、リモート サイト B1、B2、B3 が別の ローカル サーバ上の統合データベース B と同期を取るとします。A と B は順番にリモート サイトとして機能して、マスタ サーバ上の統合 データベース C と同期を取ります。データベース C には 任意の ODBC 準拠のデータベースを利用できますが、A と B は SQL Anywhere デー タベースでなければなりません。 アプリケーション テクニック 205 MobiLink 同期について 図 13-1: MobiLink 階層構造 同期スクリプト MobiLink 同期は、イベント駆動型のプロセスです。MobiLink クライア ントが同期を開始すると、MobiLink サーバ内で多数の同期イベントが 発生します。イベントが発生すると、MobiLink はその同期イベントと 一致するスクリプトを探します。MobiLink サーバで何らかの動作を実 行させるには、イベントに対応するスクリプトを提供する必要があり ます。 接続レベルのイベント、およびリモート データベースの各テーブル レ ベルのイベントに対応する同期スクリプトを記述できます。これらの スクリプトは統合データベースに保存します。 SQL、Java、または .NET を使用してスクリプトを記述できます。イベ ント スクリプト、および Sybase Central での MobiLink 同期プラグイン でのイベント スクリプトの記述についての詳細は、222 ページの「統 合データベースの準備」を参照してください。 206 PowerBuilder 第 13 章 MobiLink 同期クライ アント MobiLink 同期の使い方 リモート サイト上の SQL Anywhere クライアントは、コマンド ライン ユーティリティ dbmlsync を実行して同期を開始します。このユーティ リティは、リモート データベース上の 1 つまたは複数のサブスクリプ ションと MobiLink 同期サーバとの同期を取ります。サブスクリプショ ンについては、次の「パブリケーション、アーティクル、ユーザ、サ ブスクリプション」で説明します。dbmlsync ユーティリティとそのオ プションについての詳細は、SQL Anywhere オンライン ブックのイン デックスで「dbmlsync ユーティリティ」を参照してください。 PowerBuilder では、ASA MobiLink 同期ウィザードで作成される同期オ ブジェクトが dbmlsync プロセスを管理します。詳細については、210 ページの「PowerBuilder 同期オブジェクトの使い方」を参照してくだ さい。 パブリケーション、 アーティクル、ユー ザ、サブスクリプショ ン パブリケーションは、リモート データベース上のデータベース オブ ジェクトであり、同期を取るテーブルとカラムを識別します。各パブ リケーションには、1 つまたは複数のアーティクルを含めることがで きます。アーティクルはデータベース オブジェクトであり、テーブル 全体、またはテーブル内のカラムと行のサブセットを示します。 ユーザは、リモート データベース上のデータベース オブジェクトであ り、固有の同期クライアントを記述します。MobilLink システムのリ モート データベースごとに 1 つの MobiLink ユーザ名があります。統 合データベース上の ml_user という MobiLink システム テーブルは、 MobiLink ユーザ名のリストを保持します。これらの名前は認証に使用 されます。 サブスクリプションは、ユーザを 1 つまたは複数のパブリケーションに 関連付けます。また、同期プロトコル(TCP/IP、HTTP、または HTTPS) 、 アドレス(myserver.acmetools.com など)、その他の任意の接続および 拡張オプションを指定します。 ユーザ、パブリケーション、サブスクリプションは、リモート データ ベースで作成されます。これらは、Sybase Central で SQL Anywhere プ ラグイン(MobiLink 同期プラグインではありません)を使用して作成 できます。ユーザ、パブリケーション、サブスクリプションの作成に ついては、231 ページの「リモート データベースの作成」を参照して ください。 アプリケーション テクニック 207 同期の動作方法 同期プロセス dbmlsync は、TCP/IP、HTTP、または HTTPS を使用してリモート デー タベースに接続し、統合データベースにアップロードするデータのス トリーム(アップロード ストリーム)を準備します。dbmlsync は、リ モート データベースのトランザクション ログ内の情報を使用して、 アップロード ストリームを作成します。アップロード ストリームに は、MobiLink ユーザ名とパスワード、使用する同期スクリプトのバー ジョン、前回の同期のタイムスタンプ、パブリケーション内のテーブ ルとカラムのスキーマ、および前回の同期以降のすべての挿入、更新、 削除の最終結果が含まれます。 アップロード ストリームを作成した後、dbmlsync は、指定されたパブ リケーションとサブスクリプションに格納された情報を使用して、 MobiLink 同期サーバに接続し、データを交換します。 MobiLink 同期サーバは、データを受信すると、統合データベースを更 新し、関連する変更をすべて含むダウンロード ストリームを作成し て、それをリモート サイトに戻します。それぞれの同期が正常に終了 した時点で、統合データベースとリモート データベースの一貫性が維 持されています。同期は、トランザクション全体について実行される か全く実行されないかのどちらかです。これで、各データベースでト ランザクションの整合性が維持されます。 同期の動作方法 MLSync イベントの実 装方法 図 13-2 に示すように、PowerBuilder アプリケーションの MLSync オブ ジェクトと dbmlsync プロセスは、2 つのウィンドウ間でメッセージを 送信して互いに通信します。MLSync オブジェクトが作成するウィン ドウは内部関数 MlSyncControlWindowProc を使用して、これらのメッ セージを処理します。 Synchronize 関数は、dbmlsync を起動するコマンド ライン文字列の最後 に、 「-wh window_handle」引数を追加します。これにより、dbmlsync は WM_COPYDATA メッセージをこのウィンドウ ハンドルに送信しま す。MlSyncControlWindowProc は次に、MLSync オブジェクトの対象イ ベントを起動させます。 208 PowerBuilder 第 13 章 MobiLink 同期の使い方 図 13-2: 同期プロセスの動作方法 進行状態ウィンドウ イベントの起動方法 MobiLink 同期ウィザードは、イベントごとに PowerScript コードを含 む MLSync オブジェクトのインスタンスを生成します。生成されたイ ンスタンスが適切である場合、このコードは進行状態ウィンドウで同 じ名前のイベントを起動します。この進行状態ウィンドウは、ウィザー ドが生成したウィンドウ、またはアプリケーション用にカスタマイズ されたウィンドウのいずれかです。 CancelSync 関数の実 装方法 dbmlsync コマンド文字列には「-wc window_class」引数があります。こ の引数には、dbmlsync が登録して作成するコミュニケーション ウィン ドウのクラス名を指定します。PowerBuilder アプリケーションで、任 意のイベント処理ロジックを実行中に同期プロセスをキャンセルする 必要がある場合は、CancelSync を呼び出します。この関数は、-wc ウィ ンドウ クラスに関連付けられたウィンドウ ハンドルを見つけて、 WM_CLOSE メッセージを送信します。 アプリケーション テクニック 209 PowerBuilder 同期オブジェクトの使い方 PowerBuilder 同期オブジェクトの使い方 新規作成 ダイアログボックスの[データベース]ページから ASA MobiLink 同期ウィザードを実行すると、ウィザードによってオブジェ クトが生成されます。これを PowerBuilder アプリケーションからの MobiLink 同期リクエストの開始と制御に使用できます。これらのオブ ジェクトを使用して、同期プロセス中にフィードバックを取得したり、 同期中の特定の時点での PowerScript イベントのコードを作成したり、 プロセスをプログラムによってキャンセルしたりできます。 MobiLink 同期ウィザードの詳細については、『ユーザーズ ガイド』マ ニュアルの「データベースの管理」を参照してください。 ウィザードを使用する準備 本稼動アプリケーションでウィザードを使用する前に、次の作業を行 う必要があります。 • 222 ページの「統合データベースの準備」に従って、統合データ ベースをセットアップし、同期スクリプトを記述します。 • 231 ページの「リモート データベースの作成」に従って、デスク トップにリモート データベースを作成し、1 つまたは複数のパブ リケーション、ユーザ、サブスクリプションをセットアップしま す。 • PowerBuilder オンライン ヘルプにある『データベースとの接続』マ ニュアルと 221 ページの「ファイル DSN によるレジストリ DSN の代用方法」に従って、すべてのリモート マシンで ODBC マネー ジャにデータベースを登録するか、リモート データベース用の ファイル DSN を作成します。 • 219 ページの「リモート マシンでの同期の実行時要件」に従って、 すべてのリモート マシンに必要なサポート ファイルがあること を確認します。 • (オプション)PowerBuilder オンライン ヘルプにある『データベー スとの接続』マニュアルに従って、リモート データベースのデー タベース接続プロファイルを作成します。プロファイルを作成す ると、ウィザードが、MobiLink サブスクリプションが入力されて いるリモート データベースから、パブリケーションのリストを取 り出すことができます。 210 PowerBuilder 第 13 章 MobiLink 同期の使い方 生成されるもの ウィザードは、2 つのオブジェクト セットを生成します。 同期を開始およびモニ タするオブジェクト 1 つ目のオブジェクト セットは、エンド ユーザによる同期の開始およ びモニタに使用できます。 • nvo_appname_mlsync – MobiLink クライアントを制御するカスタム クラス ユーザ オブジェクト(appname はアプリケーションの名前) • gf_appname_sync – ユーザ オブジェクトをインスタンス化し、同期 リクエストを開始する関数を呼び出すグローバル関数 • w_appname_syncprogress – 同期プロセスの進行をレポートする、省 略可能なステータス ウィンドウ ウィザードでは、アプリケーションでステータス ウィンドウを使用す るかどうかを選択できます。生成されるステータス ウィンドウには、 ウィンドウを閉じる前にユーザがステータスを確認できる[OK]ボタ ンと、完了前の同期をユーザがキャンセルできる[キャンセル]ボタ ンがあります。アプリケーションのニーズに合わせてウィンドウをカ スタマイズすることもできます。 同期オプションを変更 するオブジェクト 2 つ目のオブジェクト セットは、ウィザードで[ユーザのパスワード と実行オプションの入力]を選択している場合にだけ生成されます。 これを使用すると、エンド ユーザは同期を開始する前に同期オプショ ンを変更できます。 • w_appname_sync_options – MobiLink ユーザ名とパスワード、 MobiLink サーバのホスト名とポート、および dbmlsync のその他の オプションの変更、およびステータスの表示方法の選択をエンド ユーザが行うことができるオプション ウィンドウ。 • gf_appname_configure_sync – オプション ウィンドウを開くグローバ ル関数。ユーザが[OK]をクリックした場合は、gf_appname_sync を呼び出して同期を開始します。 オプション ウィンドウを使用するほとんどのアプリケーションは、同 期を開始するための 2 つのメニュー項目またはコマンド ボタンを提供 します。1 つは、ユーザが同期をリクエストする前に dbmlsync オプショ ンをセットアップまたは変更できるオプション ウィンドウを開きま す。もう 1 つは、現在のオプションで同期をリクエストします。 アプリケーション テクニック 211 PowerBuilder 同期オブジェクトの使い方 MLSync のインスタンスの作成 Dbmlsync.exe を起動する非ビジュアル オブジェクトの作成に、MobiLink 同期ウィザードを使用する必要はありません。次の方法で、MLSync シ ステム オブジェクトをアプリケーションに組み込むことができます。 プログラミングによる MLSync オブジェクト の追加 • PowerScript を使用してプログラムで作成 • 新規作成 ダイアログボックスから選択 次に示すコード フラグメントは、MLSync オブジェクトのインスタン スを作成し、システムの SyncParm 構造体のインスタンスを使用して、 オプションのプロパティと必要なプロパティすべてをプログラムで設 定します。次に、Synchronize 関数を呼び出してデータベースの同期を 開始します。 SyncParm MLSync Long Parms mySync rc mySync = CREATE MLSync mySync.MLServerVersion = 9// 必須 mySync.Publication = 'salesapi'// 必須 mySync.UseLogFile = TRUE// オプション mySync.LogFileName = "C:\temp\sync.log"// オプション mySync.Datasource = 'salesdb_remote'// 必須 Parms.MLUser = '50'// 必須 Parms.MLPass = 'xyz123'// 必須 // 以下の値は DSN で設定されない場合に // 必要な値 Parms.DBUser = 'dba' Parms.DBPass = 'sql' // プロパティ値を sync オブジェクトに適用 mySync.SetParm(Parms) // 同期プロセスの起動 rc = mySync.Synchronize() destroy mySync 新規作成 ダイアログ ボックスからの MLSync オブジェクト の追加 212 新規作成 ダイアログボックスを使用して、MLSync オブジェクトを対 象 PBL に追加できます。PowerBuilder のメニューから[ファイル|新 規作成]を選択して[PB オブジェクト]タブに移動し、 [標準クラス] を選択して、次に[MLSync]を選択します。これで、ユーザ オブジェ クト ペインタに新しい MLSync オブジェクトが開かれます。ここで、 すべてまたは一部のプロパティを初期化できます。すべての設定が終 了したら、対象 PBL に新しいオブジェクトとして保存できます。 PowerBuilder 第 13 章 MobiLink 同期の使い方 すべてのプロパティは、ユーザ ID とパスワードを含めてすでに初期化 されているため、すぐに使用できます。同期を取るには、次の例に示 すような多少のコーディングが必要です。この例の MLsync オブジェ クトは、「nvo_my_mlsync」として保存したオブジェクトです。 nvo_my_mlsync mySync Long rc mySync = CREATE nvo_my_mlsync mySync.Synchronize() destroy mySync これらのコードは、通常、アプリケーション ウィンドウの 1 つで、メ ニュー項目やコマンド ボタンの Clicked イベントに追加します。 詳細情報 同期に関連するシステム オブジェクト、および、システム オブジェク トの関数、イベント、プロパティの詳細については、オンライン ヘル プの MLSynchronization、MLSync、および SyncParm を参照してくださ い。 MobiLink 同期の補助オブジェクト PowerScript コードまたは新規作成 ダイアログボックスで MLSync の インスタンスを作成する場合は、補助オブジェクトの使用を検討して ください。この補助オブジェクトはウィザードで自動的に生成され、 PowerBuilder のウィンドウ ペインタでカスタマイズできます。 既存の同期進行状態 ウィンドウの使い方 MLSync オブジェクトをインスタンス化し、SetParm を呼び出して、エ ンド ユーザが実行時に認証プロパティを設定できるようにすると、デー タベース同期の進行状況を確認する Response! 型のウィンドウを呼び 出すことができます。進行状態ウィンドウを表示するには、ウィンド ウ名と MLSync オブジェクト名を引数として指定し、OpenWithParm を 呼び出します。デフォルトでは、ウィザードは w_appname_syncprogress という名前の進行状態ウィンドウを生成し、OpenWithParm の呼び出し を追加します。 MLSync オブジェクトのプロパティ ビューでは、同期呼び出しの進行 状況を確認する、カスタマイズされた進行状態ウィンドウを選択でき ます。ウィザードで生成された進行状態ウィンドウは、通常、タブ ページの一部のフィールドが非表示になっていたり、1 ~ 2 個のタブ ページが非表示になっていたりします。このウィンドウをカスタマイ ズする場合は、すべての MobiLink アプリケーションに対して、カス タマイズされた進行状態ウィンドウを選択できます。 アプリケーション テクニック 213 PowerBuilder 同期オブジェクトの使い方 実行時における接続引 数の変更 ユーザが実行時に認証パラメータを上書きできるようにするには、カ スタマイズされたオプション ウィンドウ、または、ウィザードで生成 された同期オプション ウィンドウを呼び出します。このオプション ウィンドウでは、SyncParm オブジェクトのインスタンスを順番に呼び 出すことができます。このインスタンスは、リモート データベース テーブルなどの、より高レベルのセキュリティ保護された永続的な保 存場所から、認証値を初期化できます。一部またはすべての認証値を 書き込み可能に設定すると、エンド ユーザが実行時に上書きできるよ うになります。 MLSync オブジェクトのプロパティ設定の管理 通常、MLSync オブジェクトから SetParm (SyncParm) を呼び出す場合、 MLSync オブジェクトのプロパティに対して設定した認証値 (AuthenticationParms、DBUser、DBPass、EncryptionKey、MLUser、お よび MLPass)を、特定の SyncParm プロパティの値が空の文字列で あっても、自動的に上書きします。ただし、SetParm を呼び出す前に、 SetNull を呼び出して SyncParm オブジェクトの特定のプロパティを NULL に設定した場合は、かわりに、MLSync オブジェクトのプロパ ティ値が使用されます。 デフォルトの同期オプション ウィンドウ w_appname_sync_options は、 Message オブジェクトの PowerObjectParm プロパティを使用して、呼び 出し側に SyncParm 構造体を返します。これによって呼び出し側は、よ り機密性の高い認証プロパティ値を安全な場所に保存できます。また、 実際の同期処理を続行するかどうかを指定する整数値を持つ SyncParm ReturnCode プロパティも設定できます。 オプション ウィンド ウのデフォルトのタブ ページ デフォルトの同期オプション ウィンドウには、[サブスクリプショ ン]、 [SQL Anywhere] 、 [ML サーバ]、 [設定]の 4 つのタブ ページが あります。 [サブスクリプション]ページ MobiLink ウィザードを使用したときに、 利用可能なパブリケーションのリストから 1 つまたは複数のパブリ ケーションを選択しています。選択したパブリケーションは、 [サブス クリプション]ページに表示されますが、実行時に編集することはで きません。 各リモート ユーザは、このページで MobiLink 同期ユーザ名を入力す ることができます。この名前は、サブスクリプションでそのページに 表示されているパブリケーションと関連付けられている必要がありま す。アプリケーションを使用する MobiLink ユーザがいつも同じである 場合は、この情報を再入力する必要はありません。名前は、レジスト リに保存され、このデバイスのアプリケーションから同期処理が起動 されるたびにデフォルトで使用されます。 214 PowerBuilder 第 13 章 MobiLink 同期の使い方 MobiLink のパスワードと認証パラメータは、ユーザのレジストリには 保存されません。どちらも、毎回、ユーザが入力するか、安全なデー タベースから提供されます。 リモート ユーザは、このページで DSN ファ イル名を入力して、リモート データベースとの接続に必要なすべての 引数を渡すことができます。 [SQL Anywhere]ページ DSN ファイルが使用されない場合、または DSN ファイルにユーザ名 およびパスワードが記述されていない場合は、各リモート ユーザがリ モート データベースのユーザ名を入力できます。名前はレジストリに 保存され、このデバイスのアプリケーションから同期処理が起動され るたびにデフォルトで使用されます。 図 13-3 に、オプション ウィンドウの[SQL Anywhere]タブ ページを 示します。このタブ ページのフィールドは、 [DSN]、 [ユーザ ID] 、 [パ スワード]、および[暗号化キー]です。データベース パスワードと 暗号化キーはレジストリには保存されません。 図 13-3: 同期オプション ウィンドウ サブスクリプションを作成するときは、プロトコ ル、ホスト、ポート、そのほかの接続オプションを指定します。テス トを簡単にするために、デフォルト プロトコルを TCP/IP、デフォルト ホストを localhost にします。デフォルト ポートは、TCP/IP の場合は 2439、HTTP の場合は 80、HTTPS の場合は 443 です。 [ML サーバ]ページ アプリケーション テクニック 215 PowerBuilder 同期オブジェクトの使い方 テスト中にこれらのデフォルト値の変更が必要になる場合がありま す。また、サーバが別のホストに移動された場合やポートが変更され た場合は、アプリケーションの使用中にユーザがデフォルト値を変更 する必要があります。設計時にホストおよびポートの値を入力しな かった場合、および、ユーザがこのページで何も変更をしない場合、 dbmlsync はサブスクリプション内の値を使用します。 サブスクリプションの詳細については、236 ページの「サブスクリプ ションの追加」を参照してください。 [設定]ページ [設定]ページには、ログ オプションと、設計時に指定 したそのほかの dbmlsync オプションが表示され、ユーザはこれらのオ プションを実行時に変更できます。また、このページを使用して、同 期進行状態ウィンドウを表示するかどうかを選択できます。 拡張オプション 拡張オプションを追加するには、dbmlsync コマンド ラインで -e スイッ チを指定します。テキストボックスに -e スイッチを入力する必要はあ りません。 アプリケーションでの同期オブジェクトの使い方 生成されたオブジェクトを使用する前に、PowerBuilder のペインタを 使ってオブジェクトの操作方法を理解しておいてください。多数の関 数およびイベント スクリプトに、その用途を説明するコメントが含ま れています。 アプリケーションによる同期の管理を全面的に制御できるように、す べてのソース コードが提供されています。オブジェクトは、そのまま でも、変更しても、または独自オブジェクトのテンプレートとしても 使用できます。 ユーザ オブジェクト のプロパティ 216 nvo_appname_mlsync ユーザ オブジェクトには、パブリケーション名、 MobiLink サーバのホスト名とポート、リモート データベースに接続す るためのユーザ名とパスワードなどの特定の dbmlsync 引数を示すプロ パティが含まれています。 PowerBuilder 第 13 章 MobiLink 同期の使い方 ウィザードを実行すると、これらのプロパティで指定した値が、ユー ザ オブジェクトの constructor イベントのスクリプトにデフォルト値と して設定されます。また、これらの値は、開発コンピュータの Windows レジストリ HKEY_CURRENT_USER\Software\Sybase\PowerBuilder\11.0\appname \MobiLink にも設定されます。ここで appname はアプリケーションの 名前です。 実行時に、constructor イベントのスクリプトは、リモート マシンのレ ジストリからプロパティの値を取得します。レジストリから取得でき ない場合、またはレジストリ設定を上書きしている場合は、かわりに、 スクリプトで提供されているデフォルト値が使用され、レジストリに 書き込まれます。 イベント スクリプトのデフォルト値は変更できます。また、 w_appname_sync_options ウィンドウを開くメニュー項目を提供するこ とによって、実行時にユーザがレジストリ値を変更できるようにする こともできます。 dbmlsync の開始 ユーザが同期プロセスを開始できるようにするには、gf_appname_sync グローバル関数を呼び出すボタンまたはメニューのイベントスクリプ トを記述します。この関数は、nvo_appname_mlsync ユーザ オブジェク トのインスタンスを作成します。ユーザ オブジェクトの constructor イベ ント スクリプトは、リモート マシンのレジストリの appname\MobiLink キーを設定します。 ウィザードで進行状態ウィンドウを表示するように指定した場合、グロー バル関数は進行状態ウィンドウを開き、このウィンドウの ue_postopen イ ベントがユーザ オブジェクトの同期関数 nvo_appname_mlsync を呼び 出します。それ以外の場合、グローバル関数は同期関数を呼び出しま す。同期関数は dbmlsync を外部プロセスとして起動します。 MobiLink ユーザ名お よびパスワードの入力 グローバル関数は、唯一の引数として構造体を受け取ります。ここで は、インスタンス化したシステムの SyncParm 構造体を渡すことができ ます。この構造体には、String データ型の 6 つの変数(MobiLink とリ モート データベースそれぞれのユーザ名とパスワード、認証パラメー タと暗号化キーの変数)と、リターン コード用に Long データ型の別 の変数が含まれています。 引数として渡す構造体に有効な値を割り当てる場合、グローバル関数 は、MobiLink サーバとリモート データベースの接続を可能にするユー ザ オブジェクトに、これらの値を渡します。 アプリケーション テクニック 217 PowerBuilder 同期オブジェクトの使い方 オプション ウィンドウ(214 ページの「オプション ウィンドウのデ フォルトのタブ ページ」を参照)は、ユーザが初めて同期を開始する ときにこれらの値をレジストリに確実に格納するメカニズムを提供し ています。機密性の高いパスワードと暗号化情報は、レジストリには 保存されません。初回以降の同期は、ユーザが情報を再入力しなくて も開始できますが、オプション ウィンドウを使用してレジストリ値を 上書きしたり再設定したりすることもできます。 同期後のデータの取り 出し 同期の後は、一般に同期エラーについてテストし、新しく同期された データベースからデータを取り出します。たとえば、次のようになり ます。 if gf_myapp_sync(s_opt) <> 0 then MessageBox(" エラー ", "MobiLink エラー ") else dw_1.Retrieve() end if dbmlsync メッセージ の取得 PowerBuilder VM は、同期プロセスの実行中に、dbmlsync プロセスから のメッセージをトラップし、ユーザ オブジェクトのイベントを発生さ せます。 次のイベントは、同期開始前のアップロード ストリームを準備すると きに発生します。 ue_begin_logscan ( long rescan_log ) ue_progress_info ( long progress_index, long progress_max ) ue_end_logscan ( ) 次のイベントは、223 ページの「接続イベント」で説明する同期サー バでのイベントに対応しています。 ue_begin_sync ( string user_name, string pub_names) ue_connect_MobiLink ( ) ue_begin_upload ( ) ue_end_upload ( ) ue_begin_download ( ) ue_end_download ( long upsert_rows, long delete_rows ) ue_disconnect_MobiLink( ) ue_end_sync ( long status_code ) 次のイベントは、ue_end_upload の後、ue_begin_download の前に発生し ます。 ue_wait_for_upload_ack ( ) ue_upload_ack ( long upload_status ) 218 PowerBuilder 第 13 章 MobiLink 同期の使い方 次のイベントは、各種のメッセージがサーバから送信されるときに発 生します。 ue_error_msg ( string error_msg ) ue_warning_msg ( string warning_msg ) ue_file_msg ( string file_msg ) ue_display_msg ( string display_msg ) ウィザードが作成するデフォルト イベント スクリプトは、オプション の進行状態ウィンドウがある場合はそこで対応するイベントを発生さ せます。ウィンドウ イベントは、進行状態ウィンドウのマルチライン エディット コントロールに進行状況(プログレス)を書き込みます。 一部のウィンドウ イベントは、実行中の同期操作のフェーズ(ログ ス キャン、アップロード、またはダウンロード)を表示するスタティッ ク テキスト コントロールも更新します。また、完了した操作のパーセ ンテージを表示する水平プログレスバーを制御します。 ユーザ オブジェクトまたはウィンドウ イベントに、対応する MobiLink イベントが同期プロセス中に発生した時点で実行されるコードを追加 することもできます。dbmlsync プロセスは、イベント メッセージを制 御元の PowerBuilder アプリケーションに送信し、PowerBuilder イベン ト処理が完了するまで待ってから処理を継続します。 同期のキャンセル 進行状態ウィンドウの[キャンセル]ボタンは、cancelsync ユーザ オ ブジェクト関数を呼び出して、同期プロセスをキャンセルします。ア プリケーションが進行状態ウィンドウを使用しない場合は、この関数 を、アプリケーションの別のイベント スクリプトで呼び出すことがで きます。 リモート マシンでの同期の実行時要件 リモート マシンで必 要なサポート ファイ ル PowerBuilder または SQL Anywhere をリモート マシンにインストール していない場合、PowerBuilder アプリケーションとの MobiLink 同期を 使用するには、表 13-1 に示されているファイルをコピーする必要があ ります。これらのファイルは、リモート マシンのシステム パス、または PowerBuilder アプリケーションをコピーしたディレクトリにコピーし てください。 アプリケーション テクニック 219 PowerBuilder 同期オブジェクトの使い方 表 13-1: リモート マシンのシステム パスに必要なランタイム ファイル リモート マシンのレ ジストリ要件 必須ファイル PBVM110.DLL、PBDWE110.DLL、 PBSHR110.DLL、PBODB110.DLL、 PBODB110.INI、LIBJCC.DLL、 LIBJUTILS.DLL 説明 開発マシンの Shared\PowerBuilder ディ レクトリからコピーできる PowerBuilder ファイル ATL71.DLL、GDIPLUS.DLL、 MSVCP71.DLL、MSVCR71.DLL PowerBuilder とともに出荷される Microsoft ファイル。クライアント アプ リケーションとこれらのファイルを配 布する際の制限については、『リリー ス ノート』マニュアルを参照してくだ さい。 DBENG10.EXE、 DBMLSYNC.EXE、 DBSERV10.DLL、 DBTOOL10.DLL、 DBODBC10.DLL、 DBMLSOCK.DLL、 DBLIB10.DLL、DBGEN10.DLL、 DBCON10.DLL、DBCTRS.DLL 開発マシンの Sybase\SQL Anywhere 10\win32 ディレクトリから コピーできる SQL Anywhere および MobiLink ファイル。これらのファイル は、PowerBuilder アプリケーションお よびサポート ランタイム ファイルを コピーする場所の「win32」サブディ レクトリにコピーする必要がある MobiLink 同期で使用するすべてのリモート マシンに SQL Anywhere を インストールする場合は、必要なレジストリ エントリが自動的に割り 当てられます。SQL Anywhere および MobiLink ファイルをリモート マ シンにコピーする場合は、 HKEY_CURRENT_USER\SOFTWARE\Sybase\SQL Anywhere\10.0 レジ ストリ キーを作成して、SQL Anywhere および MobiLink ファイルをコ ピーした win32 サブディレクトリの親ディレクトリを示す「Location」 文字列値を追加する必要があります(nvo_appname_sync ユーザ オブ ジェクトの uf_runsync 関数のコードは、このレジストリ値に割り当て たパスの末尾に「\win32\dbmlsync.exe」を追加します)。 ASA MobiLink 同期ウィザードで生成されたオブジェクトも、リモート SQL Anywhere 接続の ODBC データ ソースを定義するレジストリ エン トリを必要とします。表 13-2 に、必須レジストリ エントリを示します。 これらのレジストリ エントリをインストールする REG ファイルを作 成できます。 表 13-2: リモート マシンでの必須レジストリ エントリ レジストリ キー HKEY_LOCAL_MACHINE\SOFT WARE\ ODBC\ODBCINST.INI\SQL Anywhere\10.0 220 文字列値の名前と割り当てるデータ Driver = DBODBC10.DLL へのフルパス Setup = DBODBC10.DLL へのフルパス PowerBuilder 第 13 章 レジストリ キー HKEY_LOCAL_MACHINE\SOFT WARE\ ODBC\ODBCINST.INI\ODBC Drivers 文字列値の名前と割り当てるデータ SQL Anywhere 10.0 = "Installed" HKEY_LOCAL_MACHINE\SOFT WARE\ ODBC\ODBC.INI\ODBC Data Sources HKEY_LOCAL_MACHINE \ S OFTWARE\ ODBC\ODBC.INI\dataSourceN dataSourceName = "SQL Anywhere 10.0" ame ファイル DSN による レジストリ DSN の代 用方法 MobiLink 同期の使い方 Driver = DBODBC10.DLL へのフルパス Userid = リモート データベースのユーザ 名 Password = リモート データベースへの パスワード DatabaseName = remoteDatabaseName DatabaseFile = リモート データベースへ のフルパス ServerName = remoteDatabaseName Start = "dbeng10 -c 8M" CommLinks = "shmem" リモート データベース接続に対するファイル DSN またはレジストリ DSN を使用できます。絶対パス名の指定を回避するには、ファイル DSN を ODBC レジストリ キー(通常は c:\program files\common files\ODBC\data sources)で指定したパスにコピーします。 次に、有効なファイル DSN の内容の例を示します。 [ODBC] DRIVER=SQL Anywhere 10.0 UID=dba Compress=NO AutoStop=YES Start=dbeng10 -c 8M -zl -ti 0 EngineName=SalesDB_Remote DBN=SalesDB_Remote DatabaseFile=C:\work\salesdb\salesdb_remote.db DatabaseName=SalesDB_remote MLSync オブジェクトの Datasource プロパティは、次のルールを使用 して、レジストリ DSN とファイル DSN を区別します。 • Datasource の名前の最後が .dsn ファイル拡張子の場合は、ファイ ル DSN • Datasource の名前の先頭が「drive:\」接頭辞の場合は、ファイル DSN(drive は任意のアルファベット文字) アプリケーション テクニック 221 統合データベースの準備 EBF が適用される前のファイル DSN の場所 SQL Anywhere 10.0.0 または Adaptive Server Anywhere 9 に最新の EBF を適用していない状態で、フルパスが指定されていない場合、dbmlsync はファイル DSN を、ODBC レジストリ キーで指定されたパスではな く、現行ディレクトリで探します。SQL Anywhere 10.0.1 以降で絶対パ スが指定されていない場合は、レジストリ キーがファイル DSN の検 索に使用されます。 統合データベースの準備 新規データベースを設計しているか、既存のデータベースを MobiLink 統合データベースとして使用するように準備しているかにかかわらず、 そのデータベースに MobiLink システム テーブルをインストールする必 要があります。SQL Anywhere は、Sybase Adaptive Server Enterprise、 Oracle、Microsoft SQL Server、および IBM DB2 用のセットアップ スク リプトを提供します。SQL Anywhere データベースにはセットアップ スクリプトは必要ありません。 MobiLink システム テーブルは、MobiLink ユーザ、テーブル、スクリ プト、スクリプトのバージョンについての情報を統合データベースに 格納します。これらのテーブルに直接アクセスすることはおそらくあ りませんが、同期スクリプトを追加するなどの操作を行うとテーブル は変更されます。 ODBC 接続およびド ライバ 同期を実行するために、MobiLink 同期サーバは、統合データベースと ODBC 接続する必要があります。使用するサーバには ODBC ドライバ が必要です。また、MobiLink 同期サーバを実行しているマシン上の データベース用に ODBC データ ソースを作成する必要があります。サ ポートされているドライバのリストについては、Recommended ODBC Drivers for MobiLink のサイト http://www.sybase.com/detail?id=1011880 を参照 してください。 同期スクリプトの記述 同期中に発生するイベントには 2 つのタイプがあるので、それぞれに ついて同期スクリプトを記述する必要があります。 222 • 接続イベント – それぞれの同期中に必要な全体的なタスクを実行 します。 • テーブル イベント – 特定のテーブルに関連付けられ、そのテーブ ル内のデータの変更に関連するタスクを実行します。 PowerBuilder 第 13 章 MobiLink 同期の使い方 接続イベント 接続レベルでは、主要なイベントは次の順に発生します。 begin_connection begin_synchronization begin_upload end_upload prepare_for_download begin_download end_download end_synchronization end_connection 同期リクエストが発生すると、begin_connection イベントが発生します。 スクリプトの現行バージョンのすべての同期リクエストが完了する と、end_connection イベントが発生します。通常、これらのイベントの スクリプトに、変数宣言やデータベースのクリーンアップなどの初期 化およびクリーンアップ コードを配置します。 begin_connection および end_connection 以外のすべてのイベントは、統 合データベースの ml_user テーブルに格納されている MobiLink ユーザ 名をパラメータとして取ります。パラメータ値と置き換えたい場所に 疑問符を配置すると、スクリプトでパラメータを使用できます。 SQL Anywhere データベースのスクリプトを読みやすくするには、 begin_connection スクリプトで変数を宣言し、それを begin_synchronization スクリプトで ml_username の値に設定します。 たとえば、begin_connection に次の行を挿入します。 CREATE VARIABLE @sync_user VARCHAR(128); begin_synchronization に次の行を挿入します。 SET @sync_user = ? begin_synchronization および end_synchronization イベントは、リモート データベースと統合データベースに変更が適用される前と後に発生し ます。 begin_upload イベントは、アップロード トランザクションの開始を示 します。統合データベースに対する適切な挿入と更新が、すべてのリ モート テーブルについて実行されます。その後すべてのリモート テー ブルで適切に行が削除されます。end_upload の後、アップロードの変 更がコミットされます。 アプリケーション テクニック 223 統合データベースの準備 統合データベースから行を削除したくない場合は、upload_delete イベン ト に 対 す る ス ク リ プ ト を 書 か な い か、PowerScript コ ー ド で STOP SYNCHRONIZATION DELETE ステートメントを使用します。詳細につい ては、239 ページの「リモート データベースだけからの行の削除」を 参照してください。 begin_download イベントは、ダウンロード トランザクションの開始を 示します。すべてのリモート テーブルで適切な削除が実行され、その 後 download_cursor で、すべてのリモート テーブルで適切に行が追加さ れます。end_download の後、ダウンロードの変更がコミットされます。 これらのイベントは、最後のダウンロードの日付をパラメータとして 保持します。 handle_error、report_error、synchronization_statistics など、そのほかの接続 レベルのイベントが発生することもあります。すべてのイベントとそ の使用例については、『MobiLink 管理ガイド』マニュアルの同期イベ ントについての章を参照してください。 テーブル イベント begin_download や end_upload な ど、begin_synchronization イ ベ ン ト と end_synchronization イベントの間に発生する接続イベントの多くには、 対応するテーブル イベントもあります。これらのイベントとその他の 全体的なテーブルのイベントは、変更を保持する中間テーブルの作成 やログ ファイルへの情報の出力などのタスクに使用できます。 テーブルの各行に適用するテーブル イベントのスクリプトを記述す ることもできます。行レベルのイベントの場合、スクリプト内のカラ ム の順 序は、そ れらの カラ ムがリ モー ト デー タベー スの CREATE TABLE ステートメントで出現する順序と一致していなければなりませ ん。また、スクリプト内のカラム名は、統合データベース上のカラム 名を参照する必要があります。 デフォルト スクリプ トの生成 行レベルのイベントは複数ありますが、ほとんどのテーブルで必要に なるのは、3 つのアップロード イベント(INSERT、UPDATE、DELETE) と 1 つのダウンロード イベントについてのスクリプトです。各テーブ ルに対してこれらの 4 つのスクリプトを作成するタスクを高速化する には、Sybase Central の MobiLink プラグインから「create a synchronization model」タスクを実行すると、これらのスクリプトを自動的に生成でき ます。 MobiLink プラグインの詳細については、『MobiLink クイック・スター ト』マニュアルを参照してください。 224 PowerBuilder 第 13 章 MobiLink 同期の使い方 MobiLink プラグインを使用すると、MobiLink の以前のバージョンで生 成されたデフォルト スクリプトよりも多くの機能を、デフォルト スク リプトに追加できます。ただし、SQL Anywhere 10 ではなく ASA 8 ま たは ASA 9 を使用している場合は、-za スイッチを使用して MobiLink 同期サーバを起動し、dbmlsync の SendColumnNames 拡張オプションを 設定することで、前バージョンのデフォルトの同期スクリプトを生成 できます。 PowerBuilder ユーザ インタフェースから ASA 8 または ASA 9 の同期ス クリプトを生成する方法は、次のとおりです。 ❖ PowerBuilder で ASA 8 または ASA 9 の同期スクリプトを自動的に生成す るには 1 データベース ペインタで ODBC の[Utilities]フォルダを展開し、 [MobiLink Synchronization Server]項目をダブルクリックします。 MobiLink 同期 サーバ オプション ダイアログボックスが表示され ます。 2 [MobiLink バージョン]ドロップダウン リストから、Adaptive Server Anywhere 8 または 9 を選択します。 [自動スクリプト生成]チェックボックスをオンにします。 3 [OK]をクリックしてサーバを起動します。 このダイアログボックスは、データベース ペインタおよび DB プ ロファイル ダイアログボックスの[Utilities]フォルダから開くこ とができます。 4 アプリケーションで、w_appname_sync_options ウィンドウの[設定] ページの[拡張設定]テキストボックスに、 「SendColumnNames=ON」 と入力します。 リモート データベースには、パブリケーション、ユーザ、サブス クリプションを少なくとも 1 つずつ定義しておく必要がありま す。複数のパブリケーションまたはユーザがある場合は、-n また は -u あるいはその両方のスイッチを使用して、作業するサブスク リプションを指定する必要があります。 統合データベースに既存のスクリプトがある場合、MobiLink は何 も実行しません。既存のスクリプトがない場合、MobiLink はパブ リケーションで指定されているすべてのテーブルについてスクリ プトを生成します。スクリプトは、クライアントと統合データベー スとの間で行われるデータのアップロードおよびダウンロードを 制御します。 アプリケーション テクニック 225 統合データベースの準備 リモート データベースと統合データベースでカラム名が異なる場 合は、生成されたスクリプトを変更して統合データベース上の名 前に合わせる必要があります。 コマンド プロンプトから ASA 8 または ASA 9 の同期スクリプトを生成 することもできます。-za スイッチを指定してサーバを起動し、dbmlsync を実行し、SendColumnNames 拡張オプションを on に設定します。た とえば、次のようになります。 dbmlsrv9 -c "dsn=masterdb" -za dbmlsync -c "dsn=remotedb" -e SendColumnNames=ON 生成されたスクリプト 226 表 13-3 に、Sybase Central の MobiLink プラグインで生成されるデフォ ルト スクリプトのサンプルを示します。このスクリプトは、カラム emp_id、emp_name、および dept_id を持つ emp と言う名前のテーブル に対して生成されます。主キーは emp_id です。生成されたダウンロー ド スクリプトは、ダウンロードに基づいたタイムスタンプを使用しま す。 PowerBuilder 第 13 章 MobiLink 同期の使い方 表 13-3: MobiLink プラグインで生成される同期デフォルト スクリプトのサ ンプル スクリプト名 スクリプト upload_insert INSERT INTO "GROUP1"."emp" ( "emp_id", "emp_name", "dept_id" ) VALUES ( {ml r."emp_id"}, {ml r."emp_name"}, {ml r."dept_id"} ) upload_update upload_delete download_cursor download_delete_c ursor UPDATE "GROUP1"."emp" SET "emp_name" = {ml r."emp_name"}, "dept_id" = {ml r."dept_id"} WHERE "emp_id" = {ml r."emp_id"} DELETE FROM "GROUP1"."emp" WHERE "emp_id" = {ml r."emp_id"} SELECT "GROUP1"."emp"."emp_id", "GROUP1"."emp"."emp_name", "GROUP1"."emp"."dept_id" FROM "GROUP1"."emp" WHERE "GROUP1"."emp"."last_modified" >= {ml s.last_table_download} SELECT "emp_del"."emp_id FROM "emp_del" WHERE "emp_del"."last_modified" s.last_table_download} >= {ml MobiLink プラグインで生成したスクリプトは、同期モデルを構成しま す。同期モデルを作成すると、プラグインの「Deploy a synchronization model」タスクを使用して、スクリプトを統合データベースとリモート データベース、または SQL ファイルに配布する必要があります。 表 13-3 に、ASA 9 MobiLink 同期サーバの -za コマンド スイッチを使用 して、同じテーブルに対して生成されたスクリプトを示します。デー タをダウンロードするために生成されたスクリプトは、 「スナップ ショット」同期を実行します。テーブルの完全なイメージがリモート データベースにダウンロードされます。通常、これらのスクリプトを 編集して、転送されるデータを制限する必要があります。 詳細については、237 ページの「データのダウンロードの制限」を参 照してください。 アプリケーション テクニック 227 統合データベースの準備 表 13-4: dbmlsrv9 -za で生成されたデフォルト スクリプトのサンプル スクリプト名 スクリプト upload_insert INSERT INTO emp (emp_id, emp_name, dept_id) VALUES (?,?,?) upload_update UPDATE emp SET emp_name = ?, dept_id = ? WHERE emp_id=? upload_delete DELETE FROM emp WHERE emp_id=? download_cursor SELECT emp_id, emp_name, dept_id FROM emp いずれかのスクリプトを変更する前に、同期プロセスをテストして、 生成されたスクリプトが予想どおりに動作することを確認します。1 つ変更するたびにテストを実行すると、エラーの絞り込みに役立ちま す。 Sybase Central でのスクリプトおよびユーザに対する作業 Sybase Central では、Mobile Link 同期プラグインで、既存のスクリプト を表示して変更したり、新しいスクリプトを書き込んだりすることが できます。以下の手順では、プラグインとの接続とスクリプトの記述 方法、およびユーザを統合データベースに追加する方法について説明 します。 ❖ Sybase Central で統合データベースに接続するには 1 Sybase Central を起動し、メニューバーの[接続| Mobil Link 10 に 接続]を選択します。 2 総合データベースへの接続 ダイアログボックスの[ID]ページで、 データ ソース名またはファイルを選択するか参照し、[OK]をク リックします。 MobiLink 同期プラグインで統合データベースのノードを展開すると、 [テーブル(所有者別)]、[接続スクリプト]、[同期テーブル]、 [ユー ザ]、 [バージョン]、 [通知]のフォルダが表示されます。この節のす べての手順では、まず、これらのフォルダのいずれかを開きます。 スクリプト バージョ ン 228 スクリプトは、スクリプト バージョンと呼ばれるグループに分けられ ます。特定のバージョンを指定すると、MobiLink クライアントは、アッ プロード ストリームの処理とダウンロード ストリームの準備に使用 する同期スクリプトのセットを選択できます。異なるバージョンのス クリプトを定義したい場合は、統合データベースに、まずスクリプト バージョンを追加し、その後スクリプトを追加する必要があります。 PowerBuilder 第 13 章 MobiLink 同期の使い方 2 つの異なるバージョンを作成する場合は、必要なすべてのイベント のスクリプトを両方のバージョンで用意していることを確認します。 ❖ スクリプト バージョンを追加するには 1 [バージョン]フォルダを開き、Sybase Central のメニュー バーで [ファイル|新規|バージョン]を選択します。 2 スクリプト・バージョン作成ウィザードで、バージョンの名前と、 必要に応じて説明を設定し、[完了]をクリックします。 Sybase Central によって、新しいバージョンが作成され、固有の整 数識別子が付けられます。 接続イベント用に追加されたスクリプトは、同期のたびに実行されま す。テーブル イベントに追加されたスクリプトは、特定のテーブルが 変更されたときに実行されます。テーブルに対するスクリプトを追加 する前に、そのテーブルを同期するように指定する必要があります。 同期済みのテーブルと スクリプトの追加 ❖ 同期するテーブルを追加するには 1 [同期テーブル]フォルダを開き、 [ファイル|新規|同期済みテー ブル]を選択します。 2 同期するリモート テーブルの名前を指定するか、リモート デー タベースのテーブルと同じ名前の統合データベースのテーブルを 選択します。 3 [完了]をクリックします。 ❖ 同期テーブルにスクリプトを追加するには 1 [同期テーブル]フォルダでテーブル名をダブルクリックし、 [ファイル|新規|テーブル・スクリプト]を選択します。 2 テーブル・スクリプト作成ウィザードで、スクリプトを追加する バージョンを選択し、スクリプトで実行させるイベントを選択し て、[次へ]をクリックします。 3 新しいスクリプト定義の作成とその定義を記述する言語(SQL、 Java、または .NET)を選択するか、新しいスクリプトとして共有 する既存のスクリプト バージョンを選択します。 4 [完了]をクリックします。 5 アプリケーション テクニック 表示されるエディタにスクリプトを入力し、ファイルを保存して 閉じます。 229 統合データベースの準備 たとえば、リモート データベースの Order テーブルから出荷済み の行を削除する場合は、次の SELECT ステートメントを download_delete_cursor イベントに配置できます。ここでは order_id は主キー カラムです。このイベントの最初のパラメータは、 last_download タイムスタンプです。ここでは、last_modified カラム の値を入力するために使用されています。 SELECT order_id FROM Order WHERE status = 'Shipped' AND last_modified >= ? download_delete_cursor イベントの使い方についての詳細は、オン ラインの『MobiLink - サーバ管理』マニュアルで 「download_delete_cursor スクリプトの作成」の節を参照してくださ い。 ❖ 接続レベルのスクリプトを追加するには 1 [接続スクリプト]フォルダを開き、メニュー バーの[ファイル| 新規|接続スクリプト]を選択します。 2 ユーザの追加 前の手順の 2 ~ 5 に従います。 統合データベースの ml_user テーブルに直接ユーザを追加し、そのユー ザ名とオプションのパスワードをユーザに提供できます。ユーザを追 加するには、[ユーザ]フォルダを開き、[ファイル|新規|ユーザ] を選択して、ユーザ作成ウィザードで設定します。 234 ページの「Mobile Link ユーザの作成」で説明するように、各リモー ト データベースに少なくとも 1 つのユーザ名を追加する必要がありま す。 230 PowerBuilder 第 13 章 MobiLink 同期の使い方 リモート データベースの作成 MobiLink インストールでリモート データベースとして使用するため に、任意の SQL Anywhere データベースを変換できます。また、統合 された SQL Anywhere データベースの全部または一部を使用する新し い SQL Anywhere リモート データベースを作成できます。 Sybase Central SQL Anywhere プラグイン、データベース ペインタの Create ASA Database ユーティリティ、またはその他のツールを使用し てデスクトップにデータベースを作成します。データベースで英語文 字セットを使用している場合は、1252 Latin1 照合順序を使用します。 データベースを MobiLink 同期のリモート データベースとして使用す るには、少なくとも 1 つのパブリケーションと MobiLink ユーザを作成 し、そのユーザのパブリケーションにサブスクリプションを追加する 必要があります。231 ページの「パブリケーションの作成と変更」、234 ページの「Mobile Link ユーザの作成」、および 236 ページの「サブス クリプションの追加」を参照してください。 リモート データベー ス スキーマ リモート データベース内のテーブルは、統合データベース内のテーブ ルと同じでなくてもかまいませんが、一般に、統合データベースのテー ブル構造のサブセットであるテーブル構造をリモート データベース で使用することによってデザインを単純化できます。この方法では、 リモート データベース内のすべてのテーブルが必ず統合データベー ス上に存在することになります。対応するテーブルは、統合データベー スのテーブルと同じ構造および外部キー関係を持っています。 統合データベース上のテーブルには、同期されていない別のカラムが 含まれていることがよくあります。これらのカラムを使って、同期を 促進することもできます。たとえば、タイムスタンプ カラムで、統合 データベース上の新しい行または更新された行を識別できます。また、 統合データベース上の別のカラムまたはテーブルに、リモート サイト では必要ない情報を保持することもあります。 パブリケーションの作成と変更 パブリケーションは、Sybase Central または SQL CREATE PUBLICATION ステートメントを使用して作成します。Sybase Central では、すべての パブリケーションとアーティクルが[パブリケーション]フォルダに 表示されます。この節では、Sybase Central でパブリケーションを作成 する方法について説明します。SQL を使用したパブリケーションの作 成と変更については、オンラインの『MobiLink - クライアント管理』マ ニュアルを参照してください。 アプリケーション テクニック 231 リモート データベースの作成 Mobile Link 同期プラグインではなく、Sybase Central で SQL Anywhere プラグインを使用して、MobiLink クライアントおよびリモート データ ベ ー ス に つ い て 作 業 し ま す。PowerBuilder 設 計 時 環 境 か ら Sybase Central を開始する方法については、『ユーザーズ ガイド』マニュアル を参照してください。 Sybase Central での データベースへの接続 パブリケーション、MobiLink ユーザ、サブスクリプションを作成また は変更するには、DBA 権限が必要です。 ❖ テーブル内のすべての 行およびカラムのパブ リッシュ Sybase Central のデータベースに接続するには 1 Sybase Central を起動し、Sybase Central のメニュー バーの[接続| SQL Anywhere 10 に接続]を選択します。 2 接続 ダイアログボックスの[ID] ページに、ユーザ名として「DBA」 、 パスワードとして「SQL」と入力します。データ ソース名または ファイルを選択するか参照し、[OK]をクリックします。 作成できる最も簡単なパブリケーションは、1 つまたは複数のテーブ ルのすべての行とカラムで構成される単一のアーティクルです。テー ブルはすでに存在していなければなりません。 ❖ Sybase Central で 1 つまたは複数のテーブル全体をパブリッシュするには 1 232 ページの「Sybase Central でのデータベースへの接続」の説明 に従って、Sybase Central に接続します。 2 [パブリケーション]フォルダを開き、Sybase Central メニューの [ファイル|新規|パブリケーション]を選択します。 3 新しいパブリケーションの名前を入力し、 [次へ]をクリックしま す。 4 [テーブルの指定]ページで、 [使用可能なテーブル]リストから テーブルを選択し、[追加]をクリックします。 テーブルは、右側の[選択したテーブル]リストに表示されます。 5 さらにテーブルを追加することもできます。テーブルの順序は重 要ではありません。 6 [完了]をクリックします。 テーブルのすべての行と一部だけのカラムを含むパブリケーションを 作成できます。 テーブル内の一部のカ ラムだけのパブリッ シュ ❖ Sybase Central でテーブル内の一部のカラムだけをパブリッシュするには 1 232 232 ページの「テーブル内のすべての行およびカラムのパブリッ シュ」の最初の 4 つの手順に従います。 PowerBuilder 第 13 章 MobiLink 同期の使い方 2 [次へ]をクリックします。 [カラムの指定]ページで、テーブル のアイコンをダブルクリックして[使用可能なカラム]リストを 展開します。パブリッシュするカラムをそれぞれ選択し、 [追加] をクリックします。 選択したカラムが右側に表示されます。 3 [完了]をクリックします。 テーブル内の一部の行 だけのパブリッシュ テーブルの一部または全部のカラムと、一部だけの行を含むパブリ ケーションを作成できます。それには、パブリッシュする行だけに一 致する検索条件を記述します。 MobiLink では、WHERE 句を使用して、すべてのサブスクリプション からパブリケーションに同じ行セットを除外します。パブリケーショ ンのすべてのサブスクライバは、検索条件を満たす行に対するすべて の変更をアップロードします。 ❖ Sybase Central で WHERE 句を使ってパブリケーションを作成するには 1 232 ページの「テーブル内のすべての行およびカラムのパブリッ シュ」の最初の 4 つの手順、および、必要に応じて、232 ページの 「テーブル内の一部のカラムだけのパブリッシュ」の最初の 2 つの 手順に従います。 2 [次へ]をクリックします。 [WHERE 句の指定]ページで、テーブ ルを選択し、下のボックスに検索条件を入力します。 3 [完了]をクリックします。 既存のパブリケーションにアーティクルを追加できます。 アーティクルの追加 ❖ Sybase Central でアーティクルを追加するには 1 232 ページの「Sybase Central でのデータベースへの接続」の説明 に従って、Sybase Central に接続します。 2 [パブリケーション]フォルダを開き、アーティクルを追加するパ ブリケーションの名前をダブルクリックします。 3 Sybase Central メニューの[ファイル|新規|アーティクル]を選 択します。 4 アーティクルの作成ウィザードで、テーブルを選択し、 [次へ]を クリックします。 5 一部のカラムだけが同期されるようにしたい場合は、 [選択したカ ラム]ラジオボタンを選択し、カラムを選択します。 アプリケーション テクニック 233 リモート データベースの作成 6 WHERE 句を追加する場合は、 [次へ]をクリックし、句を入力し ます。 7 [完了]をクリックします。 パブリケーションと アーティクルの変更と 削除 パブリケーションの場所に移動し、ポップアップ メニューから[プロ パティ]または[削除]を選択すると、Sybase Central で既存のパブリ ケーションを変更または削除できます。同じ方法で、アーティクルを 変更および削除することができます。 パブリケーションを変更できるのは、DBA または パブリケーションの オーナーだけです。パブリケーションを削除するには、DBA 権限が必 要です。パブリケーションを削除した場合、そのパブリケーションの すべてのサブスクリプションも同様に自動的に削除されます。 実行中の MobiLink セットアップではパブリケーションの変更を避ける 実行中の MobiLink セットアップでパブリケーションを変更すると、複 製エラーが発生して、データの損失につながるおそれがあるので、実 行する場合は十分に注意してください。 Mobile Link ユーザの作成 Mobile Link ユーザは、データベース ユーザと同じではありません。そ れぞれのタイプのユーザは、別の名前空間に置かれています。Mobile Link ユーザ ID がデータベース ユーザの名前と一致することはありま すが、これは必須ではありません。 ❖ Sybase Central で Mobile Link ユーザをリモート データベースに追加するには 1 232 ページの「Sybase Central でのデータベースへの接続」の説明 に従って、Sybase Central に接続します。 2 [Mobile Link ユーザ]フォルダを開き、Sybase Central メニューの [ファイル|新規| Mobile Link ユーザ]を選択します。 3 Mobile Link ユーザの名前を入力します。 名前は、同期中に Mobile Link 同期サーバに入力されます。本稼動 データベースでは、通常、各ユーザ名が統合データベースに追加 され、個別のユーザに提供されます。 4 [完了]をクリックします。 234 PowerBuilder 第 13 章 ❖ MobiLink 同期の使い方 Sybase Central で Mobile Link ユーザ プロパティを設定するには 1 232 ページの「Sybase Central でのデータベースへの接続」の説明 に従って、Sybase Central に接続します。 2 [Mobile Link ユーザ]フォルダを開き、Mobile Link ユーザを右ク リックし、ポップアップ メニューから[プロパティ]を選択します。 3 ❖ 必要に応じてプロパティを変更します。 Sybase Central で Mobile Link ユーザを削除するには 1 232 ページの「Sybase Central でのデータベースへの接続」の説明 に従って、Sybase Central に接続します。 2 [Mobile Link ユーザ]フォルダを開き、Mobile Link ユーザを右ク リックし、ポップアップ メニューから[削除]を選択します。 Mobile Link ユーザの削除 リモート データベースから Mobile Link ユーザを削除するには、まず そのユーザに対するすべてのサブスクリプションを削除する必要があ ります。 統合データベースへの Mobile Link ユーザの 追加 統合データベースには、同期がリクエストされたときに Mobile Link ユーザの名前の認証に使用される ml_user というテーブルが含まれて います。ユーザをリモート データベースに追加するときは、そのユー ザが ml_user テーブルにも追加されていることを確認する必要があり ます。 MobiLink 同期 サーバ オプション ダイアログボックスの[ユーザの自 動追加]チェックボックスをオンにしてサーバを起動すると、ユーザ を自動的に追加できます。このダイアログボックスは、データベース ペインタまたは DB プロファイル ダイアログボックスの[Utilities] フォルダから開くことができます。または、コマンド プロンプトから、 -zu+ スイッチを指定してサーバを起動できます。 リモート データベースで定義された任意のユーザは、authenticate_user 接続イベントのスクリプトが未定義の間は、統合データベースの ml_user テーブルに追加されます。通常、-zu+ スイッチは、本稼働環境 では使用されません。名前は、通常、統合データベースの ml_user テー ブルに追加され、その後各リモート データベースに追加されます。各 ユーザには、固有の名前とオプションのパスワードが与えられます。 アプリケーション テクニック 235 リモート データベースの作成 サブスクリプションの追加 同期サブスクリプションは、特定の Mobile Link ユーザとパブリケー ションをリンクします。少なくとも 1 つのパブリケーションと 1 人の ユーザで、サブスクリプションを作成してください。 サブスクリプションには、同期に必要なほかの情報も含めることがで きます。たとえば、Mobile Link サーバのアドレス、およびその他の接 続オプションを指定できます。特定のサブスクリプションの値は、個 別の Mobile Link ユーザの設定を上書きします。 ウィザードでのオプションの上書き PowerBuilder の ASA MobiLink 同期ウィザードでの設定を使用して、サ ブスクリプションとユーザに対して設定されている Mobile Link サー バ名とポートを上書きできます。 同期サブスクリプションは、Mobile Link SQL Anywhere リモート デー タベースで必要です。サーバ ロジックは、統合データベースの Mobile Link システム テーブルに格納されている同期スクリプトを通じて実 装されます。 単一の SQL Anywhere データベースが、複数の Mobile Link 同期サーバ と同期を取ることができます。複数のサーバとの同期を可能にするに は、各ユーザに対して異なるサブスクリプションを作成します。 ❖ Sybase Central で Mobile Link ユーザのサブスクリプションを追加するには 1 232 ページの「Sybase Central でのデータベースへの接続」の説明 に従って、Sybase Central に接続します。 2 [パブリケーション]フォルダを開き、サブスクリプションを挿入 するパブリケーションを選択し、Sybase Central の右側のペインで [同期サブスクリプション]タブを選択します。次に、メニュー バーの[ファイル|新規|同期サブスクリプション]を選択しま す。 [パブリケーション]フォルダで新しいサブスクリプションを作成 するのではなく、 [Mobile Link ユーザ]フォルダで、サブスクリプ ションを作成するユーザをダブルクリックし、メニュー バーの [ファイル|新規|同期サブスクリプション]を選択しても、新し いサブスクリプションを作成できます。 3 236 同期サブスクリプション作成ウィザードで、サブスクリプション を挿入するユーザを選択し、[完了]をクリックします。 PowerBuilder 第 13 章 MobiLink 同期の使い方 このウィザードを[Mobile Link ユーザ]フォルダから起動した場 合は、サブスクライブするパブリケーションの選択を要求する メッセージが表示されます。パブリケーションを選択して[完了] をクリックしてください。 ❖ Sybase Central でサブスクリプションを変更するには 1 232 ページの「Sybase Central でのデータベースへの接続」の説明 に従って、Sybase Central に接続します。 2 [Mobile Link ユーザ]フォルダを開き、変更するサブスクリプショ ンを所有する Mobile Link ユーザの名前をダブルクリックします。 3 [同期サブスクリプション]タブで、変更するサブスクリプショ ンを右クリックし、ポップアップ メニューの[プロパティ]を選 択します。 4 ❖ 同期サブスクリプションのプロパティ ダイアログボックスの[接 続]ページと[拡張オプション]ページで、必要に応じてプロパ ティを変更します。 Sybase Central で同期サブスクリプションを削除するには 1 232 ページの「Sybase Central でのデータベースへの接続」の説明 に従って、Sybase Central に接続します。 2 [Mobile Link ユーザ]フォルダを開き、削除するサブスクリプショ ンを所有する Mobile Link ユーザの名前をダブルクリックします。 3 [同期サブスクリプション]タブで、削除するサブスクリプション を右クリックし、[削除]をクリックします。 4 削除の確認 ダイアログボックスで、[はい]をクリックします。 同期のテクニック この節では、Mobile Link 同期を使用するアプリケーションの設計で考 慮が必要な問題を取り上げます。 データのダウンロード の制限 同期の主要な目的の 1 つは、移動されるデータの量を制限することに よって、データ移動の高速化と効率化を図ることです。download_cursor スクリプトによって転送されるデータを制限するために、タイムスタ ンプ、Mobile Link ユーザ名、またはその両方に基づいてデータを分割 できます。 アプリケーション テクニック 237 同期のテクニック タイムスタンプによる分割 ダウンロードを、前回のダウンロード以降 に変更されたデータに限定するには、統合データベースの各テーブル に last_modified カラムを追加する方法があります。テーブル自体を変更 できない場合は、主キーを保持し、download_cursor スクリプトでオリ ジナルのテーブルに結合されるシャドウ テーブルに追加します。 last_modified カラムは、統合データベースにだけ追加する必要がありま す。 SQL Anywhere では、このカラム用に組み込みの DEFAULT TIMESTAMP データ型を使用できます。他の DBMS では、更新トリガを提供して、 last_modified カラムのタイムスタンプを設定する必要があります。 タイムスタンプは、統合データベースで生成され、同期中には変更さ れずにリモート データベースにダウンロードされます。リモート デー タベースのタイム ゾーンはこれに影響しません。 ユーザベースの分割 download_cursor スクリプトには、datetime データ型 の last_download と、varchar(128)型の ml_username の 2 つのパラメー タがあります。これらのパラメータを使用すると、前回の同期以降に 変更された行だけでなく、現行ユーザに属する行にもダウンロードを 限定できます。 次のサンプル スクリプト download_cursor では、前回の同期以降に変更 された行、および ID が MobiLink ユーザ ID と一致する営業担当に該 当する行だけがダウンロードされます。 SELECT order_id, cust_id, order_date FROM Sales_Order WHERE last_modified >= ? AND sales_rep = ? こ の ス ク リ プ ト が 正 し く 機 能 す る に は、Mobile Link ユ ー ザ ID が sales_rep ID と一致しなければなりません。一致しない場合は、2 つの ID を関連付けるテーブルを結合する必要があります。 主キーの一意性 クライアントが常に接続されている従来のクライアント / サーバ環境 では、参照整合性が直接求められます。モバイル環境では、主キーが 固有であり、更新されないことを確認する必要があります。このため には、主キー プールを使用するなど、複数のテクニックがあります。 衝突の処理 たとえば、同期間隔が異なる 2 人のリモート ユーザが同じ行を更新し た場合、最新の同期が最新の更新にならない可能性があるので衝突が 発生します。この衝突を処理する必要があります。Mobile Link は、衝 突の検出と解決のためのメカニズムを提供しています。 238 PowerBuilder 第 13 章 リモート データベー スだけからの行の削除 MobiLink 同期の使い方 デフォルトでは、ユーザが同期を開始すると、前回の同期以降にデー タベースに対して行われたすべての変更の最終結果が統合データベー スにアップロードされます。しかし、データが古くなったり、顧客が 別の販売担当に移されたりしたことで、リモート ユーザがリモート データベースの特定の行を削除して空き容量を再取得している場合が あります。通常は、検出されたこれらの行を統合データベースから削 除しないでください。 削除行を処理する方法として、PowerBuilder アプリケーションのスク リプトで STOP SYNCHRONIZATION DELETE コマンドを使用して、それに 続く SQL DELETE ステートメントをトランザクション ログから隠す方 法 が あ り ま す。そ の 接 続 で の そ れ 以 降 の DELETE 操 作 は、START SYNCHRONIZATION DELETE ステートメントが実行されるまで同期され ません。 たとえば、Delete Local というメニュー項目を提供し、削除を扱うコー ドを次の例のようにラップできます。 STOP SYNCHRONIZATION DELETE; // 削除操作を実行するコードを呼び出します。 START SYNCHRONIZATION DELETE; COMMIT; 削除については、ほかの方法でも対処できます。詳細については、オ ンラインの『MobiLink - サーバ管理』マニュアルの同期のテクニック についての章を参照してください。 アプリケーション テクニック 239 同期のテクニック 240 PowerBuilder 第 1 4 章 PowerBuilder XML サービスの使 い方 この章について この章では、PowerBuilder の XML サービスの概要について説明し ます。PowerBuilder ドキュメント オブジェクト モデル(PBDOM: PowerBuilder Document Object Model)と、それを PowerBuilder ア プリケーションで使う方法について説明します。 内容 項目 XML と PowerBuilder について PBDOM について PBDOM オブジェクト階層 PBDOM ノード オブジェクト アプリケーションへの pbdom110.pbx の追加 PBDOM の使い方 PBDOM 例外の処理 XML 名前空間 ページ 241 242 243 244 260 261 267 269 XML と PowerBuilder について PowerBuilder には、 Extensible Markup Language (XML) を扱うための 機能がいくつかあります。以下のことを行うことができます。 アプリケーション テクニック • データウィンドウ オブジェクト内のデータを XML にエクス ポートし、XML ドキュメント内のデータ、または文字列を データウィンドウ オブジェクトにインポートする • PowerScript 関数の XMLParseFile と XMLParseString を使用して、 XML ドキュメントや文字列が well-formed(整形式)であるか、 あるいはスキーマや DTD に準拠しているかを判断する • XML ドキュメントの作成および処理を行うアプリケーション とコンポーネントを作成する 241 PBDOM について XML の概要と、データウィンドウのエクスポート機能とインポート機 能の詳細については、PowerBuilder の『ユーザーズ ガイド』マニュア ルの「XML データのエクスポートとインポート」の章を参照してくだ さい。 XML パーサ関数については、オンライン ヘルプの解説を参照してく ださい。 この章では、PowerBuilder ドキュメント オブジェクト モデルを使用し て XML ドキュメントを作成および処理する方法について説明します。 PBDOM について PBDOM は、PowerBuilder に実装しているドキュメント オブジェクト モデル(DOM: Document Object Model)です。DOM は、XML ドキュ メントへのアクセスと操作の方法を定義するプログラミング インタ フェースです。 PBDOM は、World Wide Web コンソーシアム(W3C)DOM API の実装 ではありませんが、それとよく似ています。PBDOM PowerBuilder API を使用して、PowerScript コード内から標準形式 XML の読み書きや操 作を行うことができます。PBDOM は、XML ドキュメントを相互関連 オブジェクトの集合として表現し、また、各オブジェクトの用途と機 能を直観的に示す方法を提供しています。 PBDOM は、XML ファイル用の Java ベースのドキュメント オブジェ クト モデルである JDOM とも似ています。 W3C DOM オブジェクトと JDOM オブジェクト、および階層について は、それぞれの仕様を参照してください。W3C DOM 仕様は W3C のサ イト http://www.w3.org/DOM/ から入手できます。JDOM 仕様およびその仕 様へのリンクは、JDOM のサイト http://www.jdom.org/docs/ に掲載されてい ます。 PBDOM を使用したアプリケーションでは、既存の XML ドキュメント を解析したり、外部要求への応答の中やビジネス ロジックの一部とし て含まれている情報を抽出したりすることができます。アプリケー ションは、ほかのアプリケーション、プロセス、またはシステムが要 求するタイプかスキーマに合致する XML ドキュメントを作成するこ ともできます。XML 文字列を直接編集するかわりに、オブジェクトの PBDOM ツリーを操作したり変換したりすることにより、既存の XML ドキュメントの読み込みと修正が行えます。 242 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 多層アプリケーションで使用する XML ドキュメント、または Web サービスの一部としての XML ドキュメントを作成または処理するコ ンポーネントも作成できます。 ノード ツリー PBDOM は、親ノードと子ノードで構成されるツリービュー モデルに 従って、XML ドキュメントと対話します。ドキュメント要素は、XML ドキュメントのトップ レベルのノードを表します。ドキュメント要素 のそれぞれの子ノードには、ツリーの分岐を表す 1 つ以上の子ノード があります。ツリー内のノードには、PBDOM クラスのメソッドを使っ てアクセスできます。 XML パーサ PBDOM XML パーサを使用して、XML ドキュメントをロードおよび 解析したり、ユーザ指定の DOM ノードに基づいた XML ドキュメント を生成したりします。 PBDOM には、ノード ツリー内での移動、ノードと属性値(存在する 場合)へのアクセス、ノードの挿入と削除を行うためのすべてのメソッ ドが用意されています。また、ノード ツリーをほかのシステムで使用 するために XML ドキュメントを変換する際に必要なメソッドも用意 されています。 PBDOM オブジェクト階層 次の図に、PBDOM オブジェクト階層を示します。 図 14-1: PBDOM オブジェクト階層 アプリケーション テクニック 243 PBDOM ノード オブジェクト PBDOM_OBJECT と その子孫 PBDOM_BUILDER XML ノードを表す PBDOM オブジェクトの基本クラスである PBDOM_OBJECT は、PowerBuilder NonVisualObject クラスから継承し ます。各ノード タイプは、PBDOM クラスにより表されます。このク ラスのメソッドを使用して PBDOM ノード ツリー内のオブジェクトに アクセスします。PBDOM_OBJECT とその子孫については、次の 「PBDOM ノード オブジェクト」で説明します。XML ノード タイプに ついては、PowerBuilder の『ユーザーズ ガイド』マニュアルの「XML データのエクスポートとインポート」の章でも説明しています。 PBDOM_BUILDER クラスも NonVisualObject から継承します。このク ラスは、文字列、ファイル、データストアなど各種の XML 入力元か ら PBDOM_DOCUMENT を作成するファクトリ クラスとして機能し ます。 PBDOM_DOCUMENT を最初から作成する 既存の XML ソースを使用せずに PBDOM_DOCUMENT を作成するに は、PBDOM_DOCUMENT NewDocument メソッドを使用します。 PBDOM_EXCEPTION PBDOM_EXCEPTION クラスは、PowerBuilder Exception クラスから継 承します。このクラスは、PBDOM アプリケーションで例外が発生し たときに定義済み例外コードを返すメソッドを持つ Exception クラス を拡張します。このクラスの詳細については、267 ページの「PBDOM 例外の処理」を参照してください。 PBDOM ノード オブジェクト この節では、PBDOM_OBJECT クラスと、そのクラスを継承するすべ てのクラスについて説明します。 244 • PBDOM_OBJECT • PBDOM_DOCUMENT • PBDOM_DOCTYPE • PBDOM_ELEMENT • PBDOM_ATTRIBUTE • PBDOM_ENTITYREFERENCE • PBDOM_CHARACTERDATA PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 • PBDOM_TEXT • PBDOM_CDATA • PBDOM_COMMENT • PBDOM_PROCESSINGINSTRUCTION PBDOM クラスのメソッド詳細については、『PowerBuilder エクステン ション リファレンス』マニュアルを参照してください。 PBDOM_OBJECT PBDOM_OBJECT クラスは、XML ノード ツリー内のノードを表し、特 定のノード タイプを表す専用 PBDOM クラスの基本クラスとして機能 します。PBDOM_OBJECT に対応する DOM クラスはノード オブジェ クトです。PBDOM_OBJECT には、派生クラスに必要な基本機能がす べて含まれます。ノードは、要素ノード、ドキュメント ノード、また は、上記の PBDOM_OBJECT から派生した任意のノード タイプです。 メソッド PBDOM_OBJECT 基本クラスには以下のメソッドがあります。 • AddContent、GetContent、InsertContent、RemoveContent、および SetContent では、PBDOM_OBJECT の子を操作できる • Clone では、PBDOM_OBJECT の簡易クローンか詳細クローンを作 成できる • Detach では、PBDOM_OBJECT をその親からデタッチする • Equals では、別の PBDOM_OBJECT と同等であることをテストする • GetName と SetName では、PBDOM_OBJECT の名前の取得と設定 を行う • GetObjectClass と GetObjectClassString では、PBDOM_OBJECT のク ラスを識別する • GetOwnerDocumentObject では、 現行の PBDOM_OBJECT のオーナー PBDOM_DOCUMENT を識別する • GetParentObject と SetParentObject では、PBDOM_OBJECT の親の取 得と設定を行う • GetText、GetTextNormalize、および GetTextTrim では、 PBDOM_OBJECT のテキスト データを取得する • アプリケーション テクニック HasChildren では、PBDOM_OBJECT に子があるかどうかを判断する 245 PBDOM ノード オブジェクト • IsAncestorObjectOf では、PBDOM_OBJECT が別の PBDOM_OBJECT の先祖かどうかを判断する PBDOM_OBJECT 継 承 PBDOM_OBJECT クラスは、直接インスタンス化および使用すること が前提とされない点で、C++ の仮想クラスに似ています。たとえば、 PowerScript の CREATE 文を使用して PBDOM_OBJECT を作成できます が、そのメソッドを直接使うことはできません。 PBDOM_OBJECT pbdom_obj pbdom_obj = CREATE PBDOM_OBJECT pbdom_obj.SetName("VIRTUAL_PBDOM_OBJ") // 例外 ! 上のコードの 3 行目は、基本クラス PBDOM_OBJECT の SetName メ ソッドに直接アクセスしようとするので、例外を送出します。ただし、 SetName メソッドが PBDOM_ELEMENT などの派生クラスからアクセ スされる場合には、このような実装の仕方もありえます。 PBDOM_OBJECT pbdom_obj pbdom_obj = CREATE PBDOM_ELEMENT pbdom_obj.SetName ("VIRTUAL_PBDOM_OBJ") プレースホルダとして の基本クラス PBDOM_OBJECT の 使い方 PBDOM_OBJECT クラスを、派生クラスのオブジェクトのプレースホ ルダとして使用できます。 PBDOM_DOCUMENT pbdom_doc PBDOM_OBJECT pbdom_obj pbdom_doc = CREATE PBDOM_DOCUMENT pbdom_doc.NewDocument ("", "", & "Root_Element_From_Doc_1", "", "") pbdom_obj = pbdom_doc.GetRootElement pbdom_obj.SetName & ("Root_Element_From_Doc_1_Now_Changed") インスタンス化された PBDOM_OBJECT pbdom_obj は、 PBDOM_DOCUMENT オブジェクトに割り当てられます。このオブ ジェクトには、GetRootElement メソッドの戻り値が格納されます。ここ で、pbdom_obj は、PBDOM_ELEMENT への参照を保持し、また、 PBDOM_OBJECT から派生したクラスの任意のオブジェクトに対して 有効に動作します。 スタンドアロン オブ ジェクト PBDOM_OBJECT は、すべてのドキュメントや親の PBDOM_OBJECT から独立した自己完結型のオブジェクトを作成できます。このような PBDOM_OBJECT をスタンドアロン オブジェクトと呼びます。たとえ ば、次のようになります。 PBDOM_ELEMENT pbdom_elem_1 pbdom_elem_1 = Create PBDOM_ELEMENT 246 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 pbdom_elem_1.SetName("pbdom_elem_1") pbdom_elem_1 は、Create キーワードを使用して派生クラス PBDOM_ELEMENT 内でインスタンス化されます。次に、どのドキュ メント内にも含まれないスタンドアロン オブジェクトである pbdom_elem_1 オブジェクトから、SetName メソッドを呼び出すことが できます。 スタンドアロン オブジェクトは有効な PBDOM 操作を実行できます が、スタンドアロンであることによってそのオブジェクトに特別なメ リットまたはデメリットがあるわけではありません。 親がオーナーのオブ ジェクトおよびドキュ メントがオーナーのオ ブジェクト 次の例のように、PBDOM_OBJECT を別のスタンドアロン PBDOM_OBJECT に追加することにより、PBDOM_OBJECT に親クラ スを割り当てることができます。 PBDOM_ELEMENT pbdom_elem_1 PBDOM_ELEMENT pbdom_elem_2 pbdom_elem_1 = Create PBDOM_ELEMENT pbdom_elem_2 = Create PBDOM_ELEMENT pbdom_elem_1.SetName("pbdom_elem_1") pbdom_elem_2.SetName("pbdom_elem_2") pbdom_elem_1.AddContent(pbdom_elem_2) 2 つの PBDOM_ELEMENT オブジェクト pbdom_elem_1 と pbdom_elem_2 がインスタンス化されます。pbdom_elem_2 オブジェク トは、AddContent メソッドを使用して、pbdom_elem_1 の子オブジェク トとして追加されます。 この例では、pbdom_elem_1 と pbdom_elem_2 のいずれも、オーナーは ドキュメントではありません。また、pbdom_elem_1 オブジェクトはス タンドアロンのままです。pbdom_elem_1 に、ドキュメントをオーナー とする親の PBDOM_OBJECT が割り当てられた場合、pbdom_elem_1 は スタンドアロン オブジェクトではなくなります。 PBDOM_DOCUMENT PBDOM_DOCUMENT クラスは、PBDOM_OBJECT から派生し、XML DOM ドキュメントを表します。PBDOM_DOCUMENT メソッドでは、 ルート要素、処理命令などのドキュメントレベル情報にアクセスでき ます。 アプリケーション テクニック 247 PBDOM ノード オブジェクト メソッド PBDOM_OBJECT から継承するメソッドに加え、PBDOM_DOCUMENT クラスには以下のメソッドがあります。 • DetachRootElement、GetRootElement、HasRootElement、および SetRootElement では、PBDOM_DOCUMENT のルート要素を操作 する • GetDocType と SetDocType では、 XML ドキュメントの DOCTYPE 宣 言を取得および設定する • NewDocument では、新規の PBDOM_DOCUMENT を最初から作成 する • SaveDocument では、PBDOM_DOCUMENT 内の DOM ツリーの内 容をファイルに保存する PBDOM_DOCTYPE PBDOM_DOCTYPE クラスは、XML DOM ドキュメントのドキュメン ト型宣言オブジェクトを表します。PBDOM_DOCTYPE メソッドを使 用して、ルート要素名、内部サブセット、および、システム ID とパブ リック ID にアクセスできます。 メソッド PBDOM_OBJECT から継承するメソッドに加え、PBDOM_DOCTYPE クラスには以下のメソッドがあります。 • GetPublicID、SetPublicID、GetSystemID、および SetSystemID では、 PBDOM_DOCTYPE 内で宣言される外部参照 ID のパブリック ID とシステム ID を取得および設定する • GetInternalSubset と SetInternalSubset では、PBDOM_DOCTYPE の内 部サブセット データを取得および設定する PBDOM_ELEMENT PBDOM_ELEMENT は、PowerScript 内でモデル化された XML 要素を 表します。PBDOM_ELEMENT メソッドを使用して、要素属性、子、 およびテキストにアクセスできます。 メソッド 248 PBDOM_OBJECT から継承するメソッドに加え、PBDOM_ELEMENT クラスには以下のメソッドがあります。 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 AddNamespaceDeclaration と RemoveNamespaceDeclaration では、 • PBDOM_ELEMENT に名前空間宣言を追加したり、 PBDOM_ELEMENT から名前空間宣言を削除したりする GetAttribute、GetAttributes、GetAttributeValue、HasAttributes、 RemoveAttribute、SetAttribute、および SetAttributes では、 • PBDOM_ELEMENT の属性を操作する GetChildElement、GetChildElements、HasChildElements、 RemoveChildElement、および RemoveChildElements では、 • PBDOM_ELEMENT の子を操作する GetNamespacePrefix と GetNamespaceURI では、PBDOM_ELEMENT • に関連付けられた名前空間の接頭辞と URI を取得する GetQualifiedName では、接頭辞(ある場合)を含めた • PBDOM_ELEMENT の完全名を取得する PBDOM_ELEMENT と PBDOM_ATTRIBUTE の関係 • SetDocument では、PBDOM_DOCUMENT を PBDOM_ELEMENT の 親として設定する • SetNamespace では、PBDOM_ELEMENT の名前空間を設定する • SetText では、PBDOM_ELEMENT のテキスト内容を設定する PBDOM では、XML 要素の属性はその要素の子ではありません。XML 要素の属性は、関連付けられた要素とは別に識別されるのではなく、 要素のプロパティです。 次の単純な XML ドキュメントについて考えてみます。 <root attr="value1"> <child attr_1="value1" attr_2="value2"/> </root> これに相当する PBDOM ツリーを図 14-2 に示します。 図 14-2: PBDOM_ELEMENT と PBDOM_ATTRIBUTE の関係 ルート と 子 を結ぶ実線は、親子関係を表します。点線は、属性とその オーナー要素との間の「~のプロパティ」という関係を表します。 アプリケーション テクニック 249 PBDOM ノード オブジェクト PBDOM_ELEMENT の内容を管理するメソッドは、PBDOM_ATTRIBUTE オブジェクトには使用できません。属性を取得、設定、および削除す るメソッドは別にあります。 属性は、オーナー要素の子ではないので PBDOM ドキュメント ツリー 全体の一部とはみなされませんが、オーナー要素を通してツリーにリ ンクされます。 属性には子オブジェクト(XML テキストとエンティティ参照ノード) を格納できるので、属性はそれ自体のサブツリーを形成します。 要素の属性はその要素の子とはみなされないので、子オブジェクト間 にあるような兄弟関係が属性間にはありません。サンプルの XML ド キュメント、および図 14-2 では、attr_1 と attr_2 は兄弟ではありませ ん。オーナー要素内での属性の表示順序には、特に意味はありません。 属性の設定と作成 PBDOM では、XML 要素の属性は、PBDOM_ELEMENT SetAttribute メ ソッドと SetAttributes メソッドを使用して設定されます。これらのメ ソッドは常に、PBDOM_ELEMENT の新規属性を作成しようとし、既 存の属性を同じ名前および同じ名前空間の URI に置き換えようとしま す。 PBDOM_ELEMENT に、同じ名前と同じ名前空間 URI の既存の属性が すでに含まれている場合、これらのメソッドは、既存の属性を削除し てから新規属性を PBDOM_ELEMENT に挿入します。SetAttribute メ ソッドを呼び出すと、PBDOM_ATTRIBUTE(PBDOM_ELEMENT の既 存属性を表す)がそのオーナー PBDOM_ELEMENT からデタッチされ ます。 たとえば、次の要素について考えてみます。 <an_element an_attr="some_value"/> PBDOM_ELEMENT オブジェクト pbdom_an_elem が an_element 要素を 表し、次の文が発行された場合、このメソッドはまず、an_element 要 素の新規属性を作成しようとします。 pbdom_an_elem.SetAttribute("an_attr", "some_other_value") 次に、an_element にはすでに an_attr という名前の属性が含まれている ので、その属性は削除されます。元の an_attr 属性を表す既存の PBDOM_ATTRIBUTE オブジェクトがある場合、この PBDOM_ATTRIBUTE はそのオーナー要素(an_element)からデタッ チされます。 属性と名前空間の詳細については、269 ページの「XML 名前空間」を 参照してください。 250 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 PBDOM_ATTRIBUTE PBDOM_ATTRIBUTE クラスは、PowerScript 内でモデル化された XML 属性を表します。PBDOM_ATTRIBUTE メソッドを使用して、要素属 性および名前空間情報にアクセスできます。 メソッド PBDOM_OBJECT から継承するメソッドに加え、PBDOM_ATTRIB ク ラスには以下のメソッドがあります。 • GetBooleanValue 、SetBooleanValue 、GetDateValue 、SetDateValue 、 GetDateTimeValue、SetDateTimeValue、GetDoubleValue、SetDoubleValue、 GetIntValue、SetIntValue、GetLongValue、SetLongValue、GetRealValue、 SetRealValue、GetTimeValue、SetTimeValue、GetUIntValue、SetUintValue、 GetULongValue および SetULongValue では、PBDOM_ATTRIBUTE の 値を指定されたデータ型として取得および設定する • GetNamespacePrefix と GetNamespaceURI では、 PBDOM_ATTRIBUTE に関連付けられた名前空間の接頭辞と URI を取得する • GetOwnerElementObject と SetOwnerElementObject では、 PBDOM_ATTRIBUTE のオーナー PBDOM_ELEMENT を取得およ び設定する • GetQualifiedName では、接頭辞(ある場合)を含めた PBDOM_ATTRIBUTE の完全名を取得する 子オブジェクト PBDOM_OBJECT • SetNamespace では、PBDOM_ATTRIBUTE の名前空間を設定する • SetText では、PBDOM_ATTRIBUTE のテキスト内容を設定する PBDOM_ATTRIBUTE には、子オブジェクト PBDOM_OBJECT のサブ ツリーが含まれています。子オブジェクトは、PBDOM_TEXT オブジェ クトと PBDOM_ENTITYREFERENCE オブジェクトを組み合わせるこ ともできます。 次の例では、attr という名前の PBDOM_ATTRIBUTE が含まれている elem という名前の PBDOM_ELEMENT を作成します。 PBDOM_ATTRIBUTE pbdom_attr PBDOM_TEXT pbdom_txt PBDOM_ENTITYREFERENCE pbdom_er PBDOM_ELEMENT pbdom_elem pbdom_elem = Create PBDOM_ELEMENT pbdom_elem.SetName ("elem") pbdom_attr = Create PBDOM_ATTRIBUTE pbdom_attr.SetName("attr") アプリケーション テクニック 251 PBDOM ノード オブジェクト pbdom_attr.SetText("Part 1 ") pbdom_txt = Create PBDOM_TEXT pbdom_txt.SetText (" End.") pbdom_er = Create PBDOM_ENTITYREFERENCE pbdom_er.SetName("ER") pbdom_attr.AddContent(pbdom_er) pbdom_attr.AddContent(pbdom_txt) pbdom_elem.SetAttribute(pbdom_attr) XML 内の要素タグは次のようになります。 <elem attr="Part 1 &ER; End."> 図 14-3 で、矢印は PBDOM_ATTRIBUTE とほかの PBDOM_OBJECT と の親子関係を示します。 図 14-3: PBDOM_ATTRIBUTE サブツリーの例 PBDOM_TEXT のデ フォルトの子オブジェ クト PBDOM_ATTRIBUTE には一般に、PBDOM_TEXT の子オブジェクトが 少なくとも 1 つ含まれています。その子オブジェクトの内容が空の文 字列の場合もあります。ただし、RemoveContent メソッドの呼び出しに より PBDOM_ATTRIBUTE の内容がすべて削除された場合を除きま す。 以下の例は、空の文字列を持つ PBDOM_TEXT オブジェクトがどのよ うにして PBDOM_ATTRIBUTE の子オブジェクトになるかを示しま す。 例 1 次の例では、PBDOM_ELEMENT の SetAttribute メソッドを使用し ます。PBDOM_ATTRIBUTE の名前は attr に設定されていますが、テキ スト値は空の文字列です。PBDOM_ATTRIBUTE には、空の文字列を 持つ子オブジェクト PBDOM_TEXT が 1 つあります。 PBDOM_DOCUMENT pbdom_doc PBDOM_ATTRIBUTE pbdom_attr 252 PowerBuilder 第 14 章 PBDOM_OBJECT PowerBuilder XML サービスの使い方 pbdom_obj_array[] try pbdom_doc = Create PBDOM_DOCUMENT pbdom_doc.NewDocument("root") // 属性の名前は // "attr" に設定され、そのテキスト値は空の文字列 "" です。 pbdom_doc.GetRootElement().SetAttribute("attr", "") pbdom_attr = & pbdom_doc.GetRootElement().GetAttribute("attr") MessageBox ("HasChildren", & string(pbdom_attr.HasChildren())) catch(PBDOM_EXCEPTION pbdom_except) MessageBox ("PBDOM_EXCEPTION", & pbdom_except.GetMessage()) end try SaveDocument メソッドを使用して pbdom_doc を XML として変更すると きは、次のようになります。 <root attr="" /> 次の例では、PBDOM_ATTRIBUTE を作成し、その名前を attr に 設定します。テキスト値は設定されませんが、PBDOM_TEXT オブジェ クトが自動作成され、PBDOM_ATTRIBUTE にアタッチされます。こ れは、この方法で作成されたすべての PBDOM_ATTRIBUTE のデフォ ルトの振る舞いです。 例2 PBDOM_DOCUMENT pbdom_doc PBDOM_ATTRIBUTE pbdom_attr try pbdom_doc = Create PBDOM_DOCUMENT pbdom_doc.NewDocument("root") // PBDOM_ATTRIBUTE を作成し、名前を "attr" に設定します。 pbdom_attr = Create PBDOM_ATTRIBUTE pbdom_attr.SetName("attr") pbdom_doc.GetRootElement().SetAttribute(pbdom_attr) MessageBox ("HasChildren", & string(pbdom_attr.HasChildren())) アプリケーション テクニック 253 PBDOM ノード オブジェクト catch(PBDOM_EXCEPTION pbdom_except) MessageBox ("PBDOM_EXCEPTION", & pbdom_except.GetMessage()) end try SetText メソッド(または、SetNamespace を除くほかの Set* メソッドの いずれか。)を呼び出すとき、デフォルトの PBDOM_TEXT が新規の PBDOM_TEXT に置き換わります。SetContent メソッドを呼び出すと、 デ フ ォ ル ト の PBDOM_TEXT を、PBDOM_TEXT オ ブ ジ ェ ク ト と PBDOM_ENTITYREFERENCE オブジェクトの組み合わせに置き換え ることができます。 PBDOM_ENTITYREFERENCE PBDOM_ENTITYREFERENCE クラスは、XML エンティティ参照ノー ドの振る舞いを定義します。これは、主にエンティティ参照を、属性 ノードと同様に要素ノード内にも挿入するための単純なクラスです。 PBDOM_BUILDER クラスが XML ドキュメントを解析して DOM ツ リーを構築するとき、このクラスは、DTD 内で出現するときにエン ティティを完全に拡張します。したがって、PBDOM_BUILDER 構築メ ソッドのいずれかを使用して PBDOM_DOCUMENT オブジェクトが作 成された直後は、作成されたドキュメント ツリーにエンティティ参照 ノードはありません。 PBDOM_ENTITYREFERENCE オブジェクトは、いつでも作成でき、ど のドキュメントにも挿入できます。参照されるエンティティを表す、 対応する DOM エンティティ ノードがそのドキュメント内にあるかど うかには左右されません。 メソッド PBDOM_ENTITYREFERENCE クラスには、PBDOM_OBJECT から継承 されたメソッドしかありません。 PBDOM_CHARACTERDATA PBDOM_CHARACTERDATA クラスは PBDOM_OBJECT から派生し、 XML ドキュメント内の文字ベースの内容(マークアップではない)を 表します。PBDOM_CHARACTERDATA クラスは、PBDOM_OBJECT を拡張し、文字データの操作専用のメソッドを持ちます。 メソッド 254 PBDOM_OBJECT から継承するメソッドに加え、 PBDOM_CHARACTERDATA クラスには以下のメソッドがあります。 PowerBuilder 第 14 章 3 つのクラスの親クラ ス PowerBuilder XML サービスの使い方 • Append では、PBDOM_CHARACTERDATA オブジェクトのテキス ト文字列またはテキスト データを現行オブジェクト内のテキスト に追加する • SetText では、PBDOM_CHARACTERDATA オブジェクトのテキス ト内容を設定する PBDOM_CHARACTERDATA クラスは、以下の 3 つの PBDOM クラス の親クラスです。 • PBDOM_TEXT • PBDOM_CDATA • PBDOM_COMMENT PBDOM_CHARACTERDATA クラスは、その親クラス PBDOM_OBJECT と同様に、直接インスタンス化および使用すること が前提とされない点で、「仮想」クラスといえます。これは、C++ の 仮想クラスに似ています。たとえば、CREATE 文で PBDOM_CHARACTERDATA を作成することは PowerScript では有効 ですが、PBDOM_CHARACTERDATA を SetText メソッドを呼び出して 直接操作することは無効です。次のコードの最後の行は例外を発生し ます。 PBDOM_CHARACTERDATA pbdom_chrdata pbdom_chrdata = CREATE PBDOM_CHARACTERDATA pbdom_chrdata.SetText("character string") // 例外 ! この例では、pbdom_chrdata は、PBDOM_CHARACTERDATA として宣 言されますが PBDOM_TEXT としてインスタンス化されます。 pbdom_chrdata で SetText を呼び出すことは、PBDOM_TEXT SetText メ ソッドを呼び出すことに相当します。 PBDOM_CHARACTERDATA pbdom_chrdata pbdom_chrdata = CREATE PBDOM_TEXT pbdom_chrdata.SetText("character string") PBDOM_TEXT PBDOM_TEXT ク ラ ス は PBDOM_CHARACTERDATA か ら 派 生 し、 XML ドキュメント内の DOM テキスト ノードを表します。 アプリケーション テクニック 255 PBDOM ノード オブジェクト メソッド PBDOM_TEXT クラスには、PBDOM_OBJECT か PBDOM_CHARACTERDATA から継承されていないメソッドはありま せん。 PBDOM_TEXT オブ ジェクトの使い方 PBDOM_TEXT オブジェクトは、PBDOM_ELEMENT か PBDOM_ATTRIBUTE のテキスト内容を表すために広く使用されま す。PBDOM_TEXT オブジェクトは、カギカッコで区切られていませ んがオブジェクトであり、親クラス PBDOM_ELEMENT の値の一部で はありません。 PBDOM ツリー内でグラフィカルに表現された PBDOM_TEXT オブ ジェクトは、リーフ ノードであり、子オブジェクトを持ちません。た とえば、図 14-4 は次の PBDOM_ELEMENT を表します。 <parent_element>some text</parent_element> 図 14-4: PBDOM_TEXT 親子関係 矢印は親子関係を表します。 PBDOM_TEXT の出 現 XML ドキュメントの初回の解析時、要素の内容中にマークアップがな い場合は、要素内のテキストは単一の PBDOM_TEXT オブジェクトと して表されます。この PBDOM_TEXT オブジェクトは、その要素の唯 一の子です。マークアップがある場合、PBDOM_ELEMENT オブジェ クトと PBDOM_TEXT オブジェクトのリストに解析されます。このリ ストは、要素の子のリストになります。 たとえば、次の XML を解析すると、<element_1> を表す 1 つの PBDOM_ELEMENT と、テキスト内容 Some Text を表す 1 つの PBDOM_TEXT が作成されます。 <root> <element_1>Some Text</element_1> </root> <element_1> PBDOM_ELEMENT には、唯一の子としての PBDOM_TEXT オブジェクトがあります。 256 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 次のドキュメントについて考えてみます。 <root> <element_1> Some Text <element_1_1>Sub Element Text</element_1_1> More Text <element_1_2/> Yet More Text </element_1> </root> 次の XML を解析すると、<element_1> を表す PBDOM_ELEMENT と、そ の子が 5 つ作成されます。 隣接する PBDOM_TEXT オブ ジェクト • Some Text を表す PBDOM_TEXT • <element_1_1/> を表す PBDOM_ELEMENT • More Text を表す PBDOM_TEXT • <element_1_2/> を表す PBDOM_ELEMENT • Yet More Text を表す PBDOM_TEXT 指定された要素の内容をマークアップの介入なしで表している隣接す る PBDOM_TEXT オブジェクトを作成できます。たとえば、次のドキュ メントから始めます。 <root> <element_1>Some Text</element_1> </root> element_1 の PBDOM_ELEMENT で AddContent("More Text") を呼び 出すと、次のような結果になります。 <root> <element_1>Some TextMore Text</element_1> </root> 「Some Text」と「More Text」を表す、相互に隣接した 2 つの PBDOM_TEXT オブジェクトが作成されています。それらの間には何 もなく、またそれらの分離を表す方法もありません。 PBDOM_TEXT オブ ジェクトの永続格納 隣接する PBDOM_TEXT オブジェクトが離れると、DOM を編集する セッションは続きません。前の例で示した「More Text」の追加により 作成されたドキュメントが再オープンおよび再解析されると、1 つの PBDOM_TEXT オブジェクトだけが「Some TextMore Text」を表します。 アプリケーション テクニック 257 PBDOM ノード オブジェクト PBDOM_CDATA PBDOM_CDATA クラスは、PBDOM_TEXT から派生し、XML DOM CDATA セクションを表します。 メソッド PBDOM_CDATA クラスには、PBDOM_OBJECT か PBDOM_CHARACTERDATA から継承されていないメソッドはありま せん。 CDATA オブジェクト の使い方 PBDOM_CDATA オブジェクトは、拡張された PBDOM_TEXT オブジェ クトとして考えることができます。PBDOM_CDATA オブジェクトを使 用して、<、& など、XML で禁止されている文字を含むことのできる テキストを格納できます。このオブジェクトの主な目的は、エンティ ティ参照なしで、そのような特殊文字を大きなテキスト ブロック内に 含めることです。 次の例には PBDOM_CDATA オブジェクトが含まれています。 <some_text> <![CDATA[ (x < y) & (y < z) => x < z ]]> </some_text> 同じテキスト内容を PBDOM_TEXT オブジェクトとして表現するに は、次のように記述します。 <some_text> (x < y) & (y < z) => x < z </some_text> PBDOM_CDATA クラスは PBDOM_TEXT から派生しますが、 PBDOM_TEXT を挿入できる個所に PBDOM_CDATA オブジェクトを 必ず挿入できるわけではありません。たとえば、PBDOM_TEXT オブ ジェクトを PBDOM_ATTRIBUTE の子オブジェクトとして追加できま すが、PBDOM_CDATA オブジェクトは追加できません。 PBDOM_COMMENT PBDOM_COMMENT クラスは、XML ドキュメント内の DOM コメン ト ノードです。PBDOM_COMMENT クラスは PBDOM_CHARACTERDATA クラスから派生します。 メソッド 258 PBDOM_COMMENT クラスには、PBDOM_OBJECT か PBDOM_CHARACTERDATA から継承されていないメソッドはありま せん。 PowerBuilder 第 14 章 コメントの使い方 PowerBuilder XML サービスの使い方 コメントは、ユーザが読める表現で XML ドキュメントに注釈を付け るのに便利です。 ドキュメントの解析時、ドキュメント内のすべてのコメントは、DOM ツリーの一部としてメモリ内に永続します。実行時に作成された PBDOM_COMMENT も DOM ツリーの一部になります。 XML コメントは、通常、ドキュメントの内容モデルの一部ではありま せん。コメントの有無はドキュメントの有効性に影響しません。また、 DTD 内でコメントを宣言する必要もありません。 PBDOM_PROCESSINGINSTRUCTION PBDOM_PROCESSINGINSTRUCTION クラスは、XML 処理命令(PI) を表します。PBDOM_PROCESSINGINSTRUCTION メソッドを使用し て、処理命令先とそのデータにアクセスできます。そのデータには、 文字列として、または、必要に応じて名前と値のペアとしてアクセス できます。 PI の実際の処理命令は文字列です。これは、命令が個別の name="value" のペアに分割される場合も同じです。PBDOM はこのよ うな PI 書式をサポートします。一般に、PI データはこれらのペアを 含みます。その場合、PBDOM_PROCESSINGINSTRUCTION はこれら のペアを名前と値の内部リストに解析します。 メソッド PBDOM_OBJECT から継承するメソッドに加え、 PBDOM_PROCESSINGINSTRUCTION クラスには以下のメソッドがあ ります。 • GetData と SetData では、PBDOM_PROCESSINGINSTRUCTION オ ブジェクトの生データを取得および設定する • GetNames では、PBDOM_PROCESSINGINSTRUCTION のデータの 一部(name="value" のペアに分割されている)から取った、名前 のリストを取得する • GetValue、RemoveValue、および SetValue では、 PBDOM_PROCESSINGINSTRUCTION オブジェクト内で、指定さ れた名前と値のペアの値を取得、削除、および設定する • アプリケーション テクニック GetTarget では、PBDOM_PROCESSINGINSTRUCTION のターゲッ トを取得する。たとえば、XML 宣言のターゲット(特殊な処理命 令)は文字列 xml になる 259 アプリケーションへの pbdom110.pbx の追加 アプリケーションへの pbdom110.pbx の追加 PBDOM クラスは、接尾辞 PBX(PowerBuilder エクステンション用)を 持つ DLL ファイルに実装されます。PBDOM クラスを PowerBuilder ターゲットに追加する最も簡単な方法は、PowerBuilder システム ツ リー内のライブラリに pbdom110.pbx PBX ファイル内のオブジェクト ディスクリプションをインポートすることです。pbdom110.pbd ファイ ル(クラスのラッパーとして動作)をターゲットのライブラリ探索パ スに追加することもできます。 pbdom110.pbx ファイルと pbdom110.pbd ファイルは、PowerBuilder のイ ンストール時に Shared\PowerBuilder ディレクトリに配置されます。 PBDOM アプリケーションの作成時に pbdom110.pbx を別の場所にコ ピーする必要はありませんが、アプリケーションの探索パス中のディ レクトリに、このファイルをアプリケーションとともに配布する必要 があります。 ❖ エクステンション内のディスクリプションをライブラリにインポートするに は 1 2 システム ツリーで、エクステンションを使用したいターゲットを 展開し、ライブラリを右クリックし、ポップアップ メニューから [ PB エクステンションのインポート]を選択します。 PBX ファイルの位置に移動し、[開く]をクリックします。 PBX 内の各クラスがシステム ツリーに表示されます。そのためク ラスを展開し、そのプロパティ、イベント、およびメソッドを表 示して、それらをスクリプトに追加するためにドラッグアンドド ロップできます。 260 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 pbdom110.pbx をインポートした後に、PBDOM オブジェクトがシステ ム ツリーに表示されます。 PBDOM の使い方 この節では、PBDOM のクラスおよびメソッドを使用して基本的なタ スクを遂行する方法について説明します。ダウンロードしてテストで きる完全なコード サンプルを見るには、Windows の[スタート|プロ グラム| Sybase | PowerBuilder 11.0 | PB 11.0 コード サンプル]を選 択します。 XML の検証 ファイルか文字列からドキュメントを作成する前に、XMLParseFile PowerScript 関数または XMLParseString PowerScript 関数を使用して、そ の XML が well formed(整形式)であるかどうか、あるいはオプショ ンで、DTD かスキーマに準拠しているかどうかをテストできます。た とえば、次のコードは、ファイル内の XML が well formed(整形式)で あるかどうかをテストします。 long ll_ret ll_ret = XMLParseFile("c:\temp\mydoc.xml", ValNever!) アプリケーション テクニック 261 PBDOM の使い方 デフォルトでは、これらの関数により、エラーが発生した場合にメッ セージ ボックスが表示されます。parsingerrors 文字列引数を指定して、 プログラムによりエラーを処理することもできます。これらの関数の 詳細については、 『PowerScript リファレンス』マニュアルかオンライ ン ヘルプの解説を参照してください。 XML から XML ドキュメントの作成 PBDOM_BUILDER クラスは、既存の XML ソースから PBDOM_DOCUMENT を作成するための 3 つのメソッドを提供しま す。また、発生したすべての解析エラーのリストを取得する GetParseErrors メソッドも提供します。 BuildFromString の使 い方 次 の 例 で は、XML 文 字 列 と PBDOM_BUILDER ク ラ ス を 使 用 し て PBDOM_DOCUMENT を作成します。まず、オブジェクトを宣言します。 PBDOM_BUILDER pbdom_builder_new PBDOM_DOCUMENT pbdom_doc 次に、コンストラクタと PBDOM_BUILDER の BuildFromString メソッド を使用してオブジェクトをインスタンス化します。 pbdombuilder_new = Create PBDOM_Builder pbdom_doc = pbdombuilder_new.BuildFromString(Xml_doc) XML は、次の例のように、文字列変数に直接ロードすることもできま す。 string Xml_str Xml_str = "<?xml version="1.0" ?>" Xml_str += "<WHITEPAPER>" Xml_str += "<TITLE>Document Title</TITLE>" Xml_str += "<AUTHOR>Author Name</AUTHOR>" Xml_str += "<PARAGRAPH>Document text.</PARAGRAPH>" Xml_str += "</WHITEPAPER>" BuildFromFile の使い 方 BuildFromFile メソッドと、PBDOM_DOCUMENT の作成元となるファイ ルへのパスを含む文字列を使用して、XML ファイルを作成できます。 PBDOM_BUILDER pbdombuilder_new PBDOM_DOCUMENT pbdom_doc pbdombuilder_new = Create PBDOM_Builder pbdom_doc = pbdombuilder_new.BuildFromFile & ("c:\pbdom_doc_1.xml") 262 PowerBuilder 第 14 章 BuildFromDataStore の使い方 PowerBuilder XML サービスの使い方 次に示す PowerScript コードの一部は、BuildFromDataStore メソッドを、 参照されるデータストア オブジェクトとともに使用する方法を示し ます。 PBDOM_Builder pbdom_bldr pbdom_document pbdom_doc datastore ds ds = Create datastore ds.DataObject = "d_customer" ds.SetTransObject (SQLCA) ds.Retrieve pbdom_doc = pbdom_bldr.BuildFromDataStore(ds) GetParseErrors の使 い方 Build メソッドのいずれかを呼び出した後、GetParseErrors メソッドを 使用して、Build メソッドで発生した解析エラーと検証エラーのリスト を取得できます。 PBDOM_Builder pbdom_bldr pbdom_document pbdom_doc string strParseErrors[] BOOLEAN bRetTemp = FALSE pbdom_buildr = Create PBDOM_BUILDER pbdom_doc = pbdom_buildr.BuildFromFile("D:\temp.xml") bRetTemp = pbdom_buildr.GetParseErrors(strParseErrors) if bRetTemp = true then for l = 1 to UpperBound(strParseErrors) MessageBox (" 解析エラー ", strParseErrors[l]) next end if 解析エラー 解析エラーが検出され、GetParseErrors が true を返した場合、調べるこ とができる完全な PBDOM ノード ツリーが作成されている場合があり ます。 アプリケーション テクニック 263 PBDOM の使い方 最初からの XML ドキュメントの作成 適切な PBDOM_OBJECT サブクラスとメソッドを使用して、スクリプ ト内に XML ドキュメントを作成できます。次のコードでは、 PBDOM_ELEMENT クラスと PBDOM_DOCUMENT クラス、およびそ れらのメソッドの一部を使用して、単純な XML ドキュメントを作成 します。 まず、オブジェクトを宣言し、インスタンス化します。 PBDOM_ELEMENT pbdom_elem_1 PBDOM_ELEMENT pbdom_elem_2 PBDOM_ELEMENT pbdom_elem_3 PBDOM_ELEMENT pbdom_elem_root PBDOM_DOCUMENT pbdom_doc1 pbdom_elem_1 = Create PBDOM_ELEMENT pbdom_elem_2 = Create PBDOM_ELEMENT pbdom_elem_3 = Create PBDOM_ELEMENT インスタンス化されたオブジェクトに命名します。 PBDOM_DOCUMENT オブジェクトの pbdom_doc1 には命名しないこ とに注意してください。 pbdom_elem_1.SetName("pbdom_elem_1") pbdom_elem_2.SetName("pbdom_elem_2") pbdom_elem_3.SetName("pbdom_elem_3") AddContent メソッドを使用して、オブジェクトをノード ツリーに配置 します。AddContent メソッドは、参照されるオブジェクトを、AddContent の呼び出し元オブジェクトの子ノードとして追加します。 pbdom_elem_1.AddContent(pbdom_elem_2) pbdom_elem_2.AddContent(pbdom_elem_3) NewDocument メソッドを使用して新規の XML ドキュメントを作成し ます。NewDocument メソッドに指定したパラメータ値が、ルート要素 の名前になります。次に、GetRootElement メソッドを使用して、 PBDOM_DOCUMENT オブジェクト pbdom_doc1 からこの名前にアク セスし、それを PBDOM_ELEMENT オブジェクト pbdom_elem_root に 割り当てます。 pbdom_doc1.NewDocument("Root_Element_From_Doc_1") pbdom_elem_root = pbdom_doc1.GetRootElement() 264 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 要素オブジェクト pbdom_elem_1 およびそのオブジェクトのすべての 子ノードを、AddContent メソッドを使用してルート要素下の新規の XML ドキュメント ノード ツリーに配置します。 子孫ノード pbdom_elem_1 をノード ツリーに配置すると、そのすべての子ノードが移動されるこ とに注目してください。 pbdom_elem_root.AddContent(pbdom_elem_1) 作成された XML ドキュメントは次のようになります。 <!DOCTYPE Root_Element_From_Doc_1> <Root_Element_From_Doc_1> <pbdom_elem_1> <pbdom_elem_2> <pbdom_elem_3/> </pbdom_elem_2> </pbdom_elem_1> </Root_Element_From_Doc_1> ノード データへのアクセス XML ドキュメントは、適切な PBDOM_OBJECT サブクラスとメソッ ドを使用してノード ツリーの要素にアクセスすることによって、読み 込むことができます。次のコードでは、配列、PBDOM_OBJECT とそ の子孫クラス PBDOM_DOCUMENT、および、PBDOM_DOCUMENT クラスの GetContent メソッドと GetRootElement メソッドを使用して、 XML ドキュメントのノード データにアクセスします。 pbdom_doc という名前の PBDOM_DOCUMENT オブジェクトには、次 の XML ドキュメントが含まれます。 <Root> <Element_1> <Element_1_1/> <Element_1_2/> <Element_1_3/> </Element_1> <Element_2/> <Element_3/> </Root> 次のコードは、GetContent メソッドから返された要素を格納する配列 を宣言します。このメソッドは、pbdom_doc という名前の PBDOM_DOCUMENT オブジェクトを読み込みます。 PBDOM_OBJECT pbdom_obj_array[] アプリケーション テクニック 265 PBDOM の使い方 ... pbdom_doc.GetContent(ref pbdom_obj_array) これで、pbdom_obj_array 配列に pbdom_doc のルート要素を表す 1 つの 値 <Root> が格納されます。 pbdom_doc 内のほかのノードにアクセスするには、GetRootElement メ ソッドを GetContent メソッドとともに使用します。 pbdom_doc.GetRootElement().GetContent & (ref pbdom_obj_array) これで、pbdom_obj_array 配列に、pbdom_doc のルート要素の 3 つの子 ノードに対応する 3 つの値、つまり <Element_1>、<Element_2>、およ び <Element_3> が格納されます。 PBDOM には、データにアクセスするためのメソッドがほかにもあり ます。InsertContent、AddContent、RemoveContent、SetContent などです。 配列によるノード内容 の変更 AddContent メソッドを使用してノード内容を変更できます。 pbdom_obj_array[3].AddContent("This is Element 3.") 次のコード行は、次のようにノード ツリーを変更します。 <Root> <Element_1> <Element_1_1/> <Element_1_2/> <Element_1_3/> </Element_1> <Element_2/> <Element_3>This is Element 3.</Element_3> </Root> 配列とオブジェクト参照 PBDOM_DOCUMENT クラスの GetContent メソッドなどのメソッドを 使用して PBDOM_OBJECT 参照の配列を返す場合、その参照は PBDOM オブジェクトに対するものです。配列項目を通してこれらのオブジェ クトのいずれかを修正した場合、変更内容は永続し、同じオブジェク ト参照を持つほかのすべての配列に反映されます。 266 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 ノード ツリー階層の操作 XML ノード ツリーは、ノードを再配置することにより再構築できま す。ノード操作の 1 つの方法は、子ノードを親ノードからデタッチす ることです。これは、次の例のように、Detach メソッドを使用して実 行できます。 pbdom_doc という名前の PBDOM_DOCUMENT オブジェクトのルート 要素を、GetRootElement メソッドを使用して取得します。 pbdom_obj = pbdom_doc.GetRootElement() ルート要素を PBDOM_DOCUMENT オブジェクトからデタッチしま す。このオブジェクトはルート要素の親ノードです。 pbdom_obj.Detach() PBDOM は、別のオブジェクトの子オブジェクトを作成する SetParentObject メソッドを提供します。 親ノードのチェック 次の例のように、GetParentObject メソッドを使用して、要素に親オブ ジェクトがあるかどうかを判断できます。 pbdom_parent_obj = pbdom_obj.GetParentObject() if not IsValid(pbdom_parent_obj) then MessageBox (" 不正 ", " ルート要素に親がありません。") end if GetParentObject が呼び出されるオブジェクトに親オブジェクトがない 場合、関数は NULL を返します。 PBDOM には、XML ノード ツリー内での要素の場所に関する情報を返 すメソッドがほかにもあります。そのようなメソッドの例は、HasChildren (オブジェクトに子オブジェクトがあるかどうかのブール値を返す)、 IsAncestorObjectOf(オブジェクトが別のオブジェクトの先祖かどうかを 示す)などです。 PBDOM 例外の処理 PBDOM は、標準の PowerBuilder Exception クラスから派生する例外ク ラス PBDOM_EXCEPTION を定義します。Exception クラスの標準 Text プロパティを使用して、送出される例外の性質に関する詳細を知るこ とができます。このクラスは PowerBuilder Exception クラスを拡張し、 1 つのメソッド GetExceptionCode を持ちます。このメソッドは、送出さ れる例外を識別する固有のコードを返します。 アプリケーション テクニック 267 PBDOM 例外の処理 例外コードのリストについては、『PowerBuilder エクステンション リ ファレンス』マニュアルか、オンライン ヘルプの PBDOM 例外に関す るトピックを参照してください。 PBDOM は PowerBuilder エクステンションであり、PBNI を使用して作 成されます。このエクステンション自体が PBXRuntimeError 例外を送 出する場合があります。次の例では、try-catch ブロックが、まず PBDOM 例外をチェックし、次に PBXRuntimeError をチェックします。 次の例では、渡されたファイル名から PBDOM_DOCUMENT を作成し、 ProcessData という名前のユーザ定義関数を使用して DOM ノードを処 理します。ProcessData 関数は、以降の処理のために DOM 要素から情 報を抽出する再帰関数である場合もあります。 Long ll_ret ll_ret = XMLParseFile(filename, ValNever!) if ll_ret < 0 then return PBDOM_Builder domBuilder TRY domBuilder = CREATE PBDOM_Builder PBDOM_Document domDoc PBDOM_Element root domDoc = domBuilder.BuildFromFile( filename ) IF IsValid( domDoc ) THEN IF domDoc.HasChildren() THEN PBDOM_Object data[] IF domDoc.GetContent( data ) THEN Long ll_index, ll_count ll_count = UpperBound( data ) FOR ll_index = 1 TO ll_count ProcessData( data[ll_index], 0 ) NEXT END IF END IF END IF CATCH ( PBDOM_Exception pbde ) MessageBox( "PBDOM 例外 ", pbde.getMessage() ) CATCH ( PBXRuntimeError re ) MessageBox( "PBNI 例外 ", re.getMessage() ) END TRY 268 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 XML 名前空間 XML 名前空間を使用すれば、グローバルに固有名を作成して、名前は 同じだが用語の種類が異なるという要素と属性とを区別することがで きます。たとえば、書店の XML 送り状ドキュメントで、「date」とい う名前は、会計処理では注文日を表し、注文処理では発行日を表す場 合があります。 XML 名前空間は、Web 上のリソースを一意に識別する短い文字列であ る Uniform Resource Identifier(URI)によって識別されます。各名前空 間内の要素と属性は、要素名または属性名(ローカル名)に名前空間 の URI を使用して接頭辞を付けることによって一意に識別できます。 接頭辞と名前空間の関 連付け xmlns を使用して、名前空間宣言属性の一部として XML 名前空間を宣 言します。名前空間宣言属性を使用して、接頭辞を名前空間に関連付 けることができます。 たとえば、次の名前空間宣言属性は、http://www.pre.com の名前空間を 宣言し、接頭辞 pre をこの名前空間に関連付けます。 xmlns:pre="http://www.pre.com" デフォルトの XML 名 前空間 XML 名前空間宣言が接頭辞を指定しない場合、その名前空間はデフォ ルトの XML 名前空間になります。たとえば、次の要素 digicom は名前 空間として http://www.digital_software.com を宣言します。 <digicom xmlns="http://www.digital_software.com" /> 名前空間 http://www.digital_software.com は、要素 digicom、および digicom に含まれる可能性のあるすべての子要素の、スコープ内でのデフォル トの名前空間です。digicom の子要素は、自動的にこの名前空間に配置 されます。 NONAMESPACE 宣言 次の名前空間宣言を NONAMESPACE 宣言と呼びます。 xmlns="" 含んでいる要素とその子要素を名前空間内に配置しないよう宣言しま す。NONAMESPACE の名前空間内の要素には、空の文字列に設定され た名前空間の接頭辞および URI セットが付けられています。 初期状態 PBDOM_ELEMENT か PBDOM_ATTRIBUTE を初めて作成したとき、 そ れ に は 名 前 が あ り ま せ ん。名 前 空 間 の 情 報 は、デ フ ォ ル ト で NONAMESPACE に設定されています。(つまり、その名前空間の接頭 辞と URI はどちらも空の文字列です。)SetName メソッドを使用して ローカル名を設定し、SetNamespace メソッドを使用して名前空間の接 頭辞と URI を設定します。 アプリケーション テクニック 269 XML 名前空間 名前は必須 名前は PBDOM_ELEMENT および PBDOM_ATTRIBUTE の必須プロパ ティですが、名前空間の情報は必須ではありません。 解析済みドキュメント からの取り出し PBDOM_ELEMENT か PBDOM_ATTRIBUTE を解析済みドキュメント からプログラムによって取り出すと、名前と名前空間の情報が、解析 済みドキュメントに含まれている Element か Attribute から継承されま す。ただし解析後も、SetName メソッドおよび SetNamespace メソッド を使用して、PBDOM_ELEMENT および PBDOM_ATTRIBUTE の名前 と名前空間の情報をさらに修正することができます。 名前と名前空間の情報は、内部で個別に格納されます。 PBDOM_ELEMENT か PBDOM_ATTRIBUTE の名前の変更は、名前空 間の情報には影響しません。また、名前空間の情報の変更は、名前に 影響しません。 PBDOM_ATTRIBUTE の名前および名前空間の設定 W3C の「XML 名前空間」仕様(セクション 5.3)では、 PBDOM_ATTRIBUTE の名前および名前空間の設定に制限を設けてい ます。1 つのタグ内に同一名の属性を 2 つ置くことはできません。ま た、同一ローカル名を含んでいる修飾名、かつ同一名前空間名に関連 付けられた接頭辞を含んでいる修飾名を持つ属性を、1 つのタグ内に 2 つ置くことはできません。 この仕様では、不正な属性および有効な属性として以下の例が挙げら れています。 <!-- http://www.w3.org is bound to n1 and n2 --> <x xmlns:n1="http://www.w3.org" xmlns:n2="http://www.w3.org" > <bad a="1" a="2" /> <bad n1:a="1" n2:a="2" /> </x> <!-- http://www.w3.org is bound to n1 and is the default --> <x xmlns:n1="http://www.w3.org" xmlns="http://www.w3.org" > <good a="1" b="2" /> <good a="1" n1:a="2" /> </x> 270 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 最初の例では、<bad a="1" a="2" /> は、1 つのタグ内に同一名の属 性を 2 つ置くことはできないという規約に違反しています。2 つ目の タグにある複数の属性は、ローカル名は同じですが接頭辞が異なるの で、属性の名前は相互に異なります。しかし、これらの属性の接頭辞 は同じ名前空間 URI http://www.w3.org を指すので、同じオーナー要素 内にそれらの属性を配置することは不正です。 PBDOM シナリオ 以下のシナリオでは、どのようにして PBDOM が上の要件を満たすか を示します。 • PBDOM_ATTRIBUTE の SetName メソッドを呼び出す場合 : PBDOM_ATTRIBUTE の pbdom_attr1 のオーナー PBDOM_ELEMENT に含まれている既存の PBDOM_ATTRIBUTE が、pbdom_attr1 に設定されることになっている名前と同じ名前を 持ち、かつ pbdom_attr1 と同じ名前空間 URI を持つ場合、 EXCEPTION_INVALID_NAME 例外が送出されます。 • PBDOM_ATTRIBUTE の SetNamespace メソッドを呼び出す場合 : PBDOM_ATTRIBUTE の pbdom_attr1 のオーナー PBDOM_ELEMENT に含まれている既存の PBDOM_ATTRIBUTE が、pbdom_attr1 と同じ名前を持ち、かつ pbdom_attr1 に設定される ことになっているものと同じ名前空間 URI を持つ場合、 EXCEPTION_INVALID_NAME 例外が送出されます。 • PBDOM_ELEMENT の SetAttribute(pbdom_attribute pbdom_attribute_ref) メソッドを呼び出す場合 : PBDOM_ELEMENT に、入力 PBDOM_ATTRIBUTE と同じ名前お よび同じ名前空間 URI の属性がすでにある場合、既存の属性は入 力 PBDOM_ATTRIBUTE に置き換えられます。したがって、既存 の属性はオーナー要素から削除(デタッチ)されます。 • PBDOM_ELEMENT の SetAttributes(pbdom_attribute pbdom_attribute_array[]) メソッドを呼び出す場合 : 配列内で、いずれか 2 つの PBDOM_ATTRIBUTE オブジェクトが 同じ名前および同じ名前空間 URI を持つ場合、 EXCEPTION_INVALID_NAME 例外が送出されます。名前の衝突 または名前空間の衝突が配列内にない場合、PBDOM_ELEMENT のすべての既存の属性が、配列内で PBDOM_ATTRIBUTE オブ ジェクトに置き換えられます。 アプリケーション テクニック 271 XML 名前空間 注意 上のシナリオはすべて、NONAMESPACE 名前空間に含まれている PBDOM_ATTRIBUTE オブジェクトに適用されるものです。 • PBDOM_ELEMENT の SetAttribute(string strName, string strValue) メ ソッドを呼び出す場合 : 指定された名前と値を持つ PBDOM_ATTRIBUTE が新規に作成さ れ、PBDOM_ELEMENT に設定されます。PBDOM_ELEMENT に、 同じ名前で、かつ NONAMESPACE 名前空間内に含まれている属 性がすでにある場合、その属性は PBDOM_ELEMENT から削除(デ タッチ)されます。 • PBDOM_ELEMENT の SetAttribute(string strName, string strValue, string strNamespacePrefix, string strNamespaceUri, boolean bVerifyNamespace) メソッドを呼び出す場合 : 指定された名前、値、および名前空間の情報を持つ PBDOM_ATTRIBUTE が新規に作成され、PBDOM_ELEMENT に 設定されます。PBDOM_ELEMENT に、入力名前空間 URI と同じ 名前および同じ名前空間 URI を持つ PBDOM_ATTRIBUTE がすで にある場合、その属性は PBDOM_ELEMENT から削除(デタッ チ)されます。 例 次の例は、入力 PBDOM_ATTRIBUTE と同じ名前および同じ名前空間 URI の属性が PBDOM_ELEMENT にすでに存在する場合に、 PBDOM_ATTRIBUTE を PBDOM_ELEMENT に対して設定するとどの ような影響があるかを示します。 次の例では、次のドキュメントに基づいて PBDOM_DOCUMENT を作 成します。 <root xmlns:pre1="http://www.pre.com" xmlns:pre2="http://www.pre.com"> <child1 pre1:a="123"/> </root> 272 PowerBuilder 第 14 章 PowerBuilder XML サービスの使い方 次に、PBDOM_ATTRIBUTE オブジェクトを作成し、名前を a に、接 頭辞 URI をそれぞれ pre2 と http://www.pre.com に設定します。 PBDOM_ATTRIBUTE にオーナー PBDOM_ELEMENT がまだ割り当て られていないので、bVerifyNamespace 引数を FALSE に設定します。こ れにより、事前に宣言された名前空間の信頼確認が失敗します。テキ スト値を 456 に設定します。child1 要素には、接頭辞 pre1 が示すよう に、名前空間 http://www.pre.com に属する a という名前の属性がすでに あります。新規の PBDOM_ATTRIBUTE は接頭辞 pre2 を使用します が、これは同じ名前空間 URI を表すので、新規の PBDOM_ATTRIBUTE を child1 に正常に設定すると、既存の pre1:a は 新規の PBDOM_ATTRIBUTE pre2:a に置き換えられます。 PBDOM_BUILDER pbdom_buildr PBDOM_DOCUMENT pbdom_doc PBDOM_ATTRIBUTE pbdom_attr string strXML = "<root xmlns:pre1=~"http://www.pre.com~" xmlns:pre2=~"http://www.pre.com~"><child1 pre1:a=~"123~"/></root>" try pbdom_buildr = Create PBDOM_BUILDER pbdom_doc = pbdom_buildr.BuildFromString (strXML) // PBDOM_ATTRIBUTE を作成し、そのプロパティを設定します。 pbdom_attr = Create PBDOM_ATTRIBUTE pbdom_attr.SetName ("a") pbdom_attr.SetNamespace ("pre2", & "http://www.pre.com", false) pbdom_attr.SetText("456") // child1 要素の取得を試み、 // 新規属性をそれに設定します。 pbdom_doc.GetRootElement(). & GetChildElement("child1").SetAttribute(pbdom_attr) pbdom_doc.SaveDocument & ("pbdom_elem_set_attribute_1.xml") catch (PBDOM_EXCEPTION except) MessageBox ("PBDOM_EXCEPTION", except.GetMessage()) end try アプリケーション テクニック 273 XML 名前空間 SaveDocument からの XML 出力は、次のようになります。 <root xmlns:pre1="http://www.pre.com" xmlns:pre2="http://www.pre.com"> <child1 pre2:a="456"/> </root> 274 PowerBuilder 第 1 5 章 グラフの操作 この章について この章では、実行時に、アプリケーションのグラフにアクセスし て変更するためのコードの記述方法について説明します。 内容 項目 グラフの使い方 グラフへのデータ表示 グラフのプロパティの修正 データのプロパティへのアクセス ポイント アンド クリックの使い方 ページ 275 277 279 281 283 グラフの使い方 PowerBuilder でグラフを表示するには、2 つの方法があります。 • データウィンドウで、データウィンドウ データ ソースから取 り出したデータを使用する方法 • ユーザ オブジェクトまたはウィンドウ内のグラフ コントロー ルで、アプリケーション コードから提供されたデータを使用 する方法 この章では、グラフ コントロールについて検討し、アプリケーショ ン コードを使用してグラフにデータを提供し、その外観を操作す る方法について説明します。 データウィンドウのグラフについての詳細は、 『データウィンドウ プログラマーズ ガイド』マニュアルと『データウィンドウ リファ レンス』マニュアルを参照してください。 ペインタにおけるグラフのデザインとグラフ プロパティの設定に ついては、PowerBuilder の『ユーザーズ ガイド』マニュアルを参 照してください。 アプリケーション テクニック 275 グラフの使い方 コードにおけるグラフ コントロールの操作 ウィンドウ内のグラフ コントロールは、使用可能 / 使用不可、表示 / 非表示を切り替えることができ、ドラッグ アンド ドロップを使用でき ます。また、グラフ コントロールのイベントおよび補助的なグラフ関 数を使用するコードも記述できます。 グラフ コントロール のプロパティ グラフにアクセスする(そしてオプションで修正する)には、実行時 にスクリプトでグラフのプロパティを操作します。グラフのプロパ ティには次の 2 種類があります。 • グラフ定義自体のプロパティ これは、グラフを作成するときにデー タウィンドウ ペインタで最初に設定するプロパティです。グラフ の種類、タイトル、軸ラベルを設定し、軸に目盛りを付けるかど うかを指定します。 • データのプロパティ これらのプロパティは、実行時にデータがグ ラフにロードされたときにだけ関係します。これらのプロパティ では、グラフ内の系列数(系列は実行時に作成される)、系列の横 棒または縦棒の色、系列がオーバーレイかどうか、項目の文字(項 目は実行時に作成される)などを設定します。 グラフ コントロール のイベント グラフ コントロールには、表 15-1 にリストされているイベントがあり ます。 表 15-1: グラフ コントロールのイベント Clicked DragLeave Constructor DragWithin Destructor GetFocus DoubleClicked LoseFocus DragDrop Other DragEnter RButtonDown たとえば、 (グラフが使用できる状態で)エンド ユーザがグラフをク リックしたとき、またはオブジェクトをグラフ上にドラッグしたとき に起動されるようなスクリプトを記述できます。 グラフ コントロール 用の関数 276 表 15-2 の PowerScript グラフ関数を使って、グラフのデータを操作で きます。 PowerBuilder 第 15 章 グラフの操作 表 15-2: PowerScript グラフ関数 関数 動作内容 AddCategory 項目の追加 データ ポイントの追加 系列の追加 項目の削除 データ ポイントの削除 系列の削除 クリップボードからグラフにデータをコピー テキスト ファイル内のデータをグラフにコピー 文字列の内容をグラフにコピー ほかの項目の前に項目を挿入 AddData AddSeries DeleteCategory DeleteData DeleteSeries ImportClipboard ImportFile ImportString InsertCategory InsertData InsertSeries ModifyData Reset 系列内のほかのデータ ポイントの前にデータ ポイント を挿入 ほかの系列の前に系列を挿入 データ ポイントの値を変更 グラフのデータをリセット グラフへのデータ表示 この節では、空のグラフにデータを表示する方法を示します。 AddSeries 関数の使い 方 AddSeries 関数を使用して系列を作成します。AddSeries 関数の構文は次 のとおりです。 graphName.AddSeries ( seriesName ) AddSeries 関数は、作成された系列を識別する整数を返します。最初の 系列には 1、2 番目には 2 のように番号が付けられます。一般にこの番 号は、系列を操作するほかのグラフ関数の最初の引数として使用され ます。 ステラという名前の系列を作成するには、次のコードを使用します。 int SNum SNum = gr_1.AddSeries(" ステラ ") AddData 関数の使い 方 AddData 関数を使って、指定した系列にデータ ポイントを追加します。 AddData 関数の構文は次のとおりです。 graphName.AddData ( seriesNumber, value, categoryLabel ) アプリケーション テクニック 277 グラフへのデータ表示 AddData 関数の最初の引数は、PowerBuilder によってその系列に割り当 てられている番号です。したがって、上記のように変数 SNum に番号 が格納されているステラという系列に 2 つのデータ ポイントを追加す るには、次のコードを使用します。 gr_1.AddData(SNum, 12, "Q1") // 項目は Q1 です。 gr_1.AddData(SNum, 14, "Q2") // 項目は Q2 です。 系列番号の取得 FindSeries 関数を使用して、系列に割り当てられた番号を知ることがで きます。FindSeries 関数は系列番号を返します。これは、汎用関数を記 述してグラフを操作するときに便利です。 例 四半期ごとのプリンタ販売台数のグラフを作成するには、次のスクリ プトを使用してデータをグラフにします。 gr_1.Reset(All!)// グラフをリセットします。 // 最初の系列を作成し、データを表示します。 int SNum SNum = gr_1.AddSeries(" ステラ ") gr_1.AddData(SNum, 12, "Q1") // 項目は Q1 gr_1.AddData(SNum, 14, "Q2") // 項目は Q2 gr_1.Adddata(SNum, 18, "Q3") // 項目は Q3 gr_1.AddData(SNum, 25, "Q4") // 項目は Q4 // 2 番目の系列を作成し、データを表示します。 SNum = gr_1.AddSeries(" コスミック ") です。 です。 です。 です。 // 系列 1 と同じ項目を使用するため、データは // 系列 1 のデータの横に表示されます。 gr_1.AddData(SNum, 18, "Q1") gr_1.AddData(SNum, 24, "Q2") gr_1.Adddata(SNum, 38, "Q3") gr_1.AddData(SNum, 45, "Q4") // 3 番目の系列を作成し、データを表示します。 SNum = gr_1.AddSeries(" ギャラクティック ") gr_1.AddData(SNum, 44, "Q1") gr_1.AddData(SNum, 44, "Q2") gr_1.Adddata(SNum, 58, "Q3") gr_1.AddData(SNum, 65, "Q4") 278 PowerBuilder 第 15 章 グラフの操作 次に実行結果のグラフを示します。 実行時には、グラフ関数を介して、ウィンドウ内のグラフのデータを 追加、修正、または削除できます。 詳細情報 各グラフ関数についての詳細は、『PowerScript リファレンス』マニュ アルを参照してください。 グラフのプロパティの修正 ウィンドウまたはユーザ オブジェクト ペインタでグラフを定義する ときは、その動作と表示方法を指定します。たとえば、何らかのタイ トルをもつ縦棒グラフとしてグラフを定義し、数値軸を 4 つの目盛り に分割します。各入力項目は、グラフのプロパティに対応します。ど のグラフにも、グラフの種類を指定するカタログ型の属性 GraphType があります。 グラフの種類の動的な変更 グラフの種類を変更する場合、新しいグラフを正しく定義するには、 必要に応じてほかのプロパティも変更しなければなりません。 実行時にこれらのグラフ プロパティを変更するには、スクリプトでグ ラフ プロパティに値を割り当てます。たとえば、グラフ gr_emp の種 類を縦棒グラフに変更するには、次のコードを使用します。 gr_emp.GraphType = ColGraph! 実行時にグラフのタイトルを変更するには、次のコードを使用します。 gr_emp.Title = " 新しいタイトル " アプリケーション テクニック 279 グラフのプロパティの修正 グラフ要素の表示 グラフは、タイトル、凡例、および軸で構成されます。これらの要素 には、それぞれ表示プロパティがあります。これらの表示プロパティ は、grDispAttr という名前の Graph のサブオブジェクト(構造体)にプ ロパティとして格納されています。 グラフには、タイトルの文字を指定する Title プロパティがあります。 また、grDispAttr 型の TittleDispAttr プロパティには、フォントやサイ ズ、斜体などタイトル文字の特性を指定するプロパティが入っていま す。 同様に、グラフにはそれぞれプロパティを備えた 2 本の軸があります。 軸のプロパティは、grAxis という名前の Graph サブオブジェクト(構造 体)に格納されています。値の自動スケーリングの有無、大小の区分 の数、軸ラベルなどの数値軸プロパティを指定するためのプロパティ が、grAxis 型の Values プロパティに入っています。 以下にグラフのプロパティを示します。 Graph int Height int Depth grGraphType GraphType boolean Border string Title … grDispAttr TitleDispAttr, LegendDispAttr, PieDispAttr string FaceName int TextSize boolean Italic … grAxis Values, Category, Series boolean AutoScale int MajorDivisions int MinorDivisions string Label … グラフ要素の参照 表示プロパティを参照するには、ドット(.)表記を使用します。たと えば、グラフ タイトルのプロパティの 1 つに、その文字が斜体かどう かを指定するものがあります。この情報は、グラフの TitleDispAttr プ ロパティにある Boolean 型の Italic プロパティに格納されています。 280 PowerBuilder 第 15 章 グラフの操作 たとえば、グラフ gr_emp のタイトルを斜体にするには、次のコードを 使用します。 gr_emp.TitleDispAttr.Italic = TRUE また、グラフの数値軸を自動スケーリングするには、次のコードを使 用します。 gr_emp.Values.Autoscale = TRUE 数値軸のラベルの文字を変更するには、次のコードを使用します。 gr_emp.Values.Label = " 新しいラベル " 数値軸のラベル文字の位置を変更するには、次のコードを使用します。 gr_emp.Values.LabelDispAttr.Alignment = Left! グラフのプロパティの一覧については、『オブジェクトとコントロー ル』マニュアルを参照するか、またはブラウザを使用してください。 ブラウザについての詳細は、PowerBuilder の『ユーザーズ ガイド』マ ニュアルを参照してください。 データのプロパティへのアクセス 実行時に、グラフのデータに関連付けられているプロパティにアクセ スするには、PowerScript グラフ関数を使用します。データには、以下 のような種類の関数が関連付けられています。 関数の使い方 • グラフのデータに関する情報を提供する関数 • グラフからのデータを保存する関数 • データの色や模様などの表示プロパティを変更する関数 グラフ コントロール内のグラフに対する関数を呼び出すには、次の構 文を使用します。 graphControlName.FunctionName ( Arguments ) ウィンドウ内のグラフ gr_printer の項目数を取得するには、次のように します。 Ccount = gr_printer.CategoryCount() アプリケーション テクニック 281 データのプロパティへのアクセス データウィンドウにおけるグラフのさまざまな構文 次に示すように、グラフがデータウィンドウ内にある場合には、同じ 関数の構文がもっと複雑になります。 DataWindowName.FunctionName ( "graphName", otherArguments... ) 詳細については、『データウィンドウ プログラマーズ ガイド』マニュ アルを参照してください。 データの情報の取得 表 15-3 の PowerScript 関数を使用すれば、実行時にグラフ内のデータ に関する情報を取得できます。 表 15-3: 実行時に情報を取得するための PowerScript 関数 関数 CategoryCount CategoryName DataCount FindCategory FindSeries GetData GetDataPieExplode GetDataStyle GetDataValue GetSeriesStyle ObjectAtPointer SeriesCount SeriesName 282 受け取る情報 グラフ内の項目数 指定された項目番号に対応する項目名 系列内のデータ ポイント数 指定された項目名に対応する項目番号 指定された系列名に対応する系列番号 指定された系列と位置に対応するデータ ポイント値 (GetDataValue の方が柔軟性が高い) 円グラフのスライスを突出させる割合 指定されたデータ ポイントの色や模様など表示関係 のプロパティ 指定された系列と位置に対応するデータ ポイント値 指定された系列の色や模様などの表示関係のプロパ ティ マウスがクリックされたときにポイントされている グラフの要素 グラフ内の系列数 指定された系列番号に対応する系列名 PowerBuilder 第 15 章 グラフの操作 グラフのデータの保存 表 15-4 の PowerScript 関数を使って、グラフからのデータを保存でき ます。 表 15-4: グラフのデータの保存に使用する PowerScript 関数 関数 Clipboard SaveAs 動作内容 指定されたグラフのビットマップ イメージをクリッ プボードにコピー 基になるグラフ内のデータをクリップボードまたは さまざまな書式のファイルに保存 色や模様、そのほかのデータの修正 表 15-5 の PowerScript 関数を使って、グラフ内のデータの表示方法を 修正できます。 表 15-5: データの表示を修正するための PowerScript 関数 関数 ResetDataColors SetDataPieExplode SetDataStyle SetSeriesStyle 動作内容 指定されたデータ ポイントの色をリセット 円グラフ内のスライスを突出させる 指定されたデータ ポイントの色や模様などの表示関 係のプロパティを設定 系列の色や模様などの表示関係のプロパティを設定 ポイント アンド クリックの使い方 エンド ユーザは、実行時にグラフをクリックできます。PowerScript に は、何がクリックされたかという情報を格納する ObjectAtPointer 関数が あります。この関数は、Clicked イベントにおいてさまざまな方法で使 用できます。たとえば、グラフ内のデータ値をポイント アンド クリッ クして、メッセージ ボックス内にその値に関する情報を表示する機能 を付けることができます。この節では、その方法について説明します。 Clicked イベントとグ ラフ エンド ユーザがグラフをクリックしたときにアクションが起動する ように、グラフのコントロールに Clicked スクリプトを記述します。コ ントロールが有効でなければ、Clicked イベントは発生しません。 アプリケーション テクニック 283 ポイント アンド クリックの使い方 ObjectAtPointer 関数 の使い方 ObjectAtPointer 関数の構文は、以下のとおりです。 graphName.ObjectAtPointer ( seriesNumber, dataNumber ) ObjectAtPointer 関数は、Clicked イベントの最初のステートメントで呼 び出さなければなりません。 呼び出された ObjectAtPointer 関数は、3 つのことを行います。 • クリックされたオブジェクトの種類を、カタログ値 grObjectType として返します。たとえばエンド ユーザがデータ ポイントをク リックした場合、ObjectAtPointer 関数は TypeData! を返します。エ ンド ユーザがグラフのタイトルをクリックした場合には、 ObjectAtPointer 関数は TypeTitle! を返します。 grObjectType のカタログ値をすべて閲覧するには、ペインタバーの [オブジェクト ブラウザ]をクリックして、ブラウザを開いて[カ タログ データ型]タブを選択してください。 • ポインタが置かれた系列の番号を、変数 seriesNumber に格納しま す。これは参照によって渡される引数です。 • データ ポイントの番号を、変数 dataNumber に格納します。これも 参照によって渡される引数です。 系列番号とデータ ポイント番号を取得したら、そのほかのグラフ関数 を使って情報を取得または提供できます。たとえば、クリックされた データ ポイントの値を、エンド ユーザにレポートします。 例 ウィンドウに gr_sale というグラフがあるとします。gr_sale の Clicked イベントに対して次のようなスクリプトを記述すると、以下のような メッセージ ボックスが開きます。 • • エンド ユーザが系列をクリックすると(つまり ObjectAtPointer 関数 が TypeSeries! を返すと) 、クリックした系列の名前がメッセージ ボッ クスに表示されます。このスクリプトでは、SeriesName 関数を使っ て、ObjectAtPointer 関数によって格納されている系列番号に対応す る系列名を取得します。 エンド ユーザがデータ ポイントをクリックすると(つまり ObjectAtPointer 関数が TypeData! を返すと) 、クリックされた系列の 名前と値のリストがメッセージ ボックスに表示されます。このス クリプトでは、GetData 関数を使って、データの系列番号とデータ ポイント番号に対応するデータ値を取得します。 int SeriesNum, DataNum double Value grObjectType ObjectType string SeriesName, ValueAsString 284 PowerBuilder 第 15 章 グラフの操作 // 次の関数は、クリックされた系列の番号を // SeriesNum に格納し、クリックされたデータ ポイント // の番号を DataNum に格納します。 ObjectType = & gr_sale.ObjectAtPointer (SeriesNum, DataNum) IF ObjectType = TypeSeries! THEN SeriesName = gr_sale.SeriesName (SeriesNum) MessageBox(" グラフ ", & SeriesName + " の系列がクリックされました。") ELSEIF ObjectType = TypeData! THEN Value = gr_sale.GetData (SeriesNum, DataNum) ValueAsString = String(Value) MessageBox(" グラフ ", & gr_sale.SeriesName (SeriesNum) + & " の値は " + ValueAsString + " です。") END IF アプリケーション テクニック 285 ポイント アンド クリックの使い方 286 PowerBuilder 第 1 6 章 リッチテキストの作成方法 この章について この章では、リッチテキスト データウィンドウ オブジェクトと リッチテキスト エディット コントロールにおける、リッチテキス トの使い方について説明します。 内容 はじめに 項目 アプリケーションにおけるリッチテキストの使い方 リッチテキスト データウィンドウ オブジェクトの使い方 リッチテキスト エディット コントロールの使い方 リッチテキストとエンド ユーザ ページ 287 289 291 311 この章は、PowerBuilder の『ユーザーズ ガイド』マニュアルで解 説されている、リッチテキスト データウィンドウ オブジェクトと リッチテキスト エディット コントロールの作成方法を知ってい ることを前提としています。 アプリケーションにおけるリッチテキストの使い方 リッチテキスト形式(RTF)は、1 つの ASCII 文書中に書式や文書 内容を指定するテキストファイルの標準形式です。リッチテキス ト フォーマットをサポートするエディタは、フォーマット命令を 解釈しフォーマットしたテキストを表示します。 アプリケーションでは、たとえば以下のような処理が可能です。 • リッチテキスト文書の作成用のウィンドウを表示する 本格的なワープロ機能ではありませんが、リッチテキスト エ ディット コントロールを使用することによってエンド ユーザ は、段落、単語、および文字に書式を設定することができます。 • 差し込み印刷をする 開発者またはエンド ユーザは、データベース カラムに関連付 けられた入力フィールドを使用して、文書を作成できます。 • アプリケーション テクニック 書式付きテキストのレポートを表示する 287 アプリケーションにおけるリッチテキストの使い方 リッチテキスト データウィンドウ オブジェクトは、基本的に、 データ入力よりもデータ表示のために使用されるオブジェクトで す。ほかの提示様式と異なり、データウィンドウ提示様式では編 集様式は使用できません。 • リッチテキストを String 型のデータとしてデータベースに格納し、 リッチテキスト エディット コントロールで表示させる リッチテキストの作成 ワード プロセッサ リッチテキスト形式のファイルを保存またはエクスポートできるワー ド プロセッサを使用して、リッチテキストを作成できます。 PowerBuilder だけの 入力フィールド 多くのワードプロセッサではなんらかの種類のフィールドをサポート していますが、通常それらのフィールドはほかのリッチテキストと互 換 性 が あ り ま せ ん。PowerBuilder ア プ リ ケ ー シ ョ ン に お い て 入 力 フィールドを指定するには、PowerBuilder のリッチテキスト エディッ ト コントロールを使用してフィールドを挿入しなければなりません。 データベースにおける リッチテキスト リッチテキストは ASCII 文字によって表現されているため、データ ベースの String 型カラムや文字列変数に格納することもできます。デー タベースの String 型カラムからリッチテキストを取得し、PasteRTF 関 数を使用してリッチテキスト エディット コントロールに書式付きテ キストを表示できます。 リッチテキスト アプリケーションの配布 リッチテキスト アプリケーションをサーバあるいはクライアント マ シンに配布する場合は、Sybase\Shared\PowerBuilder\RTC ディレクト リにあるリッチテキスト DLL ファイルおよび OCX ファイルを、配布 マシンの PowerBuilder VM ディレクトリあるいはアプリケーションの パスのディレクトリにもコピーする必要があります。868 ページの 表 41-5 に、コピーする必要があるファイルのリストを記載していま す。 PowerBuilder ランタイム パッケージャを使用して、アプリケーション とともに必要なリッチテキスト ファイルを配布することができます。 しかし、配布マシンにおいて tp4ole13.ocx ファイルを登録する必要も あります。 ランタイム パッケージャの詳細については、859 ページの「PowerBuilder ランタイム パッケージャ」を参照してください。 288 PowerBuilder 第 16 章 リッチテキストの作成方法 リッチテキスト データウィンドウ オブジェクトの使い方 この節では、以下の項目について説明します。 ページ スクロール • ほかの提示様式とのページ スクロールの違い • 新しい行におけるデフォルト値と入力条件則 • エンド ユーザが変更を行ったときの動作 リッチテキスト データウィンドウ オブジェクトでは、複数ページの リッチテキスト(文書テンプレート)を作成でき、1 行のデータが複 数ページにまたがることもあります。これに対して、ほかの提示様式 では、1 ページに複数行のデータが表示されることもあります。 リッチテキスト データウィンドウ オブジェクトでは、1 ページの構成 がほかの提示様式と異なるため、スクロール関数はほかの提示様式と は異なる動作をします。 • ScrollNextRow 関数と ScrollPriorRow 関数は、データベース テーブル の行から行へと移動するので、リッチテキスト(文書テンプレー ト)内において、前の行または次の行のデータを表示します。 • ScrollNextPage 関数と ScrollPriorPage 関数は、行ではなく、文書の ページをスクロールします。 改ページ スクロールすると、行から行へと移動します。文書の最終 ページで次ページへスクロールすると、次の行の最初のページへ移動 します。ユーザは、文書内の多くのインスタンスでスクロールの効果 を利用することができます。 新しい行 : デフォルト のデータと入力条件則 入力フィールドに値がない場合、入力フィールドは非表示になります。 入力フィールドが見えるように、データが検索される前は、入力フィー ルドには疑問符(??)が表示されます。新しい行に対しては、カラム のデータ型を基に入力フィールドに初期値が設定されます。 カラムにすでに初期値が設定されている場合は、その値が使用されま す。初期値が設定されていない場合、PowerBuilder は、String 型のカラ ムに対しては空白文字(スペース)を、numeric 型のカラムに対しては ゼロを初期値として設定します。 PowerBuilder で提供されるデフォルトの初期値が入 力条件則を満たさない場合、新しい行が挿入された直後にエンド ユー ザに入力条件則エラーが表示されます。これを回避するためには、入 力条件則に合う初期値を指定する必要があります。 入力条件則エラー エンド ユーザによる 変更 編集禁止の指定 リッチテキストオブジェクト プロパティ シートの [全 般]タブ ページで[編集禁止]チェックボックスをオンにすると、エ ンド ユーザはデータおよびテキストを一切変更できなくなります。 アプリケーション テクニック 289 リッチテキスト データウィンドウ オブジェクトの使い方 [ポップアップ メニュー]チェックボックスをオンにした場合は、エ ンド ユーザはプロパティ シートを開くことができるので、 [編集禁止] チェックボックスをオフにして、データウィンドウ オブジェクトを編 集可能にすることができます。 入力フィールド 編集可能なデータウィンドウでは、エンド ユーザは入 力フィールドのプロパティ シートを表示し、 [データ値]テキストボッ クスを編集して、カラム入力フィールドの値を変更します。計算フィー ルドに対応する入力フィールドの場合、 [データ値]テキストボックス は変更できません。 データのかわりに入力フィールド名を表示させることができます。 データのかわりに入力フィールド名を表示して、エンド ユーザが独自 にリッチテキスト データウィンドウを作成できる編集環境を提供す ることもできます。しかし、エンド ユーザに編集環境を提供したい場 合は、リッチテキスト データウィンドウよりも、スクリプトで制御で きるリッチテキスト エディット コントロールを使用する方が適して います。 リッチテキスト エンド ユーザがテキストまたは書式を変更した場合 は、文書テンプレートが変更されたことになります。変更はすべての 行に現れます。 文書テンプレートに対する変更を保存するスクリプトを記述しておか ないと、エンド ユーザが行った変更は現行のセッションだけに適用さ れ、次回まで保持されません。 変更を保存するには、CopyRTF 関数を使用します。この関数は、入力 フィールドを含むすべてのテキストを取得しますが、行データは取得 しません。その後、取得した文字列をファイルまたはデータベースに 保存します。これによって、エンド ユーザがリッチテキスト データ ウィンドウを操作するときに、前回の変更点を復元して表示させたり、 オリジナルの文書テンプレートに戻して表示させたりすることができ ます。 リッチテキスト デー タウィンドウにおける 関数 データウィンドウ コントロールには、数多くの関数があります。 同様に動作する関数 Update 関数や Retrieve 関数のようなデータ操作関 数は、すべての提示様式のデータウィンドウ オブジェクトに対して同 様に動作します。 コントロール内のオブジェクトがリッチテキスト データウィンドウ オブジェクトである場合には、一部の関数は適用されないか、異なる 動作を行います。 290 PowerBuilder 第 16 章 リッチテキストの作成方法 適用されない関数 関数の中には、リッチテキスト データウィンドウ オ ブジェクトでは使用できないものもあります。以下の関数は、エラー を返すか、または何も処理を行いません。 • グラフとクロスタブ データウィンドウ オブジェクトのための関数 • グループ化のための関数 : GroupCalc、FindGroupChange • コード表のための関数 : GetValue、SetValue • 行選択のための関数 : SelectRow、SetRowFocusIndicator、 GetSelectedRow • カラムと詳細区域の表示形態を指定するための関数 : SetBorderStyle、 SetDetailHeight • ObjectAtPointer • OLEActivate リッチテキスト データウィンドウの場合に異な る動作をする関数もあります。 異なる動作をする関数 • クリップボードのための関数 : Copy、Clear など • 編集可能なテキストのための関数(ほかの提示様式のエディット コントロールに適用されます): LineCount、Position、SelectText など • Find と FindNext 関数(一般的なデータウィンドウの Find 関数か、 リッチテキストの Find 関数かは、Find 関数に指定する引数によっ て決まります) • ページ スクロール リッチテキスト エディット コントロールの使い方 ウィンドウまたはユーザ オブジェクト上に配置したリッチテキスト エディット コントロールを使用して、エンド ユーザに、書式設定され た テ キ ス ト を 参 照 さ せ た り、編 集 さ せ た り す る こ と が で き ま す。 PowerScript 関数を使用して、テキストの挿入、選択されたテキストの 取得、入力フィールドの管理、内容のプロパティ設定などを行って、 コントロールの内容を操作できます。 ウィンドウ ペインタまたはユーザ オブジェクト ペインタで、リッチ テキスト エディット コントロールを定義します。 アプリケーション テクニック 291 リッチテキスト エディット コントロールの使い方 エンド ユーザに制御権を与える ウィンドウまたはユーザ オブジェクト ペインタでは、リッチテキスト エディット コントロールのプロパティ シートの[ドキュメント]ペー ジで、表 16-1 の機能を使用可能または使用不可に設定できます。 表 16-1: リッチテキスト エディット コントロールの機能 機能 編集用バー ポップアップ メ ニュー 印刷されない文字の 表示 フィールドの表示 自動ワードラップ 余白 詳細 書式設定のツールバー、ルーラ バー、およびステー タス バー プロパティシートや、ファイルの挿入、クリップボー ド コマンドが使用可能 キャリッジ リターン、タブ文字、および半角スペー ス フィールドの表示 / 非表示、フィールド名で表示す るかデータを表示するかどうか。フィールドの背景 色を変更することもできる 新たに入力されたテキストだけに影響する 既存の段落に新しいテキストを入力すると、テキス トは、コントロールの右端に達したときにワード ラップされる。コントロールがサイズ可変の場合 は、コントロールのサイズを少し縮小することに よって、既存のテキストをワードラップさせること ができる 印刷余白をデフォルトのページ サイズにあわせて 設定できる また、印刷キューに表示される文書の名前を設定することもできます。 文書名は、コントロールに挿入するテキスト ファイルとは関係ありま せん。 エンド ユーザによる プロパティの変更 292 エンド ユーザは、プロパティ シートを使用して、リッチテキスト文書 のプロパティを設定できますが、開発者が望まない操作を行う可能性 もあります。たとえば以下のような操作を行ってしまうかもしれませ ん。 • 上書き禁止に設定してある文書の[編集禁止]オプションをオフ にして、文書を編集する • ツール バー、ルーラ、ステータス バーを非表示にする • データではなく入力フィールド名を表示する • ポップアップ メニューを使用不可にしたため、非表示にしたツー ルを元に戻すことができなくなる PowerBuilder 第 16 章 リッチテキストの作成方法 このような操作ミスを防ぐために、スクリプトでプロパティ値を変更 することができます。たとえば、以下のステートメントはイベント ス クリプトで発生した時に、ポップアップ メニューを元に戻すことがで きます。 rte_1.PopMenu = TRUE 変更の取り消し エンド ユーザが〔Ctrl〕+〔Z〕を押すと、変更は取り消されます。ま た、コマンドボタンやメニュー項目のスクリプトから Undo 関数を呼び だすこともできます。 Undo 関数が繰り返し呼ばれた場合は、最大 50 までの変更を取り消し ます。スクリプトで CanUndo 関数を呼び出すと、元に戻せる変更があ るかどうか(最大数に達していないことを意味します)をチェックす ることができます。 IF rte_1.CanUndo() THEN rte_1.Undo() ELSE MessageBox(" 停止 ", " 元に戻せる操作がありません ") END IF リッチテキスト エディット コントロールのためのテキスト ウィンドウ ペインタでは、リッチテキスト エディット コントロール にテキストを入力することはできません。そのかわり、アプリケーショ ンにおいて、スクリプトからテキストを挿入したり、エンド ユーザに テキスト入力をさせたりすることができます。 デフォルト フォントの設定 リッチテキスト エディット コントロールのプロパティ ビューの [フォ ント]タブ ページで、コントロールのデフォルト フォントを設定でき ます。実行時にコントロールが最初に表示され、リッチテキスト エ ディット コントロールと一緒にツールバーを含める場合、ツールバー は設計時に[フォント]タブ ページで選択したデフォルトフォントで 表示されます。アプリケーション ユーザは実行時にフォントを変更し たり、PowerScript を使用してフォント スタイルを変更したりできます が、設計時のみデフォルト フォントを設定できます。 テキストの挿入 ファイルから挿入 InsertDocument 関数を使用して、アプリケーションに テキスト ファイルを挿入することができます。挿入できるファイル は、リッチテキスト形式または ASCII 形式です。 li_rtn = rte_1.InsertDocument アプリケーション テクニック & 293 リッチテキスト エディット コントロールの使い方 ("c:\mydir\contacts.rtf", FALSE, FileTypeRichText!) Boolean 型の clearflag 引数によって、ファイルを挿入するのか、既存 のテキストと置き換えるのかを指定できます。挿入する文書のヘッダ およびフッタを含めたい場合は、clearflag 引数に TRUE を設定して既 存のテキストを置き換える必要があります。 (実行時ポップアップ メ ニ ュ ー の InsertFile コ マ ン ド は、clearflag 引 数 に FALSE を 設 定 し た InsertDocument 関数と同じです。 ) DisplayOnly プロパティには false を設定 リッチテキスト コントロールの DisplayOnly プロパティに true が設定 されている場合は、リッチテキスト コントロールにドキュメントを挿 入することはできません。これを行おうとすると、PowerBuilder はラ ンタイム エラー メッセージを表示します。 データベースから挿入 データベースに文字列としてリッチテキストを 保存した場合、データストア オブジェクトを使用してテキストを取得 することができます。 以下のスクリプトは、データベースからテキストを取得して、リッチ テキスト エディット コントロールに貼り付けます。 ls_desc = dw_1.Object.prod_desc.Primary[1] rte_1.PasteRTF(ls_desc) リッチテキストとクリップボード CopyRTF 関数と PasteRTF 関数は、書式指示とともにリッチテキストを 取得して、文字列に格納します。Copy、Cut、および Paste 関数でクリッ プボードを使用すると、テキストしか取得できないため、書式指示は 失われてしまいます。 データベースにリッチ テキストを保存する例 たとえば、テクニカル サポートにかかってくる電話の内容を、データ ベース テーブルに記録しているものとします。フィールドには、電話 がかかってきた日付、サポート エンジニア名、顧客名を記録します。 別のフィールドでは、内容についてのメモを格納します。リッチテキ ストを使用すると、エンド ユーザに書式付きのメモを記録させること ができます。単純なテキストではなくリッチテキストを使用すること によって、太字や斜体で強調させることができます。 編集用のウィンドウは、以下のコントロールから構成されます。 • 294 すべてのデータを検索して、電話メモを除くすべてのデータを表 示するデータウィンドウ コントロール PowerBuilder 第 16 章 リッチテキストの作成方法 • 電話メモを表示するリッチテキスト エディット コントロール • データベースを更新するためのコマンドボタン RowFocusChanged イベント RowFocusChanged イベントにスクリプト を記述して、フォーカスが移動しても、常に現行の行の電話メモをリッ チテキスト エディット コントロールに表示させます。 string ls_richtext // call_notes カラムから文字列を取得します。 ls_richtext = dw_1.Object.call_notes[currentrow] // 点滅を防止します。 rte_1.SetRedraw(FALSE) // 現行の行のテキストで古いテキストを置き換えます。 rte_1.SelectTextAll() rte_1.Clear() rte_1.PasteRTF(ls_richtext) rte_1.SetRedraw(TRUE) LoseFocus イベント LoseFocus イベントに以下のスクリプトを記述し て、エンド ユーザが変更したテキストを、データウィンドウ コント ロールに転送します。LoseFocus イベントは、エンド ユーザがテキス トの編集を終えて、コマンドボタンまたはデータウィンドウを選択し たときに起動されます。 string ls_richtext long l_currow GraphicObject l_control // リッチテキスト エディット コントロールに // フォーカスが残っているかどうかを確認します。 // フォーカスが残っている場合は、テキストを転送しません。 l_control = GetFocus() IF TypeOf(l_control) = RichTextEdit! THEN RETURN 0 // 点滅を防止します。 rte_1.SetRedraw(FALSE) // 文字列 ls_richtext にすべてのテキストを格納します。 ls_richtext = rte_1.CopyRTF() // 現行の行の call_notes カラムに // リッチテキストを割り当てます。 l_currow = dw_1.GetRow() アプリケーション テクニック 295 リッチテキスト エディット コントロールの使い方 dw_1.Object.call_notes[l_currow] = ls_richtext rte_1.SetRedraw(TRUE) LoseFocus イベントとツールバー エンド ユーザがツールバーを選択したときも、LoseFocus イベントが 起動されます。ツール バーは、リッチテキスト エディット コントロー ルとは別のコントロールとして作成されているからです。しかし、リッ チテキスト エディット コントロールにはフォーカスが残っているた め、GetFocus 関数を使用して、ツールバーがクリックされたのかどう かを確認することができます。 ファイルにリッチテキ ストを保存 SaveDocument 関数を使用すると、 入力フィールドの定義とともに、リッ チテキスト エディット コントロール内のリッチテキストを保存する ことができます。保存するファイルの種類として、リッチテキスト形 式(RTF)または ASCII 形式を指定することができます。 rte_1.SaveDocument("c:\...\contacts.rtf", & FileTypeRichText!) SaveDocument 関数は、入力フィールドのデータは保存しません。文書 テンプレートを保存します。 同名のファイルが存在する場合 フ ァ イ ル が 既 に 存 在 す る 場 合 は、 SaveDocument 関 数 を 呼 ぶ と FileExists イ ベ ン ト が 起 動 さ れ ま す。 FileExists イベントのスクリプトで、エンド ユーザにファイルを上書き するかどうかを問い合わせることができます。 保存処理をキャンセルするには、FileExists イベントのスクリプトでリ ターン コードの 1 を指定します。 保存する必要のある変更があるか Modified プロパティは、リッチテキス ト エディット コントロールの文書が変更されたかどうかを示します。 また、文書が保存されていない状態であることも示します。最初の変 更で Modified イベントが起動されて、Modified プロパティに TRUE が 設定されます。SaveDocument 関数を呼ぶと、文書が保存され、Modified プロパティに FALSE が設定されます。 296 PowerBuilder 第 16 章 リッチテキストの作成方法 ファイルをリッチテキスト エディット コントロールに挿入すると、 リッチテキスト エディット コントロールの文書が変更されるので、 Modified イベントが起動されて Modified プロパティに TRUE が設定さ れます。しかし通常の場合、本当に知りたいのはファイルの内容がコ ントロールの内容に対応しているかどうかです。この点を確認するた めには、ファイルを開くスクリプトで、Modefied プロパティを FALSE に設定します。エンド ユーザが文章を編集すると Modified イベントが 起動され、Modified プロパティに TRUE が設定されるので、コントロー ルの文書の内容とファイルの内容が一致していないことがわかりま す。 ファイルを開いて保存する例 ファイルを開いたり保存したりするスクリプトの例を示します。エン ド ユーザは、既存のファイルを開いて、リッチテキスト エディット コ ントロールで文書を変更して保存することができます。また、文書を ファイルに保存することもできます。エンド ユーザが開いたファイル に文書を保存する場合は、ファイルの上書きは確認されずにそのまま 保存されます。既存のファイルと同名のファイル名で保存しようとす ると、ファイルの上書きを確認するメッセージボックスが表示されま す。 この例では、インスタンス変数の宣言、スクリプト、関数、イベント について解説します。 アプリケーション テクニック 297 リッチテキスト エディット コントロールの使い方 インスタンス変数の宣 言 ib_saveas FileExists イベントのためのフラグ。FALSE の場合は、エン ド ユーザが開いたファイルに保存しようとしているため、ファイルは 上書きされます。 boolean ib_saveas=FALSE is_filename 現行ファイル名。初期状態では「タイトル未設定」と設 定されます。 string is_filename ファイルを開くための スクリプト 以下のスクリプトは、エンド ユーザが選択したファイルを開きます。 ファイルを開くときに Modified イベントが起動されて Modified プロ パティが TRUE に設定されるので、スクリプトで Modified プロパティ を FALSE にリセットしています。 [変更]チェックボックスの Checked プロパティも、FALSE に設定されています。 integer li_answer, li_result string ls_name, ls_path li_answer = GetFileOpenName("Open File", ls_path, & ls_name, "rtf", & "Rich Text(*.RTF),*.RTF, Text files(*.TXT),*.TXT") IF li_answer = 1 THEN // エンド ユーザが、キャンセルしませんでした。 li_result = rte_1.InsertDocument(ls_path, TRUE) IF li_result = 1 THEN // 文書が正常に開かれました。 // 保存して、ファイル名を表示します。 is_filename = ls_path st_filename.Text = is_filename // 保存して、文書の変更状況を表示します。 rte_1.Modified = FALSE cbx_modified.Checked = rte_1.Modified ELSE MessageBox(" エラー ", " ファイルが開かれていません ") END IF END IF RETURN 0 298 PowerBuilder 第 16 章 文書を保存するための スクリプト リッチテキストの作成方法 エンド ユーザが文書を保存できるように、 [上書き保存]ボタンと[名 前を付けて保存]ボタンを用意します。また、必要に応じてメニュー 項目も作成し、同じスクリプトを記述します。 [上書き保存]ボタンの スクリプトでは、インスタンス変数 is_filename に正しいファイル名が 保持されているかどうかをチェックします。正しいファイル名であっ た場合は、of_save 関数へそのファイル名を渡します。無効なファイル 名の場合は、[名前を付けて保存]ボタンの Clicked イベントのスクリ プトを起動します。 integer li_result string ls_name // ファイル名が無効な場合は、ファイル名を取得します。 IF is_filename = " タイトル未設定 " THEN cb_saveas.EVENT Clicked() ELSE li_result = Parent.of_save(is_filename) END IF RETURN 0 FileExists イベントが起動された時に、ファイルの上書きの確認メッ セージを表示するために、[名前を付けて保存]ボタンの Clicked イベ ントのスクリプトで、インスタンス変数 ib_saveas に TRUE を設定しま す。このスクリプトでは、of_save 関数にファイル名を渡す前に、ファ イル名を取得するために of_getfilename 関数を呼びます。 integer li_result string ls_name ib_saveas = TRUE ls_name = Parent.of_getfilename() // エンド ユーザがキャンセルをしたか、エラーが発生した場合は、 // 中断させます。 IF ls_name = "" THEN RETURN -1 li_result = Parent.of_save(ls_name) ib_saveas = FALSE RETURN 0 ファイル名の保存と取 得を行う関数 of_save 関数は、ファイル名を引数として受け取り、その ファイルに文書を保存します。また、保存したファイル名をインスタ ンス変数 is_filename に設定し、SaveDocument 関数を正常に呼び出せた 後は、自動的に FALSE に設定される Modified プロパティに対応するよ うに、 [変更]チェックボックスの値を設定します。 of_save 関数 アプリケーション テクニック 299 リッチテキスト エディット コントロールの使い方 integer li_result MessageBox(" ファイル名 ", as_name) // 拡張子が正しい種類の保存を起動するので、 // ファイルの種類は必要ありません。 li_result = rte_1.SaveDocument(as_name) IF li_result = -1 THEN MessageBox(" 警告 ", " ファイルは保存されませんでした ") RETURN -1 ELSE // ファイルが正常に保存された場合。 is_filename = as_name st_filename.Text = is_filename cbx_modified.Checked = rte_1.Modified RETURN 1 END IF of_getfilename 関数 of_getfilename 関数では、エンド ユーザに対して ファイル名を入力するためのプロンプトを表示し、ユーザの選択した ファイル名を戻します。この関数は、ファイル名がまだ指定されてい ない場合、またはエンド ユーザが[名前を付けて保存]ボタンを選択 した場合に呼ばれます。 integer li_answer string ls_name, ls_path li_answer = GetFileSaveName(" 文書名 ", ls_path, & ls_name, "rtf", & "Rich Text(*.RTF),*.RTF, Text files(*.TXT),*.TXT") IF li_answer = 1 THEN // 指定したファイル名を戻します。 RETURN ls_path ELSE RETURN "" END IF 保存して閉じるための イベント エンド ユーザが指定したファイルが既に存在して いる場合に、警告メッセージを表示し、保存の取り消しができるよう にします。SaveDocument 関数がファイルを保存しようとして、ファイ ルが既に存在している場合に、FileExists イベントが起動されます。こ のスクリプトでは、変数 ib_saveas が TRUE かどうかを確認し、TRUE の場合はファイルの上書きを問い合わせます。 FileExists イベント integer li_answer 300 PowerBuilder 第 16 章 リッチテキストの作成方法 // 現行のファイルを上書き保存する場合は、 // ファイルの上書きを確認するプロンプトは表示されません。 IF ib_saveas = FALSE THEN RETURN 0 li_answer = MessageBox(" ファイルが存在 ", & filename + " はすでに存在します。上書きしますか ?", & Exclamation!, YesNo!) // ゼロでない値を戻せば、保存がキャンセルされます。 IF li_answer = 2 THEN RETURN 1 Modified イベント [変更] チェックボックスに値を設定し、エンド ユー ザに、文書の変更が保存されていないことを表示します。Modified プ ロパティは、Modified イベントが起動されたときに自動的に設定され ます。リッチテキスト エディット コントロールの文書が変更されたと きに、Modified イベントが起動されます。 cbx_modified.Checked = TRUE CloseQuery イベント 保存されていない変更があるかどうかをチェッ クして、ウィンドウを閉じる前に文書の保存を確認するメッセージ ボックスを表示します。 integer li_answer // 保存されていない変更があるかどうか。なければ、終了します。 IF rte_1.Modified = FALSE THEN RETURN 0 // 文書の保存の確認を、エンド ユーザに求めます。 li_answer = MessageBox(" 文書が保存されていません ", & " 次の文書を保存しますか ?" + is_filename, & Exclamation!, YesNo! ) IF li_answer = 1 THEN // エンド ユーザが、文書を保存する場合 // [上書き保存]ボタンの Clicked イベントを起動します。 cb_save.EVENT Clicked() END IF RETURN 0 アプリケーション テクニック 301 リッチテキスト エディット コントロールの使い方 ActiveX スペル チェック コントロールの使用 ActiveX コントロールをリッチテキスト エディット コントロール内の テキストをスペル チェックするために使用することができます。サ ポートする ActiveX スペル チェック コントロールは、ComponentOne の VSSpell および Wintertree Software の WSpell です。 リッチテキスト エディット コントロールの SelectedStartPos プロパ ティおよび SelectedTextLength プロパティを使用して、サポートする ActiveX スペル チェック コントロールで解析しているテキスト文字列 内でスペルが違う単語の位置をハイライト表示することができます。 次の手順では、ActiveX コントロールを使用して、リッチテキスト エ ディット コントロールの現行領域のテキスト全体をスペル チェック します。 ❖ リッチテキスト エディット コントロール内の選択テキストをスペル チェッ クするには 1 リッチテキスト エディット コントロールを持つウィンドウで、 ウィンドウ メニューから[挿入|コントロール| OLE]を選択し ます。 2 オブジェクトの挿入 ダイアログボックスの[コントロールの挿入] タブをクリックして、インストールされている ActiveX スペル チェック コントロールを選択して、[OK]をクリックします。 3 ウィンドウ ペインタのウィンドウ内をクリックして、ActiveX コ ントロールを挿入します。 デフォルトでは、挿入されたコントロールの名前は ole_n で、ウィ ンドウにほかの OLE コントロールがない場合は、n は 1 になりま す。 4 現行ウィンドウに関連するメニューにメニュー項目を追加し、そ のテキスト ラベルを「スペル チェック」に変更します。 5 次のコードをメニュー項目の Clicked イベントに追加します。 windowName は、リッチテキスト エディットと ActiveX コントロー ルを含むウィンドウの名前になります。 string ls_selected // 現領域のコンテキストを取得し、選択モードのままにする windowName.rte_1.selecttext(0,0,0,0) windowName.rte_1.SelectTextAll() ls_selected = windowName.rte_1.SelectedText() windowName.rte_1.SelectedTextLength = 0 // 文字列の内容を ActiveX コントロールに割り当てる windowName.ole_1.object.text = ls_selected 302 PowerBuilder 第 16 章 リッチテキストの作成方法 windowName.ole_1.object.start() 6 ウィンドウ ペインタで ActiveX コントロールを選択し、コント ロールのイベント リストから ReplaceWord を選択します。 7 次のコードを ReplaceWord イベント スクリプトに追加します。 string str str = this.object.MisspelledWord rte_1.SelectedStartPos = this.object.WordOffset rte_1.SelectedTextLength = Len(str) rte_1.ReplaceText(this.object.ReplacementWord) messagebox("misspelled word", "replaced") 次にアプリケーションを実行するときに、「スペル チェック」メ ニュー項目をクリックして、リッチテキスト エディット コント ロールの現領域の内容全体をスペル チェックすることができま す。 リッチテキストの書式設定 リッチテキスト コントロールには、ユーザがアドレス指定可能なオブ ジェクトがいくつか存在します。 • 文書(リッチテキスト データウィンドウ)全体 • 選択されたテキストと段落 • 入力フィールド • ピクチャ エンド ユーザは上記のオブジェクトを選択したり、ツールバーを使用 したり、プロパティ シートを表示させたりすることができます。 開発者またはエンドユーザが入力フィールドにデータを入力したり、 DataSource を呼び出してコントロールをデータウィンドウ オブジェク トまたはデータストアに関連付けたりすることによって、入力フィー ルドは値を取得します。 アプリケーション テクニック 303 リッチテキスト エディット コントロールの使い方 入力フィールド 入力フィールドは、名前付きの値です。入力フィールドは、名前を付 けて、値を設定して使用します。値は、入力フィールド名に関連付け られます。入力フィールドがコピーされていて、同じ名前の入力フィー ルドが複数ある場合、すべての入力フィールドに同じ値が表示されま す。また、エンド ユーザが入力フィールドの値を変更すると、その変 更は、同じ名前のすべての入力フィールドに反映されます。 以下のサンプル テキストでは、入力フィールド customer をコピーして 3 箇所で使用しています。 {customer} 様 {customer} 様からご注文いただいた品が入荷されております。ま た、30 日からセールが始まりますので、{customer} 様のお知り合 いにもお声をおかけください。 スクリプトで、入力フィールド customer にデータ値を設定することが できます。 rte_1.InputFieldChangeData("customer", " 本田 ") テキストは、以下のように表示されます。 本田様 本田様からご注文いただいた品が入荷されております。また、30 日からセールが始まりますので、本田様のお知り合いにもお声を おかけください。 さらに、エンド ユーザも、データ値を設定することができます。以下 のいずれかの方法を使用します。 • 入力フィールドを選択して、新しいデータ値を入力します。 • 入力フィールド オブジェクト プロパティ シートを表示して、[全 般]タブ ページの[データ値]テキストボックスを編集します。 スクリプトで入力フィールドを挿入 InputFieldInsert 関数は、挿入ポイント に入力フィールドを挿入します。 rtn = rte_1.InputFieldInsert("datafield") たとえば、リッチテキスト編集アプリケーションで、エンド ユーザに 入力フィールドを挿入させるとします。この場合、エンド ユーザに入 力フィールド名を指定させる方法が必要です。 たとえば、エンド ユーザに、リストボックスから入力フィールド名を 選択させるとします。以下のスクリプトは、選択された入力フィール ド名を使用して、挿入ポイントに入力フィールドを挿入します。 string ls_field 304 PowerBuilder 第 16 章 リッチテキストの作成方法 integer rtn ls_field = lb_fields.SelectedItem() IF ls_field <> "" THEN rtn = rte_1.InputFieldInsert( ls_field ) IF rtn = -1 THEN MessageBox(" エラー ", " フィールドを挿入できません ") END IF ELSE MessageBox(" 未選択 ", & " フィールド名を選択してください ") END IF 日付とページ番号のた めの入力フィールド ❖ 日付やページ番号を入れて文書を印刷するには、入力フィールドを定 義して、その入力フィールドに日付やページ番号を設定します。 文書に日付を入れるには 1 テキスト中に入力フィールドを作成し、入力フィールド名を指定 します。 2 ウィンドウの Open イベントなどで、入力フィールドのデータ値に 今日の日付を設定します。 たとえば、本文に入力フィールド today が含まれている場合、入力 フィールドにデータ値を設定するスクリプトは、以下のように記述し ます。 integer li_rtn li_rtn = rte_1.InputFieldChangeData( "today", & String(Today()) ) 印刷時にページ番号を設定する方法については、308 ページの「プレ ビューと印刷」を参照してください。 データベースのデータの使い方 リッチテキスト エディット コントロールを、データウィンドウ コン トロールまたはデータストア オブジェクトと関連付けることができ ます。入力フィールド名が、データウィンドウ オブジェクトのカラム 名または計算フィールド名と一致する場合、入力フィールドはその同 じカラム名のデータを表示します。 アプリケーション テクニック 305 リッチテキスト エディット コントロールの使い方 リッチテキスト エディット コントロールにデータ ソースがあるかな いかにかかわらず、リッチテキストの内容は常に 1 つです。つまり、 文書テンプレートとしてリッチテキスト エディット コントロールの 内容を表示することができます。行から行へスクロールしているとき は、入力フィールドのデータ値だけが変更されます。 データウィンドウ オブジェクトまたはデータストア オブジェクトと データを共有するには、DataSource 関数を使用します。 rte_1.DataSource(ds_empdata) データを共有する例 データストア オブジェクト ds_empdata に関連付けられているデータ ウィンドウ オブジェクトに 4 つのカラム emp_id、 emp_lname、 emp_fname、 state があり、 リッチテキスト エディット コントロールには以下のよう なテキストと入力フィールドがあるとします。 従業員テーブルのカラムを含むサンプル ID: {emp_id} {emp_lname} {emp_fname} 様 : 当社の新工場が福島県に開かれます。あなたが {state} から福島県に転 勤を希望する場合は、会社がすべての経費をカバーします。 行とページの操作 リッチテキスト エディット コントロールでは、エンド ユーザはペー ジ単位で文書をスクロールすることができます。ページ単位ではなく 行単位でスクロールさせるには、そのためのコマンドボタンを追加し、 スクリプトを記述しなければなりません。 [前の行へ移動]ボタンと[次の行へ移動]ボタンを追加する必要があ ります。スクリプトは簡単です。 [次の行へ移動]ボタンでは、以下の ように記述します。 rte_1.ScrollNextRow() [前の行へ移動]ボタンでは、以下のように記述します。 rte_1.ScrollPriorRow() ページ ボタンを用意することもできます。エンド ユーザが最終ページ で次ページへスクロールすると、先頭ページの次の行に対応するデー タ値を表示します。 rte_1.ScrollNextPage() 306 PowerBuilder 第 16 章 リッチテキストの作成方法 リッチテキスト エディット コントロールにおけるカーソル位置 関数を使用して、リッチテキスト エディット コントロールで選択され ている項目を取得したり、テキストを選択したりすることができます。 挿入ポイントの位置と 選択されている内容の 判定 テキストには常に挿入ポイントがあり、挿入ポイントが、選択された テキストを含むこともあります。テキストが選択されている場合、挿 入ポイントの位置は選択範囲の先頭または最後になります。テキスト を前から後ろへドラッグして選択した場合、挿入ポイントは選択範囲 の最後にあります。テキストを後ろから前へドラッグして選択した場 合、挿入ポイントは選択範囲の先頭にあります。 Position 関数は、テキストの選択範囲と挿入ポイントに関する情報を提 供します。 Position 関数についての詳細は『PowerScript リファレンス』マニュア ルを参照してください。 カーソル イメージの 変更 リッチテキスト オブジェクト プロパティ シートの[ポインタ]ペー ジには、リッチテキスト エディット コントロールまたはリッチテキス ト データウィンドウ内のカーソル位置を示すために使用できる組み 込みポインタのリスト ボックスがあります。エンド ユーザは、リッチ テキスト オブジェクト プロパティ シートでこれらのポインタの 1 つ を選択し、 [OK]をクリックして、実行時にカーソル イメージを変更 することができます。 プログラムによるテキ ストの選択 以下の関数を使用して、挿入ポイントの位置から相対的にテキストを 選択することができます。 • SelectTextWord 関数 • SelectTextLine 関数 • SelectTextAll 関数 最も一般的なテキスト選択の関数は、SelectText 関数です。テキストの 選択範囲を、最初と最後の行番号と文字番号で指定します。 SelectText 関数へ値を渡す Position 関数で得られる値は、テキストの選 択範囲だけではないので、その値を直接 SelectText 関数に渡すことはで きません。特に、ゼロは選択範囲を示すには意味がありますが、テキ スト選択には有効な値ではありません。 Position 関数についての詳細は『PowerScript リファレンス』マニュア ルを参照してください。 スペルチェックのために、1 つずつ単語を選択したい場合は、 『PowerScript リファレンス』マニュアルの SelectTextWord 関数を参照してください。 アプリケーション テクニック 307 リッチテキスト エディット コントロールの使い方 タブ順序、フォーカ ス、選択 ウィンドウまたはユーザ オブジェクトで、リッチテキスト エディット コントロールをコントロールのタブ順序に含めます。ただ し、リッチテキスト エディット コントロールにタブ移動した場合、 〔Tab〕を押すたびにテキストの中にタブを挿入してしまいます。リッ チテキスト コントロールから別のコントロールへは、タブ移動できま せん。その点に注意してください。 タブ順序 フォーカスとテキストの選択 リッチテキスト エディット コントロール を〔Tab〕を押して選択すると、コントロールがフォーカスされ、現行 の挿入ポイントまたはテキスト選択は保持されます。リッチテキスト エディット コントロールを選択してフォーカスを設定した場合は、挿 入ポイントはエンド ユーザがクリックした位置に移動します。 LoseFocus イベント エンド ユーザがリッチテキスト エディット コン トロールのツールバーを選択すると LoseFocus イベントが発生します が、リッチテキスト エディット コントロールのフォーカスは残りま す。コントロールがフォーカスを失ったかどうかを GetFocus 関数で確 認することができます。 プレビューと印刷 エンド ユーザは、リッチテキスト エディット コントロールのレイア ウトをプレビューしたり、内容を印刷したりすることができます。印 刷プレビュー モードでは、コントロールの大きさに合わせて文書の内 容が縮小されます。コントロールが小さい場合は、プレビューはとて も小さくなります。印刷プレビュー モードでコントロールを表示する 前に印刷余白やページ サイズを設定する必要があります。 印刷プレビュー モードにするには、以下のいずれかの操作を行いま す。 • エンド ユーザは、〔Ctrl〕+〔F2〕を押すことによって、編集モー ドと印刷プレビュー モードを切り換えることができます。 • スクリプトで Preview 関数を呼び出します。 rte_1.Preview(TRUE) 印刷プレビュー モードでは、上下の矢印キーおよび〔Page Up〕と〔Page Down〕を使ってコントロールのコンテンツ ページを操作できます。 308 PowerBuilder 第 16 章 印刷余白の調整 リッチテキストの作成方法 デザイン時にページ余白を設定するか、リッチテキスト コントロール のヘッダおよびフッタを有効にすると、アプリケーション ユーザは実 行時にコントロールの余白を調整することができます。ユーザは、リッ チテキスト コントロールのプロパティ シートの[印刷の仕様]タブを 開いて上下左右の余白を変更したり、PowerScript コードで余白を変更 するイベントを起動して、余白を調整したりすることができます。リッ チテキスト オブジェクト ダイアログボックスでの余白の調整は、印刷 プレビュー モードでのリッチテキスト エディット コントロールの内 容の表示にも影響します。 デザイン時にページ余白を設定しないか、それらを 0 のままにした場 合、ユーザが実行時に行う余白の変更は、印刷プレビュー モードでの み見ることができます。 ページ サイズと紙の方向の設定 デザイン時にデフォルトのページ サイズと印刷の向きを設定するこ とはできません。しかし、ユーザは実行時にリッチテキスト オブジェ クト ダイアログボックスの[印刷の仕様]タブでこれらのプロパティ を設定することができます。このダイアログボックスは標準ビューで のみ使用できます。アプリケーション ユーザがこのダイアログボック スを表示できるようにするには、リッチテキスト エディット コント ロールのポップアップ メニューを有効にする必要があります。 アプリケーション テクニック 309 リッチテキスト エディット コントロールの使い方 印刷 リッチテキスト エディット コントロールがデータウィンドウ オブ ジェクトのデータを使用している場合、データウィンドウ コントロー ルの Print.Page.Range プロパティを設定して、印刷される行の数を制限 することができます。Print.Page.Range プロパティの値は、印刷する ページ番号をリストした文字列です。ダッシュ(-)を使用して範囲を 指定できます。 ページ範囲の例 たとえば、リッチテキスト エディット コントロール が、データウィンドウ コントロール dw_source のデータを共有してい るとします。リッチテキスト文書は 3 ページで、2 行目と 5 行目のデー タを印刷するとします。印刷する前に、ページ範囲のプロパティを設 定することができます。 dw_source.Object.DataWindow.Print.Page.Range = & "4-6,13-15" さらに、行が印刷されないように、行をフィルタまたは破棄すること ができます。 詳細については、『PowerScript リファレンス』マニュアルの SetFilter、 Filter、RowsMove、RowsDiscard 関数および『データウィンドウ リファ レンス』マニュアルの Print データウィンドウ オブジェクト プロパ ティを参照してください。 ページ番号の設定 ページ番号を印刷するために、ヘッダまたはフッタの入力フィールド を使用することができます。ページ番号フィールドは文字列式または 数値式であることができますが、ヘッダまたはフッタにページ番号 フィールドを挿入するときは、文字列式のみ使用できます。たとえば、 ヘッダまたはフッタの入力フィールドで page()*2 を使用すると、コン トロールまたはレポートは、数値式の値に対して誤った結果を表示す る可能性があります。けれども、以下の文字列式は正しいページ番号 とページ数を表示します。 'Page ' + page() + ' of ' + pageCount()) スクリプトによるフッ タ テキストの挿入 以下のサンプル コードでは、フッタに挿入ポイントを設定して、2 つ の空白行、テキスト、そして 2 つの入力フィールドを挿入しています。 rte_1.SelectText(1, 1, 0, 0, Footer!) rte_1.ReplaceText("~r~n~r~nRow ") rte_1.InputFieldInsert("row") rte_1.ReplaceText(" Page ") rte_1.InputFieldInsert("page") rte_1.SetAlignment(Center!) 310 PowerBuilder 第 16 章 リッチテキストの作成方法 リッチテキストとエンド ユーザ PowerBuilder の『ユーザーズ ガイド』マニュアルのリッチテキストの 使い方に関する章、およびこの章で解説した編集ツールは、エンド ユーザも使用することができます。 エンド ユーザが行え る操作 エンド ユーザが可能 な操作のスクリプトで の記述 エンド ユーザは、以下の操作を行うことができます。 • ツールバーを使用したテキストの書式設定 • ポップアップ メニューの使用(ほかのリッチテキストや ASCII ファイルを開いたり、クリップボードを使用したりできます) • 入力フィールドの内容の編集 • 編集ツールのオン / オフの切り換え エンド ユーザが以下の操作をできるように、アプリケーションを設定 することができます。 • 入力フィールドの挿入と削除 • ピクチャの挿入 • ヘッダとフッタ編集への切り換え • 印刷する文書のプレビュー リッチテキスト エディット コントロールが、データウィンドウ オブ ジェクトまたはデータストア オブジェクトとデータを共有する場合、 以下のようにスクリプトを記述することができます。 • 行から行へスクロールさせる(ページからページへスクロールさ せるスクリプトも記述できますが、その必要はありません) • 入力フィールドで変更されたデータ値をデータベースへ更新する リッチテキストを使用するアプリケーションを作成する際には、開発 者自身がエンド ユーザとなってアプリケーションを使用し、テキスト を編集してみることをお勧めします。実行時にも、編集用のすべての ツールを使用することができます。 エンド ユーザへの表 示 デフォルトの表示は本文テキストです。ヘッダとフッタのテキストお よび印刷プレビューも表示できます。 リッチテキスト データウィンドウ オブジェクトまた はリッチテキスト エディット コントロールにおいて、メニューまたは コマンドボタンのスクリプトで ShowHeadFoot 関数を呼ぶことができ ます。ヘッダ編集パネルを表示するには、以下の関数を呼び出します。 ヘッダとフッタ dw_1.ShowHeadFoot(TRUE) アプリケーション テクニック 311 リッチテキストとエンド ユーザ フッタ編集パネルを表示するには、以下の関数を呼び出します。 dw_1.ShowHeadFoot(TRUE, FALSE) フッタに現行のページ番号を挿入する 以下のスクリプトは、フッタに現行のページ番号を挿入し、リッチ テ キスト コントロールの文書の本文にフォーカスを戻します。 rte_1.ShowHeadFoot(true,false) rte_1.SetAlignment ( Center! ) rte_1.InputFieldInsert("PAGENO") rte_1.ShowHeadFoot(false,false) 多重定義関数 ShowHeadFoot では、2 番目の引数の値が指定されない と、デフォルトで TRUE になります。通常の表示に戻すには、再度 ShowHeadFoot 関数を呼び出します。 dw_1.ShowHeadFoot(FALSE) 〔Ctrl〕+〔F2〕を押すことによって、 印刷プレビュー エンド ユーザは、 印刷プレビュー モードのオンとオフを切り換えることができます。ま た、スクリプトから印刷プレビュー モードを制御することもできま す。 リッチテキスト エディット コントロールでは、Preview 関数を呼び出 します。 rte_1.Preview(TRUE) リッチテキスト データウィンドウ オブジェクトでは、Preview プロパ ティを設定します。 dw_1.Object.DataWindow.Print.Preview = TRUE エンド ユーザは、以下の項目に対して書式設定をすることができま す。 テキストの構成要素と 書式設定 ❖ • 選択されたテキスト • 段落 • ピクチャ • リッチテキスト文書全体 オブジェクトのプロパティ シートを表示するには 1 312 以下の操作を行って、オブジェクトを選択します。たとえば、次 のようになります。 PowerBuilder 第 16 章 2 ❖ • ドラッグするか、または編集キーを使用してテキストを選択し ます。 • ピクチャをクリックします。 • リッチテキスト文書に挿入ポイントを設定します(テキストを 選択しないように注意してください)。 ワークスペースで右クリックして、ポップアップ メニューから[プ ロパティ]を選択します。 選択された段落に書式を設定するには • 入力フィールドの値の 変更 リッチテキストの作成方法 ルーラをダブルクリックします。 または 〔Ctrl〕+〔Shift〕+〔S〕を押します。 リッチテキスト オブジェクトを編集禁止に設定していない限り、エン ド ユーザは入力フィールドの値を変更できます。 ❖ 入力フィールドの値を変更するには 1 入力フィールドをクリックして選択します。 2 ワークスペースで右クリックして、ポップアップ メニューから[プ ロパティ]を選択します。 入力フィールド オブジェクト プロパティ シートが表示されます。 3 [全般]ページの[データ値]テキストボックスを編集します。 入力フィールドに書式を設 定することができます。入力フィールドを選択している場合は、入力 フィールド オブジェクト プロパティ シートの[フォント]ページと ツールバーによって書式を設定することができます。テキストととも に入力フィールドを選択している場合は、書式設定は、入力フィール ドを含むすべてのテキストに反映されます。 入力フィールドにおけるデータ値の書式設定 エンド ユーザは、入力フィールドの個々の文字または単語に書式を設 定することはできません。入力フィールドを選択すると、入力フィー ルド全体が選択されます。 スクリプトを記述して、エンド ユーザに 入力フィールドを挿入させたり削除させたりすることができます。ま た、エンド ユーザは、既存の入力フィールドをコピーして貼り付ける こともできます。コピーされた入力フィールドは、すべて同じデータ 値を表示します。 入力フィールドの挿入と削除 アプリケーション テクニック 313 リッチテキストとエンド ユーザ 書式設定のためのキー とツールバー ツールバーが表示されている場合、エンド ユーザはツールバーのボタ ンを使用してテキストの書式を設定したり、指定済みのショートカッ ト キーを使用してリッチテキスト エディット コントロール内のテキ ストの書式を設定したりできます。 リッチテキストにおける書式設定のためのショートカット キーにつ いては、PowerBuilder の『ユーザーズ ガイド』マニュアルのリッチテ キストに関する章を参照してください。 314 PowerBuilder 第 1 7 章 データ ソース間のデータ転送 この章について この章では、アプリケーションでパイプライン オブジェクトを使 用して、1 つまたは複数の転送元テーブルから新規または既存の転 送先テーブルへデータ パイプライン処理を行う方法について説明 します。 内容 サンプル アプリケーショ ン 項目 データ パイプラインについて 必要なオブジェクトの作成 パイプライン処理の前準備 パイプライン処理の開始 エラー行の処理 パイプラインの後処理 ページ 316 317 325 328 335 339 この章では、簡単な商品受注管理システムを使ってデータ パイプ ラインの使い方を説明します。データ パイプライン処理の参考例 として、Code Examples サンプル アプリケーションのデータ パイ プライン項目にあるサンプルを参照してください。 サンプル アプリケーションの使い方についての詳細は、第 1 章「サ ンプル アプリケーションの使い方」を参照してください。 アプリケーション テクニック 315 データ パイプラインについて データ パイプラインについて データ パイプラインとは、データベース テーブル間でデータを転送で きる機能です。データ パイプライン機能によって、1 つまたは複数の 転送元テーブルから、新規または既存の転送先テーブルに行をコピー できます。また、この機能によって、同一のデータベース内、複数の データベース間、または異なる DBMS 間においてもデータを移行でき ます。 データ パイプライン 処理の用途 データ パイプライン処理は、以下の 2 種類の用途で使用されます。 • 開発時のユーティリティとして PowerBuilder 開発環境での作業中に、データを移行したいことがあ ります(運用時に使用する大きなテーブルからテスト用に小さな テーブルを作成するときなど)。この場合、データ パイプライン ペインタで対話的に作業を行って、すぐにデータを移行できます。 データ パイプライン ペインタの開発環境での使い方についての 詳細は、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照 してください。 • アプリケーションにおけるデータ移行ツールとして実装するには 複数のテーブル間でデータの移行を必要とするようなアプリケー ションを構築している場合は、データ パイプライン ペインタで適 切なデータ パイプラインを設計し、パイプラインオブジェクトを 保存しておきます。これにより、アプリケーション実行時に、エ ンド ユーザにそのデータ パイプライン処理を行わせることがで きます。 データ パイプラインは、アプリケーションのさまざまな局面で利 用できます。たとえば、アプリケーションで、データベース サー バからテーブルのローカル コピーをリモート ユーザにダウン ロードさせる場合や、分散しているトランザクション テーブルの データをマスタ トランザクション テーブルにまとめる場合など です。 基本操作の概要 アプリケーションにデータ パイプラインを使用する必要がある場合 は、そのための手順を決定しなければなりません。通常は、以下の 5 段階の基本操作を行います。 ❖ 316 アプリケーションでデータ パイプライン処理を行うには 1 パイプライン、ユーザ オブジェクト、ウィンドウなど、必要なオ ブジェクトを作成します。 2 パイプライン処理の準備を行います。 PowerBuilder 第 17 章 3 パイプライン処理を開始します。 4 エラーとなった行を処理します。 5 パイプラインの後処理をします。 データ ソース間のデータ転送 本章の後半は、以上の各操作の詳細について説明します。 必要なオブジェクトの作成 アプリケーションでデータのパイプライン処理を実装するには、以下 の種類のオブジェクトを作成する必要があります。 • パイプライン オブジェクト • ユーザ オブジェクト • ウィンドウ パイプライン オブジェクトの作成 パイプライン オブジェクトを作成して、アプリケーションで実行した いパイプラインのデータ定義やアクセス情報を指定します。パイプラ イン オブジェクトは、PowerBuilder のデータ パイプライン ペインタで 作成し、パイプライン処理に必要な特性を定義しておきます。 パイプラインの定義 データ パイプライン ペインタでは、以下の特性を指定してパイプライ ン オブジェクトを定義します。 • アクセスする転送元テーブルとテーブルから取得(検索)するデー タ(データソースにストアド プロシージャもアクセスできる) • データを転送する転送先テーブル • パイプライン操作(作成、置き換え、リフレッシュ、追加、更新) の実行 • パイプライン操作中に COMMIT を発行する頻度(n 行ごとの発行、 すべての行を転送した後で発行、またはコミットしない。この場 合、開発者がスクリプトで COMMIT 文を実行する必要がある) • パイプライン操作が終了するまでに許容されるエラーの件数 • (転送元データベースの PowerBuilder リポジトリから)転送先デー タベースに拡張属性を転送するかどうか アプリケーション テクニック 317 必要なオブジェクトの作成 データ パイプライン ペインタを使用してパイプライン オブジェクト を作成する方法についての詳細は、PowerBuilder の『ユーザーズ ガイ ド』マニュアルを参照してください。 例 データ パイプライン ペインタを使用して、pipe_sales_extract1 というパ イプライン オブジェクトを定義する方法を以下に示します(なお、 pipe_sales_extract1 は、商品受注管理システムの w_sales_extract ウィン ドウで使用される 2 つのパイプライン オブジェクトのうちの 1 つで す)。 転送元のデータ このパイプライン オブジェクトは、会社の販売データ ベースの社員情報(Sales-rep)テーブルと売上一覧テーブル(Salessummary)を結合して、転送元データを形成しています。転送元データ は、ある特定の四半期の行だけを検索します(アプリケーションでは、 Quarter という検索引数に割り当てられた値によって、どの四半期に関 するデータを検索するかを指定します)。 パイプライン オブジェクト pipe_sales_extract1 は、各転送元テーブルか らどのカラムを転送するかを指定しています(Sales_rep テーブルから は srep_id、srep_lname、srep_fname の各カラム、さらに、Sales_summary テーブルからは ssum_quarter、ssum_rep_team の各カラム)。また、検索 時に計算してから転送する計算カラムも定義しています。この計算カ ラムでは、Sales-summary テーブルの ssum-rep-actual カラムから ssumrep-quota カラムを減算しています。 318 PowerBuilder 第 17 章 データの転送方法 データ ソース間のデータ転送 pipe_sales_extract1 が転送元データを転送する方法を 以下に示します。 このパイプライン オブジェクトが、販売成績(Quarterly-extract)とい う転送先テーブルを新規に作成するように定義していることに注意し てください。アプリケーションで、この新規テーブルを格納する転送 先データベースを指定する方法については、 (転送元テーブルのデータ ベースを指定する方法についても)後で示します。 このほか、pipe_sales_extract1 について以下の項目に注意してください。 • コミットが発行されるのは、対象となる行がすべて転送された後 のみ(つまり、パイプラインの実行が中断されると、Quarterly_extract テーブルに対する変更内容はすべてロールバックされ破棄され る) • アプリケーションで発生するエラー件数の制限はない。したがっ て、どの行でエラーが起きても、パイプラインの実行は中断され ない • 拡張属性は、転送先データベースには転送されない • Quarterly-extract テーブルの主キーは、srep-id カラムと ssum-quarter カラムから構成される複合キーである • アプリケーション テクニック アプリケーションが Quarterly-extract テーブルに作成する計算カラ ムの名前は、computed_net である 319 必要なオブジェクトの作成 ユーザ オブジェクトの作成 ここまで、パイプライン オブジェクトにパイプラインに対するデータ やアクセスを定義する方法について説明してきましたが、パイプライ ン オブジェクトには、アプリケーションで実際にパイプラインを実行 したり管理したりする際に必要となるさまざまな定義(プロパティ、 イベント、関数など)は含まれていません。 アプリケーションでパイプライン処理を行う際に、そのアプリケー シ ョ ン で 必 要 と な る 個 別 の 定 義 を 実 装 す る に は、PowerBuilder の Pipeline システム オブジェクトを継承させたユーザ オブジェクトの作 成が必要です。表 17-1 に、実行時にアプリケーションによるオブジェ クトの管理を可能にする、Pipeline システム オブジェクトのさまざま なプロパティ、イベント、関数を示します。 Pipeline システム オ ブジェクトについて 表 17-1: Pipeline システム オブジェクトのプロパティ、イベント、関数 プロパティ DataObject、 イベント PipeStart、 RowsRead、 PipeMeter、 PipeEnd RowsWritten、 関数 Start、 Repair、 Cancel RowsInError、 Syntax アプリケーションにおけるこれらのプロパティ、イベント、関数の使 い方は、この章の後半で説明します。 ❖ パイプライン処理をサポートするユーザ オブジェクトを作成するには 1 新規作成 ダイアログボックスの[PB オブジェクト]タブから[標 準クラス]を選択します。 標準クラス データ型の選択 ダイアログボックスが表示され、新規 のユーザ オブジェクトに継承したい PowerBuilder のシステム オブ ジェクト名が指定できます。 320 PowerBuilder 第 17 章 データ ソース間のデータ転送 2 「pipeline」を選択して、[OK]ボタンを選択します。 3 必要に応じて、ユーザ オブジェクトに変更を加えます。アプリケー ションで使用するイベント、関数、変数などを記述します。 特に有効なユーザ オブジェクトの機能については、330 ページの 「パイプライン処理のモニタ」を参照してください。 再利用を考えた設計 ユーザ オブジェクトを作成する場合、そのユーザ オブジェクトが 将来再利用され、ほかのパイプライン処理の実行にも使用される ことがあることを考慮してください。ユーザ オブジェクトは、デー タ パイプライン ペインタで作成した特定のパイプライン オブ ジェクトと自動的に関連付けられるわけではなく、ほかのパイプ ライン オブジェクトに対しても使用することができます。 この柔軟性を有効に活用するためにも、ユーザ オブジェクトで記 述するイベント、関数、変数は、あらゆるパイプライン オブジェ クトに適応できるような汎用性を持たせておく必要があります。 4 ユーザ オブジェクトを保存します。 ユーザ オブジェクト ペインタでの操作手順については、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください。 ウィンドウの作成 ウィンドウは、アプリケーションでデータ パイプライン処理をすると きに必要となるもう 1 つのオブジェクトです。ウィンドウを作成して、 パイプライン処理に対するユーザ インタフェースを提供し、エンド ユーザによるさまざまなパイプライン操作を可能にします。通常のア プリケーションでは、以下のようなエンド ユーザ操作が考えられま す。 • パイプライン処理を開始する • エラー内容の表示や修正を行う • 必要に応じ、パイプライン処理の実行を中断する アプリケーション テクニック 321 必要なオブジェクトの作成 ウィンドウに必要とな る機能 ウィンドウを作成する際に、そのパイプライン処理でエラーとなった 行(何らかの理由で転送先テーブルに転送できない行)を表示するデー タウィンドウ コントロールが必要となります。このデータウィンドウ コントロールにデータウィンドウ オブジェクトを関連付ける必要は ありません。実行時にパイプラインによって独自のデータウィンドウ オブジェクトが提供されます。 このデータウィンドウ コントロールの使い方については、328 ページ の「パイプライン処理の開始」および 335 ページの「エラー行の処理」 を参照してください。 ウィンドウに対するオ プション機能 必要なデータウィンドウ コントロールさえ含めれば、ウィンドウは開 発者が自由に設計できます。通常は、以下のようなコントロールを配 置してユーザ インタフェースを実現します。 • エンド ユーザが(パイプラインの開始、修正、停止などの)操作 を行えるようにするコマンドボタン コントロールやピクチャボタ ン コントロール • パイプラインのステータス情報を表示するスタティック テキスト コントロール • 転送元テーブルや転送先テーブルの内容を表示するデータウィン ドウ コントロール ウィンドウの作成についての詳細は、PowerBuilder の『ユーザーズ ガ イド』マニュアルを参照してください。 322 PowerBuilder 第 17 章 例 データ ソース間のデータ転送 次のウィンドウは、商品受注管理システムにおけるデータ パイプライ ン処理のユーザ インタフェースを扱います。ウィンドウ名は、 w_sales_extract です。 このウィンドウ上の各コントロールは、パイプライン処理に関連した さまざまな機能を実現するために使用されています。使用されている コントロールの詳細を、表 17-2 にまとめています。 表 17-2: パイプラインの機能を実現するためのウィンドウ コントロール コントロールの 種類 ラジオボタン コントロール名 rb_create rb_insert アプリケーション テクニック 目的 実行するパイプライン オブジェクト に、pipe_sales_extract1 を選択する 実行するパイプライン オブジェクト に、pipe_sales_extract2 を選択する 323 必要なオブジェクトの作成 コントロールの 種類 コマンドボタン データウィンド ウ スタティック テキスト 324 コントロール名 cb_write 目的 選択したパイプライン処理の実行を 開始する cb_stop パイプラインの実行を停止し、行の修 正内容を破棄する cb_applyfixes (dw_pipe_errors データウィンドウ コ ントロール内で)エンド ユーザが行 に加えた修正内容で転送先テーブル を更新する cb_forgofixes dw_pipe_errors データウィンドウ コン トロールから、すべてのエラー行を削 除する(エンド ユーザが修復を希望 しないときに使用) dw_review_extract 転送先テーブル(Quarterly-extract)の 現行の内容を表示する dw_pipe_errors (必須)パイプライン自身が使用する データウィンドウ コントロール。 PowerBuilder のパイプライン エラー の内容(何らかのエラーで転送できな かった行のリスト)を自動的に表示す る st_status_read パイプラインが転送元テーブルから 読み込む行数を表示する st_status_written パイプラインが転送元テーブルに書 き込む行数や、dw_pipe_ errors データ ウィンドウの行数を表示する st_status_error st_status_error パイプラインが dw_pipe_ errors データウィンドウに渡 した行数(エラーとなった行数)を 表示する PowerBuilder 第 17 章 データ ソース間のデータ転送 パイプライン処理の前準備 アプリケーションで必要となるオブジェクトの準備ができたら、アプ リケーションでパイプライン処理を行うスクリプトを記述します。ま ず、アプリケーションがパイプライン処理を実行できるように、いく つかの設定を行わなければなりません。 ❖ アプリケーションでパイプラインを実行するための準備をするには 1 パイプラインに用いる転送元および転送先データベースに接続し ます。 これは、適切なイベントにおいて、接続のための一般的なスクリ プトを記述して行います。ただし、転送元データベースに接続す る際に使用するトランザクション オブジェクトと、転送先データ ベースとの接続に使用するトランザクション オブジェクトは、 (同 一のデータベースの場合でも)異なることに注意してください。 データベースへの接続についての詳細は、第 12 章「トランザク ション オブジェクトの使い方」を参照してください。 2 ユーザ オブジェクトのインスタンスを作成します(インスタンス を作成することにより、アプリケーションでユーザ オブジェクト のプロパティ、イベント、関数が使用できるようになります)。 最初に、定義したユーザ オブジェクトをデータ型とする変数を宣 言します。次に、スクリプトで CREATE 文を使って、ユーザ オブ ジェクトのインスタンスを作成し、それを変数に代入します。 3 使用したいパイプライン オブジェクトを指定します。 これは、スクリプトで代入文を記述して行います。使用するパイプ ライン オブジェクト名を示す文字列を、ユーザ オブジェクトのイ ンスタンスの DataObject プロパティに代入します。 CREATE 文および代入文についての詳細は、 『PowerScript リファレンス』 マニュアルを参照してください。 例 次のサンプル コードは、商品受注管理システムにおけるこれらのパイ プラインの設定を行います。 転送元および転送先データベースとの接続 この場合は、会社の販売デー タベース(ABNCSALE.DB)を、転送元および転送先の両方のデータ ベースとして使用しています。この販売データベースとの接続は、 uevent_pipe_setup というユーザ イベントにスクリプトを記述して行っ ています(uevent_pipe_setup イベントは、w_sales_extract ウィンドウの Open イベントからポストされます)。 アプリケーション テクニック 325 パイプライン処理の前準備 以下のスクリプトは、転送元データベースとの接続を確立します。 // トランザクション オブジェクトのインスタンスを新規に作成し、 // itrans_source(あらかじめ Transaction データ型 // として宣言した変数)に保持します。 itrans_source = CREATE transaction // 次に、トランザクション オブジェクト itrans_destination の // プロパティに値を代入します。 ... // 転送元データベースに接続します。 CONNECT USING itrans_source; 以下のスクリプトは、転送先データベースとの接続を確立します。 // トランザクション オブジェクトのインスタンスを新規に作成し、 // itrans_destination(あらかじめ Transaction データ型 // として宣言した変数)に保持します。 itrans_destination = CREATE transaction // 次に、トランザクション オブジェクト itrans_destination の // プロパティに値を代入します。 ... // 転送先データベースに接続します。 CONNECT USING itrans_destination; ネイティブ ドライバの USERID 設定 ネイティブ ドライバを使用している場合に、パイプライン ペインタで パイプラインを実行すると、PowerBuilder は、テーブルのオーナー名 でテーブル名を自動的に修飾します。ネイティブ ドライバを使用して いる場合に、アプリケーションでパイプラインを実行するときは、テー ブル名が正しく修飾されるように、トランザクション オブジェクトで USERID プロパティを設定しなければなりません。 転送先データベースのトランザクション オブジェクトで USERID プ ロパティを設定しなかった場合には、パイプラインの実行エラーが発 生します。転送元データベースがネイティブ ドライバを使用する場合 には、USERID が設定されていなければ、拡張属性は転送されません。 326 PowerBuilder 第 17 章 データ ソース間のデータ転送 ユーザ オブジェクトのインスタンスの作成 u_sales_pipe_logistics というパ イプライン処理に必要となるユーザ オブジェクトを作成する方法に ついては、すでに説明しました。このユーザ オブジェクトをアプリ ケーションで使用するには、まずそのユーザ オブジェクトをデータ型 とする変数を宣言します。 // これは w_sales_extract ウィンドウの // インスタンス変数です。 u_sales_pipe_logistics iuo_pipe_logistics 次に、ユーザ オブジェクト u_sales_pipe_logistics のインスタンスを作 成し、iuo_pipe_logistics 変数に保持するコードを、ユーザ イベント uevent_pipe_setup に記述します。 iuo_pipe_logistics = CREATE u_sales_pipe_logistics 使用するパイプライン オブジェクトの指定 このアプリケーションは、必 要とするパイプ操作の種類によって、以下のいずれかのパイプライン オブジェクトを使用しています。 • pipe_sales_extract1(前述の説明を参照)は、Quarterly-extract テーブ ルを新規に作成する(このテーブルは現時点で存在していないも のとする) • pipe_sales_extract2 は、Quarterly-extract テーブルに行を挿入する(こ のテーブルは現時点で存在しているものとする) パイプライン オブジェクトを選択し、その使用準備を行うスクリプト を、コマンドボタン cb_write の Clicked イベントに記述します(コマン ドボタンは、エンド ユーザがパイプライン処理を開始したいときにク リックします)。 // w_sales_extract ウィンドウで選択されている // ラジオボタンを確認します。次に、iuo_pipe_logistics に // 適切なパイプライン オブジェクトを代入します。 IF rb_create.checked = true THEN iuo_pipe_logistics.dataobject = "pipe_sales_extract1" ELSE iuo_pipe_logistics.dataobject = "pipe_sales_extract2" END IF このコードは、選択されたパイプラインを開始するスクリプトより前 に、通常スクリプトの先頭で記述します。 アプリケーション テクニック 327 パイプライン処理の開始 パイプライン オブジェクトを配布する際の注意 通常、アプリケーションは、実行時にパイプライン オブジェクトを (String 型の変数によって)動的に参照します。そのため、アプリケー ションを配布する場合は、これらのオブジェクトを 1 つまたは複数の PBD か DLL ファイルにパッケージ化する必要があります。なお、実行 (EXE)ファイルにパイプライン オブジェクトを含めることはできま せん。 配布についての詳細は、第 9 部「配布のテクニック」を参照してくだ さい。 パイプライン処理の開始 パイプラインの準備が整ったら、実行を開始します。 ❖ パイプライン処理を開始するには 1 適切なスクリプトに Start 関数を記述します。この関数では、以下 の内容が指定できます。 • 転送元データベースに対するトランザクション オブジェクト • 転送先データベースに対するトランザクション オブジェクト • Start 関数がエラー行を表示するデータウィンドウ コントロール Start 関数は、PowerBuilder のパイプライン エラー データウィ ンドウ オブジェクトと、使用するデータウィンドウ コント ロールを自動的に関連付けます(必要な場合のみ)。 • パイプライン オブジェクトで定義した検索引数に対する値 これらの値を省略すると、Start 関数は、アプリケーション実行 時にそれらの入力を自動的に要求します。 2 Start 関数の結果を調べます。 Start 関数の記述についての詳細は、 『PowerScript リファレンス』マニュ アルを参照してください。 328 PowerBuilder 第 17 章 例 データ ソース間のデータ転送 以下のサンプル スクリプトは、商品受注管理システムのパイプライン を開始します。 Start 関数の呼び出し 選択したパイプラインを開始する場合は、エンド ユーザに w_sales_extract ウィンドウのコマンドボタン(cb_write)を選 択させます。 cb_write コマンドボタンの Clicked イベントが起動されます(このイベ ントのスクリプトに、Start 関数が記述されています)。 // 転送を開始します。 integer li_start_result li_start_result = iuo_pipe_logistics.Start & (itrans_source,itrans_destination,dw_pipe_errors) スクリプトでは、ユーザがパイプラインの検索引数(Quarter)に対す る値を設定していません。そこで、Start 関数が、その値を入力するよ うエンド ユーザに要求します。 cb_write コマンドボタンの Clicked イベントに対する以 下のスクリプトによって、Start 関数の戻り値を調べます。これによっ て、アプリケーションで関数が正常終了したかどうか(正常終了しな かった場合は、エラーの内容)を調べることができます。 結果を調べる CHOOSE CASE li_start_result CASE -3 Beep (1) MessageBox(" 転送エラー ", & "Quarterly_Extract テーブルは既に存在しています ... RETURN アプリケーション テクニック 329 パイプライン処理の開始 CASE -4 Beep (1) MessageBox(" 転送エラー ", & "Quarterly_Extract テーブルは存在しません ... RETURN ... END CHOOSE パイプライン処理のモニタ パイプラインの実行状態をモニタするには、Start 関数の戻り値を調べ る方法があります。そのほかの方法として、ユーザ オブジェクトがパ イプライン処理された行数を保持している集計値を取得する方法もあ ります。これにより、パイプラインによって処理された以下の数値が 求められます。 • 転送元テーブルから読み込まれた行数 • 転送先テーブルおよびエラーのデータウィンドウ コントロールに 書き込まれた行数 • (転送先テーブルではなく)エラー用のデータウィンドウ コント ロールに書き込まれたエラー行の数 これらの集計値をユーザ オブジェクトから取得し、ウィンドウ上で動 的に表示して、エンド ユーザにパイプライン処理を確認させることが できます。 ❖ パイプラインによって処理された行の集計を表示するには 1 ユーザ オブジェクト ペインタで、ユーザ オブジェクトを開きま す。 ユーザ オブジェクト ペインタのワークスペースが表示され、ユー ザ オブジェクトの編集が可能になります。 2 StaticText 型の インスタンス変数を 3 種類宣言します。 statictext ist_status_read, ist_status_written, & ist_status_error これらのインスタンス変数は、今後、ウィンドウ上の 3 つのスタ ティック テキスト コントロールの内容を保持するために使用し ます。これにより、ユーザ オブジェクトでスタティック テキスト コントロールの内容を直接操作し、パイプラインによる各種の行 の集計を動的に表示できます。 330 PowerBuilder 第 17 章 3 データ ソース間のデータ転送 ユーザ オブジェクトの PipeMeter イベント スクリプトでは、Pipeline システム オブジェクトから継承したプロパティの値を、3 つのス タティック テキスト インスタンス変数のテキスト プロパティに 割り当てるステートメントを記述します。 ist_status_read.text = string(RowsRead) ist_status_written.text = string(RowsWritten) ist_status_error.text = string(RowsInError) 4 ユーザ オブジェクトに加えた変更内容を保存し、ユーザ オブジェ クト ペインタを閉じます。 5 使用するウィンドウをウィンドウ ペインタで開きます。 6 3 つのスタティック テキスト コントロールをウィンドウに挿入し ます。 RowsRead プロパティの値を表示するスタティック テキスト コントロール RowsWritten プロパティの値を表示するスタティック テキス ト コントロール RowsInError プロパティの値を表示するスタティック テキス ト コントロール 7 ウィンドウの Open イベントに対するスクリプト(または、ウィン ドウを開いた直後に実行するほかのイベントに対するスクリプ ト)を編集します。 ここでは、(ウィンドウに挿入したばかりの)3 つのスタティック テキスト コントロールを、ユーザ オブジェクトであらかじめ宣言 しておいた 3 つの対応するスタティック テキスト インスタンス変 数に割り当てるステートメントを記述します。これにより、その ユーザ オブジェクトからこれらのスタティック テキスト コント ロールを直接操作できます。 商品受注管理システムでは、このロジックを uevent_pipe_setup ユー ザ イベントに対して記述しています(このユーザ イベントは、 w_sales_extract ウィンドウの Open イベントからポストされます) 。 アプリケーション テクニック 331 パイプライン処理の開始 iuo_pipe_logistics.ist_status_read = st_status_read iuo_pipe_logistics.ist_status_written = & st_status_written iuo_pipe_logistics.ist_status_error = & st_status_error 8 ウィンドウへの変更内容を保存し、ウィンドウ ペインタを閉じま す。 商品受注管理システムの w_sales_extract ウィンドウでパイプライ ンを開始すると、ユーザ オブジェクトの PipeMeter イベントが起 動され、そのイベントのスクリプトが実行されて、パイプライン による行の集計が 3 個のスタティック テキスト コントロールに表 示されます。 パイプライン処理のキャンセル パイプラインの実行を途中で停止する機能をエンド ユーザ(またはア プリケーション)に提供したい場合が多くあります。たとえば、間違っ てパイプラインを開始したり、 (大量の行数を扱っているときに)処理 を途中で中断したりしたい場合などです。 332 PowerBuilder 第 17 章 ❖ データ ソース間のデータ転送 パイプラインの実行をキャンセルするには 1 適切なスクリプトに Cancel 関数を記述します。 Cancel 関数は、パイプラインの開始後(適切であれば) 、エンド ユー ザまたはアプリケーションのどちらからでも実行できます。Cancel 関数が実行されると、それ以降の行の転送が停止されます。 処理が中断された時点までに転送された行が転送先テーブルにコ ミットされるかどうかは、データ パイプライン ペインタでパイプ ライン オブジェクトの作成時に指定した[コミット単位]オプショ ンによって決まります。コミットについては、次節で説明します。 2 Cancel 関数の結果を調べます。 Cancel 関数の記述についての詳細は、 『PowerScript リファレンス』マ ニュアルを参照してください。 例 次の例では、エンド ユーザがコマンドボタンを使って商品受注管理シ ステムのパイプライン実行を中断します。 コマンドボタンの提供 w_sales_extract ウ ィンドウ を作成す るときに、 cb_stop というコマンドボタン コントロールを配置します。また、パイ プラインの開始時にこのコマンドボタンを使用可能にし、その終了と ともに使用不可にするコードをアプリケーションのスクリプトに記述 します。 Cancel 関数の呼び出し 次に、cb_stop コマンドボタンの Clicked イベン トに対して以下のスクリプトを記述します。このスクリプトは、Cancel 関数を呼び出し、それが正しく機能しているかどうかを調べます。 IF iuo_pipe_logistics.Cancel() = 1 THEN Beep (1) MessageBox(" パイプライン処理の状況 ", & " データ転送が(ユーザの要求によって)中断されました。") ELSE Beep (1) MessageBox(" パイプライン処理の状況 ", & " データ転送の中断時にエラーが発生しました。", & Exclamation!) END IF これらの機能は、エンド ユーザが cb_stop コマンドボタンを選択する ことによって、現在実行中のパイプラインを停止できるようにします。 アプリケーション テクニック 333 パイプライン処理の開始 更新処理のコミット パイプライン オブジェクトを実行すると、データ パイプライン ペイ ンタでの指定に従って転送先テーブルへの更新がコミットされます。 開発者は、アプリケーションのスクリプトで、このコミット処理のた めに COMMIT 文を記述する必要はありません(ただし、パイプライン オブジェクトを作成したときに、[コミット単位]オプションに[な し]を指定したときを除く)。 例 たとえば、商品受注管理システムの 2 つのパイプライン オブジェクト (pipe_sales_extract1 と pipe_sales_extract2)は、すべての行が転送された 後でコミットを行うようにデータ パイプライン ペインタで定義され ています。これにより、Start 関数(または Repair 関数)は、すべての 行が転送されてから、コミットします。 かわりに、一定量の行(10 行または 100 行など)を転送するたびに定 期的にコミットするようなパイプライン オブジェクトを定義するこ ともできます。 Cancel 関数が呼び出 された場合 アプリケーションが Cancel 関数を呼び出して、現在実行しているパイ プラインを中断した場合は、コミット処理が行われるかどうかが問題 になります。その時点でコミット処理の方法が、表 17-3 に示すように、 データ パイプライン ペインタで指定する[コミット単位]オプション によって決まります。 表 17-3: [コミット単位]オプションの値 [コミット単位] オプション の値 すべて 特定の行数(1、10、100 など) Cancel 関数の処理の内容 現行の Start 関数(または Repair 関数)によっ て、転送した行をすべてロールバックします。 中断される直前までに転送した行を、すべてコ ミットします。 これは、エラーがパイプラインの最大エラー件数に達したときに起こ るコミットやロールバックの動作と同じです(なお、最大エラー件数 はデータ パイプライン ペインタで指定します)。 パイプライン オブジェクトに対するコミットやロールバックの操作 についての詳細は、PowerBuilder の『ユーザーズ ガイド』マニュアル を参照してください。 334 PowerBuilder 第 17 章 データ ソース間のデータ転送 エラー行の処理 パイプラインの実行時に、行が転送先テーブルに書き込めない場合が あります。たとえば、転送先テーブルに転送元テーブルと同じ主キー を持つ行がある場合などです。 パイプライン エラー データウィンドウの使 い方 パイプラインは、ウィンドウ上に配置され Start 関数で指定したデータ ウィンドウ コントロールにエラーとなった行を表示します。これは、 特定のデータウィンドウ オブジェクト(PowerBuilder のパイプライン エラー データウィンドウ)とデータウィンドウ コントロールが自動的 に関連付けられて行われます。 これを商品受注管理システムで考えてみましょう。w_sales_extract ウィ ンドウでパイプラインを実行する場合、Start 関数は、すべてのエラー 行を dw_pipe_errors データウィンドウ コントロールに表示します。 dw_pipe_errors には、各行のエラーを表示するエラー メッセージ カラ ムが配置されています。 エラー メッセージを短くする パイプラインの転送先のトランザクション オブジェクトが ODBC データ ソースを指定している場合は、DBParm の MsgTerse パラメータ を設定して、データウィンドウに表示するエラー メッセージを短くす ることができます。具体的には、以下のように指定します。 MsgTerse = 'Yes' アプリケーション テクニック 335 エラー行の処理 このように指定することによって、SQLSTATE エラー番号は表示され ません。 MsgTerse DBParm についての詳細は、オンライン ヘルプを参照してく ださい。 エラー行の処理 エラー行がある場合は、それらを処理する必要があります。以下のい ずれかの操作を行います。 • エラー行の一部またはすべての修復 • エラー行の一部またはすべての破棄 エラー行の修復 ほとんどの場合は、エラーとなった行を修正して、転送先テーブルに 適用できるようにすることをお勧めします。通常、1 つまたは複数の カラム値を転送先テーブルで受け入れられるように変更して修復しま す。エラー行の修正は、エラーを表示しているデータウィンドウ コン トロール上の行を以下のいずれかの方法で編集して行います。 • エンド ユーザに編集させる(開発者がスクリプトを記述する必要 なし) • アプリケーションのスクリプトによって編集する いずれの場合も、次の操作手順で、修正した行をこのデータウィンド ウ コントロールから転送先テーブルに適用します。 ❖ 転送先テーブルに行の修正内容を適用するには 1 適切なスクリプトに Repair 関数を記述します。Repair 関数には、転 送先データベースに対する トランザクション オブジェクトを指 定します。 2 Repair 関数の結果を調べます。 Repair 関数の記述についての詳細は、 『PowerScript リファレンス』マ ニュアルを参照してください。 例 336 次の例では、エンド ユーザがデータウィンドウ コントロール dw_pipe_errors の内容を編集することで、表示されたエラー行を修正できるようにし ます。その後、修正したそれらの行を転送先テーブルに適用します。 PowerBuilder 第 17 章 データ ソース間のデータ転送 コマンドボタンの提供 w_sales_extract ウィンドウの作成時に、cb_applyfixes というコマンドボタン コントロールを配置します。また、dw_pipe_errors データウィンドウにエラー行が入力されたときに、このコマンドボタ ンを使用可能にし、エラー行がないときには使用不可にしておくコー ドをアプリケーションのスクリプトに記述します。 次に、cb_applyfixes コマンドボタンの Clicked イ ベントに対して以下のスクリプトを記述します。このスクリプトは Repair 関数を呼び出し、それが正しく機能しているかどうかを調べま す。 Repair 関数の呼び出し IF iuo_pipe_logistics.Repair(itrans_destination) & <> 1 THEN Beep (1) MessageBox(" パイプライン処理の状況 ", & " 修正しようとしたときエラーが起きました ", Exclamation!) END IF これらの機能を提供することによって、エンド ユーザが cb_applyfixes コマンドボタンをクリックすると、dw_pipe_errors データウィンドウか ら修正した行を持つ転送先テーブルを更新できるようになります。 行の修正の停止 パイプラインの実行時にエンド ユーザ(またはアプリケーション)が 転送先テーブルへの行の書き込みを中断する方法については、この章 ですでに説明しました。状況によっては、行の修正中にも同様に書き 込みを停止させることができます。 詳細については、332 ページの「パイプライン処理のキャンセル」を 参照してください。 行の修正内容のコミッ ト Repair 関数は、Start 関数と同じ方法でデータベースの更新をコミット (またはロール バック)します。 詳細については、334 ページの「更新処理のコミット」を参照してく ださい。 修正されていない行の 処理 Repair 関数の実行後、エラー行が、エラー データウィンドウ コント ロールにまだ残っていることがあります。これには、以下のような原 因が考えられます。 • エンド ユーザやアプリケーションによって修正されたにもかかわ らず、エラーがまだ直っていない場合 • エンド ユーザやアプリケーションによってエラーが修正されてい ない場合 • Cancel 関数が呼び出されたため、転送先テーブルに書き込まれな かった場合(または、停止時に、転送先テーブルからロールバッ クされた場合) アプリケーション テクニック 337 エラー行の処理 この時点でも、これらの行は、エンド ユーザやアプリケーションに よって再度修正し、Repair 関数を用いて転送先テーブルに適用するこ とができます。場合によってはこれらの行を破棄することもできます。 この方法については後述します。 エラー行の破棄 状況によっては、エラー データウィンドウ コントロールから 1 つまた は複数のエラー行を、エンド ユーザやアプリケーションによって破棄 したいことがあります。これは、修正したくないエラー行に対する有 効な措置と言えます。 表 17-4 に、エラー行の破棄を行うことができる方法を示します。 表 17-4: エラー行の破棄 破棄するエラー行 エラー データウィンドウ コントロール上の、 すべてのエラー行 エラー データウィンドウ コントロール上の、 1 つまたは複数のエラー行 使用する関数 Reset 関数 RowsDiscard 関数 これらの関数についての詳細は、 『PowerScript リファレンス』マニュ アルを参照してください。 例 次の例では、エンド ユーザが dw_pipe_errors データウィンドウ コント ロールのすべてのエラー行を破棄できるようにしています。 w_sales_extract ウィンドウの作成時に、cb_forgofixes というコマンドボタン コントロールを配置します。dw_pipe_errors デー タウィンドウにエラー行が入力されたときに、このコマンドボタンを 使用可能にし、エラー行がないときには使用不可にしておくコードを アプリケーションのスクリプトに記述します。 コマンドボタンの提供 Reset 関数の呼び出し 次に、 cb_fogofixes コマンドボタンの Clicked イベ ントに対して以下のスクリプトを記述します。このスクリプトで、 Reset 関数を呼び出します。 dw_pipe_errors.Reset() これらの機能を提供することによって、エンド ユーザが cb_forgofixes コマンドボタンを選択すると、dw_pipe_errors データウィンドウからす べてのエラー行が破棄されるようになります。 338 PowerBuilder 第 17 章 データ ソース間のデータ転送 パイプラインの後処理 アプリケーションでのパイプライン処理が終わったら、いくつかの後 処理を行わなければなりません。これらの処理には、パイプライン処 理のために取得したリソースの解放などが含まれます。 ガベージ コレクション 破棄するオブジェクトがほかで使われていないことを確認できない場 合には、リソースの後処理に DESTROY 文を使わないでください。 PowerBuilder のガベージ コレクション機能によって、参照されていな いオブジェクトは自動的に削除されます。詳細については、49 ページ の「ガベージ コレクションとメモリ管理」を参照してください。 ❖ パイプラインの後処理を行うには 1 パイプライン処理に使用したユーザ オブジェクトのインスタンス を破棄します。 適切なスクリプトに DESTROY 文を記述し、そのユーザ オブジェ クトのインスタンス変数名を指定します。 2 パイプラインの転送元データベースおよび転送先データベースと の接続を解除します。 これは、適切なスクリプトに DISCONNECT 文を 2 行記述して行い ます。一方の DISCONNECT 文では、転送元トランザクション オ ブジェクトのインスタンス変数名を、もう一方の DISCONNECT 文 では転送先トランザクション オブジェクトのインスタンス変数名 を、それぞれ指定します。 各 DISCONNECT 文の結果を調べます。 3 転送元トランザクション オブジェクトのインスタンスと転送先ト ランザクション オブジェクトのインスタンスを破棄します。 これは、適切なスクリプトに DESTROY 文を 2 行記述して行いま す。一方の DESTROY 文では、転送元トランザクション オブジェ クトのインスタンス変数名を、もう一方の DESTROY 文では転送 先トランザクション オブジェクトのインスタンス変数名を、それ ぞれ指定します。 DESTROY 文と DISCONNECT 文についての詳細は、 『PowerScript リファ レンス』マニュアルを参照してください。 例 次のコードは、w_sales_extract ウィンドウの Close イベントに対してス クリプトを記述し、パイプラインの後処理を行います。 アプリケーション テクニック 339 パイプラインの後処理 ユーザ オブジェクト インスタンスの破棄 Close イベント スクリプトの先頭 に、以下のステートメントを記述して、(iuo_pipe_logistics 変数に保持 されている)ユーザ オブジェクト u_sales_pipe_logistics のインスタンス を破棄します。 DESTROY iuo_pipe_logistics 転送元データベースとの接続の解除 次に、以下のステートメントを記述し て転送元データベースとの接続を解除し、その結果を調べて、 (itrans_source 変数に保持されている)転送元トランザクション オブジェクトのイン スタンスを破棄します。 DISCONNECT USING itrans_source; // DISCONNECT 文の結果を調べます。 IF itrans_source.SQLCode = -1 THEN Beep (1) MessageBox(" データベース接続エラー ", & " 転送元データベースとの“ & + " 接続を解除する際に問題が発生しました。" & + " テクニカルサポートまでご連絡ください。 " & + "~n~r~n~r 詳細は以下のとおりです : " + & String(itrans_source.SQLDBCode) + " " + & itrans_source.SQLErrText, Exclamation!) END IF DESTROY itrans_source 転送先データベースとの接続の解除 最後に、以下のステートメントを記 述して転送先データベースとの接続を解除し、その結果を調べて、 (itrans_destination 変数に保持されている)転送先トランザクション オ ブジェクトのインスタンスを破棄します。 DISCONNECT USING itrans_destination; // DISCONNECT 文の結果を調べます。 IF itrans_destination.SQLCode = -1 THEN Beep (1) MessageBox(" データベース接続エラー ", & " 転送先データベースとの " + & " 接続を解除にする際に問題が発生しました。 " + & " テクニカルサポートまでご連絡ください。" + & "~n~r~n~r 詳細は以下のとおりです : " + & String(itrans_destination.SQLDBCode) + " " + & itrans_destination.SQLErrText, Exclamation!) END IF DESTROY itrans_destination 340 PowerBuilder 第 5 部 プログラム アクセス テクニック 第 5 部では、PowerBuilder によるアプリケーション開発 において、プログラム アクセス機能を実現するためのテ クニックについて説明します。アプリケーションにおけ る DDE の使い方および OLE の使い方、メール対応アプ リケーションの構築、そのほかの拡張処理機能の追加な どについて説明します。 第 1 8 章 DDE の使い方 この章について この章では、PowerBuilder がサポートする DDE 機能について説明 します。 内容 項目 DDE について DDE 関数とイベント ページ 343 344 DDE について ダイナミック データ エクスチェンジ(DDE: Dynamic Data Exchange) を使用すると、2 つの Windows アプリケーション間でコマンドや データをやり取りさせて、相互に通信することができます。つま り、2 つのアプリケーションでデータを共有したり、コマンドの遠 隔実行や、エラー状態のチェックを行ったりすることができます。 PowerBuilder は DDE をサポートするために、特別な PowerScript 関 数やイベントを提供しています。これらの関数やイベントを用い ることにより、PowerBuilder アプリケーションから DDE をサポー トするほかのアプリケーションにメッセージを送信したり、ほか の DDE アプリケーションからの DDE リクエストに対して応答し たりできます。 クライアントとサーバ DDE をサポートしているアプリケーションは、クライアントまた はサーバのどちらかの役割を果たすことができます。 用語について DDE で用いるクライアントとサーバという用語は、PC やワーク ステーションのクライアント マシンがデータベース サーバにア クセスするクライアント / サーバ アーキテクチャとは関係ありま せん。 アプリケーション テクニック 343 DDE 関数とイベント クライアント アプリケーションは、DDE をサポートしているほかのア プリケーション(サーバと呼ばれる)に対してリクエストを出します。 このリクエストは、コマンド(open、close、save など)であったりデー タに対するリクエストであったりします。 サーバ アプリケーションは、クライアント アプリケーションとは逆の 機能を実行します。サーバ アプリケーションは、DDE をサポートして いるほかのアプリケーション(クライアントと呼ばれる)からのリク エストに応答します。クライアント アプリケーションの場合と同様 に、このリクエストはコマンドや特定のデータに対するリクエストで す。 PowerBuilder のアプリケーションは、DDE クライアントとしても、DDE サーバとしても機能します。 PowerBuilder では DDE クライアントおよび DDE サーバに対して特別 な組み込み関数とイベントを用意しています。コマンドやデータがク ライアントからサーバに(またはサーバからクライアントに)送られ ると、DDE 関連のイベントが起動されます。 DDE 関数とイベント 以下の表に、DDE 関連の関数とイベントを示します。関数とイベント は DDE クライアントと DDE サーバごとにそれぞれまとめられていま す。DDE サポートの詳細については、『PowerScript リファレンス』マ ニュアルを参照してください。 戻り値 DDE 関数はすべて整数値を返します。 344 PowerBuilder 第 18 章 DDE クライアント DDE の使い方 表 18-1: DDE クライアント関数 関数 動作内容 CloseChannel OpenChannel 関数で開かれた DDE サーバ アプリケー ExecRemote GetDataDDE GetDataDDEOrigin GetRemote OpenChannel RespondRemote SetRemote StartHotLink StopHotLink ションへのチャネルを閉じる DDE サーバ アプリケーションにコマンドを実行する よう要求する ホットリンクされている DDE サーバ アプリケーショ ンから新しいデータを取得して、指定した文字列型変 数に保持する どの DDE サーバ アプリケーションがホットリンクで データを送信したかを判別する DDE サーバ アプリケーションにデータを要求する。こ の関数には、チャネルを用いる形式と用いない形式の 2 通りの構文がある 指定された DDE サーバ アプリケーションへの DDE チャネルを開く DDE アプリケーションから受信したコマンドまたは データが、DDE クライアントに受け入れられたかどう かを、DDE サーバ アプリケーションに通知する DDE サーバ アプリケーションに、ワークシートのセル などの項目や変数に特定の値を設定するように要求す る。この関数には、DDE チャネルを用いる形式と用い ない形式の 2 通りの構文がある DDE サーバ アプリケーションへのホットリンクを開 始し、DDE サーバ アプリケーションの中の特定のデー タ変更が PowerBuilder にただちに通知されるようにす る DDE サーバ アプリケーションとのホットリンクを終 了する 表 18-2: DDE クライアント イベント イベント HotLinkAlarm アプリケーション テクニック 発生する状況 DDE サーバ アプリケーションが新しい(変更され た)データを送信したとき 345 DDE 関数とイベント DDE サーバ 表 18-3: DDE サーバ関数 関数 GetCommandDDE GetCommandDDEOrigin GetDataDDE GetDataDDEOrigin RespondRemote SetDataDDE StartServerDDE StopServerDDE 動作内容 DDE クライアント アプリケーションが送信した コマンドを取得する どの DDE クライアント アプリケーションがコマ ンドを送信したかを判別する DDE クライアント アプリケーションが送信した データを取得して、指定した文字列型変数に保持 する どの DDE クライアント アプリケーションがホッ トリンクでデータを送信したかを判別する DDE アプリケーションから受信したコマンドま たはデータが DDE サーバに受け入れられたかど うかを、送信元の DDE クライアント アプリケー ションに通知する 指定されたデータを DDE クライアント アプリ ケーションに送信する PowerBuilder アプリケーションを DDE サーバと して起動する PowerBuilder が DDE サーバとして動作すること を終了させる 表 18-4: DDE サーバ イベント イベント RemoteExec RemoteHotLinkStart RemoteHotLinkStop RemoteRequest RemoteSend 346 発生する状況 DDE クライアント アプリケーションがコマンド を送信したとき DDE クライアント アプリケーションがホットリ ンクの開始を要求するとき DDE クライアント アプリケーションがホットリ ンクの終了を要求するとき DDE クライアント アプリケーションがデータを 要求したとき DDE クライアント アプリケーションがデータを 送信したとき PowerBuilder 第 1 9 章 アプリケーションにおける OLE の 使い方 この章について この章では、PowerBuilder のアプリケーションで OLE を実装する 方法について説明します。 内容 項目 PowerBuilder における OLE のサポート ウィンドウにおける OLE コントロール OLE コントロールと挿入可能なオブジェクト OLE カスタム コントロール プログラム可能な OLE オブジェクト スクリプトにおける OLE オブジェクト オブジェクト ブラウザでの OLE 情報 OLE オブジェクトの高度な操作 ページ 347 349 352 366 370 380 400 402 PowerBuilder における OLE のサポート OLE(Object Linking and Embedding)を利用すると、Windows プロ グラムでのデータとプログラム機能の共有が簡単にできます。 PowerBuilder の OLE コントロールは、OLE サーバ アプリケーショ ンを呼び出して、OLE オブジェクトを表示したり、操作を行った りすることができる、OLE コンテナです。 OLE コントロール アプリケーション テクニック ウィンドウ ペインタの OLE コントロールを使用すれば、複数のア プリケーションのコンポーネントをウィンドウにリンクしたり、 埋め込んだりすることができます。さらに、OLE サーバによって 定義された関数とプロパティを使用して、OLE サーバを制御する ことができます。 347 PowerBuilder における OLE のサポート PowerBuilder の OLE コントロールは、OLE オブジェクトのコンテナで す。エンド ユーザは、OLE オブジェクトをアクティブにして、OLE サーバ アプリケーションによって提供されている機能で編集作業が 行えます。また、OLE 関連の操作は、スクリプトで OLE オブジェクト をアクティブにして、OLE サーバへコマンドを送ることによって、自 動化できます。OLE サーバは、DLL または別個の EXE ファイルのい ずれかとすることができます。これらのサーバは、異なるコンピュー タ上で動作していてもかまいません。 PowerScript のオートメーションを使用すれば、ウィンドウに表示され ている OLE コントロール、または OLEObject 変数に保持されている非 表示の OLE オブジェクトの参照を操作できます。OLEObject 型を使用 すると、OLE コンテナをウィンドウに表示しなくても OLE オブジェク トが作成できます。 OLE カスタム コント ロール 2 番目のコントロールである、OLE カスタム コントロールは、ActiveX コントロール(OCX コントロールとも呼ばれます)用のコンテナです。 ActiveX コントロールは DLL であり(拡張子 OCX が付くこともあり ます)、アプリケーションと常に同じプロセスで動作します。 OLE オブジェクトの 管理 OLE オブジェクトの管理は、OLE オブジェクトを変数に保持して、 ファイルに保存して行うことができます。このために 2 つのオブジェ クトのデータ型 OLEStorage と OLEStream が用意されています。ほと んどのアプリケーションではこれらのオブジェクトを用いる必要はあ りません。しかし、(複数の OLE オブジェクトを 1 つのデータ構造に 組み込むような)複雑な処理を必要とする場合は、OLEStorage 型や OLEStream 型のオブジェクトとその関数を使用して対処できます。 そのほかの OLE のサ ポート データウィンドウ オブジェクトにおける OLE オブジェクトについて の詳細は、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照し てください。 COM または OLE サーバとしての PowerBuilder についての詳細は、第 27 章「COM/COM+ コンポーネントの構築」および第 20 章「PowerBuilder のランタイム オートメーション サーバ」を参照してください。 348 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 ウィンドウにおける OLE コントロール OLE オブジェクトと ActiveX コントロールは、ウィンドウまたはユー ザ オブジェクトに追加できます。そのためには、OLE コンテナとして 機能する、PowerBuilder OLE コントロールの 1 つを使用します。この 節では、コントロールが OLE オブジェクト(挿入可能なオブジェクト とも呼ばれます)または ActiveX コントロールのどちらを保持するか を選ぶことによって、必要なコントロールを選択する方法について説 明します。 • 挿入可能な OLE オブジェクトは、OLE サーバ アプリケーション に関連付けられているドキュメントです。OLE オブジェクトはア クティブにできます。OLE サーバは、OLE オブジェクトを変更す るためのコマンドやツールバーを提供します。 • ActiveX コントロールまたは OLE カスタム コントロールはサーバ 自身であり、PowerBuilder でプログラミングしたスクリプトに基づ いて、ユーザのアクションを処理します。開発者は、ActiveX コン トロールのイベント用のスクリプトと、PowerBuilder コンテナのイ ベント用のスクリプトを記述できます。これらのスクリプトは、関 数を呼び出し、ActiveX コントロールに属するプロパティを設定し ます。必要であれば、ActiveX コントロールは、ユーザとの対話の ために独自のビジュアルなインタフェースを表示することもでき ます。 ActiveX コントロールは、簡単なビジュアル表示(たとえば、メータや ゲージ)やカスタマイズできる 1 つのアクティビティ(単語や句のス ペルチェックなど)を行うことができます。 OLE コントロール コ ンテナの機能 OLE コントロール コンテナは、すべて、一連の必要なインタフェース をサポートしています。PowerBuilder は、そのほかにもいくつかのサ ポートを提供しています。 • アプリケーション テクニック OLE コントロールは、拡張コントロールのプロ パティを使用して、実行時にその配置を決定、修正できます。 PowerBuilder では、X(Left)、Y(Top)、Width、Height の各プロパ ティをサポートしており、PowerBuilder 単位系で測定します。コン トロールの開発者がこれらのプロパティにアクセスするには、 IOleControlSite インタフェース上の GetExtendedControl メソッドか ら戻される、IDispatch から継承したインタフェースを使用できま す。 拡張コントロール 349 ウィンドウにおける OLE コントロール • PowerBuilder は、ウィンドウ レベ ルで IOleContainer クラスを実装しているので、ウィンドウ上のす べてのコントロールは兄弟関係にあり、お互いに各コントロール の情報を共有できます。コントロールの開発者がこの情報にアク セスするには、OLE EnumObjects メソッドが使用できます。コント ロールが一連のコントロールの一部となっている場合、兄弟関係 に関する情報はとても便利です。ほかのコントロールと異なり、 ウィンドウ上の OLE コントロールは単一の階層構造に格納されま す。 OLE コンテナとしてのウィンドウ OLE オブジェクトと OLE コントロールに限られます このオブジェクト列挙子に見えるのは OLE オブジェクトと OLE コントロールに限られます。ウィンドウ上のほかのコントロール を処理するのにはこのテクニックは使用できません。 • メッセージの反映 コントロール コンテナがメッセージの反映をサ ポートしていない場合、リフレクタ ウィンドウは、OLE コント ロールが親コントロールにメッセージを送ったときに作成されま す。リフレクタ ウィンドウはコントロールに戻るメッセージを反 映するので、コントロール自身でメッセージを処理できます。コ ンテナがメッセージの反映をサポートしている場合は、リフレク タ ウィンドウは必要なく、それに関連する実行時オーバーヘッド もなくなります。PowerBuilder の OLE コントロール コンテナは、 特定のメッセージ セットに対してメッセージの反映を行います。 コントロールの定義 OLE コントロールを作成して、その内容を選択する手順は以下のとお りです。 ❖ ウィンドウ オブジェクトやユーザ オブジェクトで OLE コントロールを配置 するには 1 OLE コントロールを含むウィンドウまたはユーザ オブジェクトを 開きます。 2 メニュー バーから[挿入|コントロール| OLE]を選択します。 オブジェクトの挿入 ダイアログボックスが表示されます。オブ ジェクトは、3 つのタブから選択できます。 3 350 サーバ アプリケーションまたは特定の OLE オブジェクトを選択 して、OLE コントロールに OLE オブジェクトを埋め込むか、リン クできます。また、OLE カスタム コントロール(OCX)を選択し て、OLE カスタム コントロールに挿入できます。または、OLE コ ントロールにオブジェクトを挿入しないでおくこともできます。 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 • 新しいオブジェクトを作成して埋め込む場合は、[新規作成] タブをクリックします。OLE サーバ アプリケーションを選択 して、[OK]ボタンをクリックします。 • OLE コントロールに既存のオブジェクトを選択する場合は、 [ファイルから作成]タブをクリックします。ファイル名を指 定して、 [OK]ボタンをクリックします。 • カスタム コントロール(ActiveX コントロール)を挿入する場 合は、 [コントロールの挿入]タブをクリックします。ActiveX コントロールを選択してから、 [OK]ボタンをクリックします。 • OLE コントロールにオブジェクトを挿入しない場合は、 [キャ ンセル]ボタンをクリックします。 [キャンセル]ボタンをクリックした場合には、コントロール は OLE カスタム コントロールではなく、OLE コントロールに なります。OLE コントロールへの OLE オブジェクトの埋め込 みまたはリンクは、いつでもできます。しかし、後から ActiveX コントロールを挿入することはできません。 4 コントロールを表示したい場所で、ウィンドウをクリックします。 OLE オブジェクトを挿入した場合、PowerBuilder は、OLE オブジェ クトを表示して編集できるように、OLE サーバ アプリケーション を起動します。ActiveX コントロールは開くことができません。 一覧表示されていない OLE サーバ アプリケーションに属するオブ ジェクトを挿入するときは、OLE サーバ アプリケーションをインス トールする必要があります。インストール方法については、OLE サー バ アプリケーションのマニュアルを参照してください。 オブジェクトの挿入 ダイアログボックスの使い方についての詳細は、 PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください。 アプリケーション テクニック 351 OLE コントロールと挿入可能なオブジェクト OLE コントロールと挿入可能なオブジェクト OLE コントロール内には、挿入可能な OLE オブジェクトがあります。 ペインタやスクリプトで OLE コントロール内の OLE オブジェクトを 変更できます。また、PowerBuilder のプロパティを設定して、OLE オ ブジェクトを指定できます。 OLE コントロールの設定 OLE コントロールを作成して、OLE オブジェクトを挿入すると、OLE サーバ アプリケーションがアクティブになり、OLE オブジェクトが修 正できます。PowerBuilderOLE オブジェクトを非アクティブにした後 (レイアウト ビューで OLE オブジェクトの枠線の外側をクリックしま す)、OLE コントロールのプロパティ シートを使用して、OLE コント ロールを設定できます。 ❖ OLE コントロールの表示と動作の形態を指定するには 1 OLE コントロールをダブルクリックするか、コントロールのポッ プアップ メニューから[プロパティ]を選択します。 2 プロパティ ビューで、使用アプリケーションに関係する名前をコ ントロールに与えます。 スクリプトではこの名前を使用します。デフォルト名は「ole_」の 接頭辞に数字を組み合わせたものです。 3 OLE サーバが使用する表示の名前の値を指定します。OLE サーバ は、ウィンドウのタイトル バーにこの名前を使用できます。 4 コントロールの外観と動作を指定するには、プロパティ ビューで 適切な設定を選択します。 ほかのコントロールにある標準的な[表示可能]、 [使用可能]、 [フォーカス時の枠表示]、および[枠のスタイル]プロパティの ほかに、OLE オブジェクトと OLE サーバとの関係を管理するオプ ションがあります。 352 PowerBuilder 第 19 章 オプション 起動方法 アプリケーションにおける OLE の使い方 意味 コントロールをアクティブにする方法 オプションは以下のとおり • ダブルクリック(activatedoubleclick!)– コントロール がダブルクリックされたときに、OLE サーバ アプリ ケーションをアクティブにする • フォーカス(activategetfocus!) – コントロールがク リックされるか、タブによって選択されたときに、 OLE サーバ アプリケーションをアクティブにする。 また、GetFocus イベントに対するスクリプトでは、 MessageBox 関数などのフォーカス移動させるような 関数を呼び出さないようにする • スクリプト(activatemanually!)– Activate 関数をスク リプトで使用しなければ、コントロールをアクティ ブにできない 表示の種類 コントロールは、 [起動方法]オプションの設定に関係 なく、いつでもスクリプトでアクティブにできる コントロールに何を表示するかの指定 オプションは以下のとおり • 内容(displayascontent!)– コントロールのサイズに合 わせて、オブジェクトを縮小して表示する • アイコン(displayasicon!)– データに関連付けられて いるアイコンを表示する。通常このアイコンは、OLE サーバ アプリケーションから提供される 内容の更新 可能 • ActiveX ドキュメント(displayasactivexdocument!)– ActiveX ドキュメントとして表示する。ActiveX ド キュメントは、コンテナのスペースを満たし、サー バ アプリケーションのすべての機能を使用できる コントロール上のオブジェクトをリンクするか埋め込 むかの指定 オプションは以下のとおり • 埋め込み / リンク(containsany!)– オブジェクトをリ ンクまたは埋め込みで挿入できる • 埋め込み(containsembeddedonly!)– オブジェクトを 埋め込みで挿入できる • リンク(containslinkedonly!)– オブジェクトをリンク で挿入できる [内容の更新可能]オプションを設定すると、 ContentsAllowed プロパティの値が変更される アプリケーション テクニック 353 OLE コントロールと挿入可能なオブジェクト オプション 意味 リンクの更新 オプション コントロール上のオブジェクトがリンクされていると きの、リンク情報の更新方法 オプションは以下のとおり • 自動(linkupdateautomatic!)– リンクが中断されて、 PowerBuilder がリンクされたファイルを検索できな い場合に、エンド ユーザがファイルを指定できるダ イアログボックスを表示する • スクリプト(linkupdatemanual!)– リンクが中断され ると、オブジェクトはアクティブにできない。スク リプトで LinkTo 関数または UpdateLinksDialog 関数を 使用して、再リンクを行う [リンクの更新オプション]を設定すると、 LinkUpdateOptions プロパティの値が変更される サイズ モード コンテナにおけるオブジェクトの表示方法 オプションは以下のとおり • クリップ(clip!)– オブジェクトの画像がフルサイズ で表示される。画像が OLE コントロールより大きい 場合は、コントロールの枠線からはみ出す部分が切 り捨てられる • ストレッチ(stretch!)– オブジェクトの画像は、OLE コンテナ コントロールのサイズに合うようにサイズ 変更される(デフォルト) ペインタにおけるオブジェクトのアクティブ化 OLE コントロール内のオブジェクトをサーバ アプリケーションを使 用して操作するには、そのオブジェクトをアクティブにしなければな りません。デフォルトでは、ユーザがオブジェクトをアクティブにす るときには、そのオブジェクトをダブルクリックします。このデフォ ルトの方法を変更するには、コントロールの[起動方法]プロパティ を設定します(前の表を参照)。開発時は、ウィンドウ ペインタでオ ブジェクトをアクティブにします。 ❖ ウィンドウ ペインタで OLE オブジェクトをアクティブにするには 1 OLE コントロールのポップアップ メニューから[開く]を選択し ます。 コントロールにオブジェクトが挿入されていない場合は、 [開く] は選択できません。ポップアップ メニューから[オブジェクトの 挿入]を選択して、コントロールにオブジェクトを挿入してくだ さい。 354 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 サーバ アプリケーションが起動され、オブジェクトがオフサイト でアクティブ化されます。 2 サーバ アプリケーション上で、オブジェクトを修正します。 3 更新が終わったら、ハッチング表示の枠線の外をクリックして、オ ブジェクトを非アクティブにします。 サーバ アプリケーションの[ファイル]メニューから[閉じる] または[閉じて戻る]を選択することもできます。 OLE コントロール内のオブジェクトの変更 ウィンドウ ペインタで、OLE コントロール内のオブジェクトの変更や 削除ができます。 ❖ OLE コントロールからオブジェクトを削除するには • OLE コントロールのポップアップ メニューから[オブジェクトの 削除]を選択します。 これで OLE コントロール内のオブジェクトは削除されたので、ア クティブ化できません。 [削除]は選択しないでください。ウィン ドウから OLE コントロールが削除されます。 ❖ OLE コントロールにオブジェクトを挿入するには 1 コントロールのポップアップ メニューから[オブジェクトの挿入] を選択します。 オブジェクトの挿入 ダイアログボックスが表示されます。 2 [新規作成]タブを選択してサーバ アプリケーションを選択する か、コントロールを定義したときと同様に、[ファイルから作成] タブを選択してファイルを指定します。 3 [OK]をクリックします。 実行時のオブジェクト の変更 InsertObject、InsertFile、InsertClass、または LinkTo 関数を呼び出して、OLE コントロールに OLE オブジェクトを挿入できます。Cut 関数または Clear 関数を呼び出して、OLE コントロールから OLE オブジェクトを 削除できます。 ユーザの OLE コントロールの使い方 OLE コントロールが配置されたウィンドウが開くと、PBL(アプリケー ションが作成されている場合は、PBD または EXE ファイル)内の OLE コントロールに格納された情報を使用して、データが表示されます。 アプリケーション テクニック 355 OLE コントロールと挿入可能なオブジェクト エンド ユーザがダブルクリックするか、コントロールをタブで選択す るか、スクリプトで Activate 関数を呼び出して、オブジェクトがアク ティブ化されると、サーバ アプリケーションが起動され、OLE コント ロール内でオブジェクトが編集できます。OLE コントロール内でオブ ジェクトが編集できない場合は、オフサイトで編集できます。 エンド ユーザがオブジェクトを変更すると、OLE コントロールのデー タは最新の状態に更新されます。オブジェクトが OLE コントロール内 で編集されているときは、データが更新されていることは明らかです が、オフサイトで編集している場合も同じように更新されます。ほと んどのサーバ アプリケーションは、連続的にではなく定期的にオブ ジェクトを更新します。そのため、ユーザが認識するのは、コントロー ルの内容に対する定期的な変更だけかもしれません。また、オフサイ トの編集を終了するときは、自動的に最後に行った変更が更新されま す。したがって、OLE コントロールの内容もそのときのタイミングで 変更が反映されます。しかし、安全のためには、オフサイトの編集を 終了する前に、サーバ アプリケーションで Update コマンドを選択して おく必要があります。 リンクと埋め込み アプリケーションでは、OLE オブジェクトはリンクすることも埋め込 むこともできます。どちらの方法を選択するかは、どのようにデータ を管理したいかによって決まります。 データの埋め込み オブジェクトを埋め込んだ場合、そのデータはアプリケーションに保 持されます。開発時には、そのデータはアプリケーションの PBL ファ イルに保存されます。また、アプリケーションが完成すると、EXE ファ イルや PBD ファイルに保存されます。このデータはユーザのためのテ ンプレートまたは開始点です。埋め込みオブジェクトは構築したアプ リケーションの一部として保存されているため、実行中にそのデータ を編集することはできますが、変更内容は保存されません。 オブジェクトの埋め込みは、たとえばレター フォームの本文のよう な、変更を行わないデータに適した方法です。また、変更してどこか ほかのところに保持するデータの開始点として使用するのに適してい ます。 実行時にデータを保存するには、SaveAs 関数と Open 関数を使用して、 ファイルまたは OLE ストレージにデータを保存することができます。 356 PowerBuilder 第 19 章 データのリンク アプリケーションにおける OLE の使い方 オブジェクトのリンクでは、データそのものではなく、データへの参 照をアプリケーションに含めます。アプリケーションは、表示を目的 としたデータの画像も格納します。サーバ アプリケーションが、実際 のデータ(通常、ファイルに保存されるデータ)を取り扱います。そ のため、ほかのアプリケーションからも同じデータにリンクできます。 アプリケーションがデータに加えた変更は、リンクしているすべての 文書に現れます。 リンクには優れた点が 2 つあります。 • 複数のアプリケーションから同一のデータにアクセスできる • サーバ アプリケーションがデータの保存を管理する。そのデータ にアクセスする PowerBuilder アプリケーションが 1 つしかなくて も、データは変更できる リンク情報の管理は、PowerBuilder ではなくサーバ が行います。起動するサーバ、および使用するファイル内のデータ ファ イルや項目といった情報は、OLE オブジェクトによって PowerBuilder に通知されます。サーバは、データを提供し、そのデータを更新して 元のデータ ファイルに保存し、さらに、その項目に関する情報(たと えば、リンクした列の範囲内に列を挿入した場合の覚え書きといった 情報)を更新します。 リンク情報の管理 中断されたリンクの修復 サーバがリンクを管理しているので、開発者 は、OLE オブジェクトが埋め込まれているのかリンクされているのか を気にせずに、そのオブジェクトをアプリケーション内で移動したり 操作したりすることができます。 ファイルの移動、名前の変更、または削除などが原因でリンクが中断さ れた場合は、コントロールの[リンクの更新オプション]の設定内容に よって、それにどう対処するかが決まります。 [リンクの更新オプショ ン]が「自動」に設定されている場合は、PowerBuilder がダイアログボッ クスを表示して、ファイルの検索を指示します。UpdateLinksDialog 関数 を使用して、スクリプトで同じダイアログボックスを表示することが できます。また、リンクは、LinkTo 関数を使用してスクリプトで行う ことができます。 コントロールには、リンクされているオブジェクトが、そのオブジェ クトを開いたときと同じ画像で表示されます。 アプリケーション テクニック 357 OLE コントロールと挿入可能なオブジェクト オフサイト アクティブ化とインプレース アクティブ化 アプリケーション実行時に、エンド ユーザが OLE コントロール上の オブジェクトをアクティブにすると、PowerBuilder は、埋め込まれて いるオブジェクトをインプレース アクティブ化しようとします。つま り、エンド ユーザによるそのオブジェクトの操作は、PowerBuilder の ウィンドウ内部で行われます。サーバ アプリケーションが提供するメ ニューは、PowerBuilder アプリケーションのメニューとマージされま す。メニューのマージは、メニュー ペインタで管理できます(359 ペー ジの「インプレース アクティブ化に対するメニュー」参照)。 コントロールがインプレース アクティブ化されると、幅広のハッチン グ表示の枠線が現れます。 オフサイト アクティブ化とは、サーバ アプリケーションが開き、サー バのウィンドウ上でオブジェクトの内容(文書など)が開かれること です。この場合は、サーバのメニューすべてが使用できます。コント ロール自体は斜線ストライプの影が付けられて表示され、オブジェク トがサーバ アプリケーションで開いていることが示されます。 インプレース アクティブ化の制限 PowerBuilder が OLE オブジェクトをインプレース アクティブ化でき るかどうかは、サーバの機能によって決まります。OLE 1.0 オブジェ クトは、インプレース アクティブ化できません。また、OLE 2.0 標準 は、リンクされたオブジェクトがインプレースではなくオフサイトで アクティブ化するように指定しています。 ウィンドウ ペインタ上では、オブジェクトは常にオフサイト アクティ ブ化されます。 358 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 デフォルトの動作形態は、スクリプトで Activate 関数を呼び出し、オブ ジェクトをインプレースまたはオフサイトのどちらでアクティブ化す るかを指定して変更することができます。コントロールの[起動方法] が「スクリプト(activatemanually!)」に設定されている場合は、Activate 関数の呼び出しを DoubleClicked イベント(またはほかのイベント)に 対するスクリプトに記述します。 デフォルトの動作形態 の変更 ole_1.Activate(Offsite!) コントロールがアクティブ化されない場合 空のコントロール、つまり OLE オブジェクトと関連付けられていない OLE コントロールは、アクティブ化できません。エンド ユーザに OLE オブジェクトを選択させたい場合は、InsertObject 関数を呼び出すスク リプトを記述します。 また、コントロール上のオブジェクトをリンクするときにリンクする ファイルが見つからない場合も、そのコントロールをアクティブ化で きません。ただし、 [リンクの更新オプション]が「自動」に設定され ている場合は、PowerBuilder がダイアログボックスを表示して、エン ド ユーザにファイルを検索させることができます。 [リンクの更新オプション]が「スクリプト(activatemanually!)」に設 定されている場合は、UpdateLinksDialog 関数を使用して、スクリプトで ダイアログボックスを表示したり、LinkTo 関数を使用して、スクリプ トで別ファイルにリンクしたりすることができます。 インプレース アクティブ化に対するメニュー オブジェクトがインプレース アクティブ化すると、サーバ アプリケー ションのメニューは、PowerBuilder アプリケーションのメニューと マージされます。メニュー ペインタの[マージ オプション]の設定内 容によって、2 つのアプリケーションのメニューのマージ方法が決定 されます。選択肢としては、「merge!」と「exclude!」のほかに、標準 メニュー名があります。 ❖ OLE オブジェクトがアクティブ化されたときに、アプリケーションのメニュー を制御するには 1 メニュー ペインタでメニューを開きます。 2 メニュー バーに表示するメニュー項目を選択します。[マージ オ プション]の設定は、ドロップダウン メニューのメニュー項目で はなく、メニュー バーのメニュー項目だけに適用されます。 アプリケーション テクニック 359 OLE コントロールと挿入可能なオブジェクト 3 プロパティ ページで、適切な[マージ オプション]の設定を選択 します。表 19-1 は設定のリストです。 表 19-1: [マージ オプション]の設定 オプション filemenu! 意味 コンテナ アプリケーション (PowerBuilder アプリケーション) のメニュー バーの一番左に表示 されるメニュー。サーバの[ファ イル]メニューは表示されない editmenu! コンテナ アプリケーションの[編 集]メニューは表示されない。サー バの[編集]メニューが表示される windowmenu! 開いているシートのリストを持つ コンテナ アプリケーションのメ ニュー。サーバの[ウィンドウ] メニューは表示されない helpmenu! コンテナ アプリケーションの[ヘ ルプ]メニューは表示されない。 サーバの[ヘルプ]メニューが表 示される merge! サーバ アプリケーションの最初 のメニューの後に、そのメニュー が表示される exclude! オブジェクトがアクティブな間 は、メニューは表示されない 4 標準メニューの標準的 な割り当て アクティブ化されたオ ブジェクトのメニュー バー 360 メニュー バーに 表示される メニューの入手先 コンテナ サーバ コンテナ サーバ コンテナ メニュー バーにある各メニュー項目に対して、操作手順 2 と 3 を 繰り返します。 通常、 [マージ オプション]の「filemenu!」 「editmenu!」、 、 「windowmenu!」 、 および 「helpmenu!」は、それぞれ[ファイル]、[編集]、 [ウィンド ウ]、[ヘルプ]の各メニューに割り当てます。実際のメニュー名が国 際的なアプリケーションにおいては異なるかもしれないので、 [マージ オプション]を使用して正しい関係を設定します。 [マージ オプション]を設定すると、メニュー バーに、コンテナの [ファイル]と[ウィンドウ]メニュー、およびサーバの[編集]と [ヘルプ]メニューを表示できます。 「merge!」が設定されたすべての メニューは、メニュー バーの適切な位置に挿入されます。また、メ ニュー バーには、サーバが適切であると判断したほかのメニューも表 示されます。 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 OLE コントロール上でのオブジェクトの修正 OLE オブジェクトが OLE コントロールに表示されているときは、その オブジェクトとそれを作成したアプリケーション(OLE サーバ)の操 作が可能です。また、そこで行われる可能性のある操作をスクリプト に記述することもできます。この節では、以下の方法について説明し ます。 • OLE オブジェクトをアクティブにして、一般的なコマンドをサー バに送る方法 • コントロール内のオブジェクトの変更と保存方法 • データまたはプロパティがイベントによって変更されたときに、 それを検出する方法 コントロールのオートメーションについては、380 ページの「スクリ プトにおける OLE オブジェクト」を参照してください。 OLE オブジェクトのアクティブ化 通常は、OLE コントロールでは、ダブルクリックでオブジェクトをア クティブ化できます。また、Activate 関数を呼び出せば、スクリプトか らもそのオブジェクトをアクティブ化できます。OLE コントロールの Activation プロパティが Manual に設定されている場合は、Activate 関数 を呼び出してサーバの編集セッションを開始しなければなりません。 ole_1.Activate(InPlace!) 一般的な OLE アクションは、DoVerb 関数を呼び出すことによって起動 できます。バーブ(Verb)とは、実行されるアクションを指定する整 数値のことです。各整数値の意味は、サーバによって異なります。通 常、デフォルトのアクション(0 を指定)は、編集です。また、この アクションはオブジェクトのアクティブ化も同時に行います。 たとえば、ole_1 コントロールが Microsoft Excel のスプレッドシートを 含んでいる場合は、以下の式によってオブジェクトをアクティブ化し て、編集可能にします。 ole_1.DoVerb(0) サーバ アプリケーションのマニュアルを調べ、サポートされている バーブの内容を確認してください。OLE バーブによる、オブジェクト の操作は比較的制限されます。柔軟なインタフェースを必要とする場 合は、オートメーションを使用してください。ただし、OLE 1.0 サー バは、バーブしかサポートしておらず、オートメーションはサポート していません。 アプリケーション テクニック 361 OLE コントロールと挿入可能なオブジェクト OLE コントロール上のオブジェクトの変更 PowerBuilder は、OLE コントロール上のオブジェクトを変更するため の関数をいくつか提供しています。これらの関数は、表 19-2 に示すよ うに、オブジェクトをエンド ユーザに選択させるか、オブジェクトを リンクするか埋め込むかによって使い分けます。 表 19-2: OLE コントロール上のオブジェクトを変更するための関数 選択条件 オブジェクトをエンド ユーザに選択させる。 コントロールの Contents プロパティが Any の 場合は、オブジェクトをリンクしても埋め込 んでもかまわない 指定したサーバで新たなオブジェクトを作成 し、コントロールに埋め込む 既存のオブジェクトのコピーをコントロール に埋め込む 既存のオブジェクトをコントロールにリンク する 既存のオブジェクトをファイルかストレージ から開く。ファイルの情報が、オブジェクト をリンクするか埋め込むかを決める 関数 InsertObject InsertClass InsertFile LinkTo Open 図 19-1 は、リンクか埋め込みかの選択ができない 3 つの関数の動きを 示しています。 図 19-1: リンクか埋め込みかの選択ができない関数 362 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 Blob 型変数に保持されている OLE オブジェクトのデータは、OLE コ ントロールの ObjectData プロパティに代入できます。 blob myblob ...// Blob 型変数に保持した OLE データを代入するコード ole_1.ObjectData = myblob コントロールの Contents プロパティによって、埋め込みやリンクの対 象となるオブジェクトを受け入れるかどうかが指定されます。これに よって、エンド ユーザにオブジェクトの挿入 ダイアログボックスで埋 め込みかリンクかを選択させるかどうかが決まります。また、Contents プロパティによって、使用可能な関数が決められます。このプロパティ が許可しない方法を選択する関数を呼び出すと、その関数の実行は失 敗します。 オブジェクト ブラウ ザでの OLE 情報 使用しているシステムにインストールされている OLE サーバ アプリ ケーションの登録名を検索する場合は、オブジェクト ブラウザを使 用します。ここに表示される名前は、InsertClass、ConnectToObject、 ConnectToNewObject の各関数の引数として使用できます(370 ページ の「プログラム可能な OLE オブジェクト」を参照)。 OLE とオブジェクト ブラウザについての詳細は、400 ページの「オブ ジェクト ブラウザでの OLE 情報」を参照してください。 クリップボードの使い 方 メニュー項目のスクリプトに Cut、Copy、Paste の各関数を記述すると、 クリップボード機能がエンド ユーザに提供されます。Cut 関数や Copy 関数を OLE コントロールに対して呼び出すと、そのコントロール上の OLE オブジェクトがクリップボードにコピーされます。同様に、エン ド ユーザがサーバ アプリケーションでこれらのメニュー項目を選択 すると、データがクリップボード上にコピーされます。これらの関数 は、メニュー項目に限らず、任意のスクリプトで記述できます。 OLE コントロールには、オブジェクトを挿入するための Paste 関数が いくつか用意されています。これらの関数には、貼り付けるオブジェ クトをリンクするか、埋め込むかの違いがあるだけです。 表 19-3: Paste 関数 選択条件 クリップボード上のオブジェクトをコント ロールに埋め込む 関数 クリップボード上のオブジェクトをコント ロールに貼り付けてリンクする 貼り付けるオブジェクトを埋め込むか、リン クするかをエンド ユーザに選択させる PasteLink アプリケーション テクニック Paste PasteSpecial 363 OLE コントロールと挿入可能なオブジェクト 通常 Paste 関数を用いて処理しているスクリプトで、貼り付け先が OLE コントロールになる場合があるときは、以下のようなスクリプト で PasteSpecial 関数(または PasteLink 関数)を呼び出します。 graphicobject lg_obj datawindow ldw_dw olecontrol lole_ctl // フォーカスされているオブジェクトを取得します。 lg_obj = GetFocus() // オブジェクトの種類を基に、クリップボード上のデータを挿入しま す。 CHOOSE CASE TypeOf(lg_obj) CASE DataWindow! ldw_dw = lg_obj ldw_dw.Paste() ... CASE OLEControl! lole_ctl = lg_obj lole_ctl.PasteSpecial() END CHOOSE 埋め込まれたオブジェ クトの保存 ウィンドウの設計時に埋め込まれた OLE オブジェクトは、OLE コント ロールとともにライブラリに保存されます。しかし、アプリケーショ ン実行時に埋め込まれたオブジェクトは、コントロールとともに保存 できません。アプリケーションの実行モジュールやライブラリは、読 み出し専用だからです。このオブジェクトを保存したい場合は、その データをファイルかデータベースに保存しなければなりません。 たとえば、以下のスクリプトは、SaveAs 関数を使用してオブジェクト をファイルに保存しています。ここでは、エンド ユーザに対してファ イル名の入力を指示し、コントロール上のオブジェクトを、サーバ ア プリケーション本来のデータとしてではなく、OLE データ ファイルと して保存します。このファイルは、スクリプトによって、別のセッショ ンのコントロール上で開くこともできます。 string myf ilename, mypathname integer result GetFileSaveName("Select File", mypathname, & myfilename, "OLE", & "OLE Files (*.OLE),*.OLE") result = ole_1.SaveAs(myfilename) 364 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 通常、ファイルに保存した OLE データはサーバ アプリケーションで 直接開くことができません。しかし、PowerBuilder でそのオブジェク トを開いてからサーバ アプリケーションを起動することはできます。 オブジェクトをコントロールに埋め込むと、実際のデータは Blob デー タとしてコントロールの ObjectData プロパティに保持されます。埋め 込んだオブジェクトをデータベースに保存して後から検索したい場合 は、そのオブジェクトを Blob データとして保存します。Blob 型変数と コントロール間のデータ転送は、Blob データをコントロールの ObjectData プロパティに代入したりその逆を行ったりして、実行します。 blob myblob myblob = ole_1.ObjectData Blob データは、埋め込み SQL の UPDATEBLOB 文を使用してデータベー スで更新することができます(『PowerScript リファレンス』マニュア ルを参照)。 また、OLE オブジェクトは、SaveAs 関数や Save 関数を使用して、 PowerBuilder の OLEStorage 型変数に保持できます(405 ページの「ス トレージを開く、保存する」を参照)。 リンクしたオブジェクトをサーバに保存しても、リンク情報に影響は ありません。したがって、その開いているオブジェクト自体は、保存 する必要はありません。しかし、エンド ユーザがそのオブジェクト名 を変更したり、リンクした項目の範囲に影響を及ぼした場合は、Save 関数を呼び出して、リンク情報を保存したりしなければなりません。 OLE コントロールにおけるイベント サーバ アプリケーションで OLE オブジェクトに影響するアクション が起きたことを PowerBuilder に通知するイベントがいくつか用意され ています。 データのイベント データに関するイベントは、次のとおりです。 • DataChange イベント データが変更されたとき • Rename イベント オブジェクトの名前が変更されたとき • Save、SaveObject イベント データが保存されたとき • ViewChange イベント エンド ユーザがデータの表示を変更したとき これらのイベントが起こると、その変更内容は OLE コントロールに自 動的に反映されます。オブジェクトに対する名前の変更、保存、また はオブジェクトの変更が行われたときに、何らかの処理を必要とする 場合は、適切なスクリプトを記述して対処します。 アプリケーション テクニック 365 OLE カスタム コントロール OLE アーキテクチャが起因して、上記イベント内で OLE オブジェクト を処理できない場合があります。実行すると、ランタイム エラーを引 き起こしかねません。通常は、PostEvent 関数を使用して非同期イベン ト ハンドラにイベントをポストします。SaveObject イベントをポスト する必要はないので、サーバ アプリケーションがオブジェクトを保存 する際に、常にオブジェクト内のデータをファイルに保存したい場合 には、このイベントが便利です。 プロパティのイベント サーバがプロパティ通知をサポートしている場合は、サーバのプロパティ 値が変更されたときに、PropertyRequestEdit イベントと PropertyChanged イベントが起動されます。変更をキャンセルしたり、古い値を保存し たり、または新しい値を読み込むスクリプトを記述したりすることが できます。 プロパティ通知の詳細については、393 ページの「ホット リンクの作 成」を参照してください。 OLE カスタム コントロール [コントロール]ドロップダウン ツールバーの[OLE]ボタンをクリッ クして、OLE コンテナに OLE オブジェクトまたは OLE カスタム コン トロールのどちらを挿入するかを選択できます。OLE カスタム コント ロール(ActiveX コントロール)を選択すると、コンテナの種類と内容 が確定されます。後から、挿入するオブジェクトを選択したり、別の ActiveX コントロールを選択したりすることはできません。 ActiveX コントロールには、ActiveX コントロール自身のプロパティ、 イベント、関数があります。スクリプトで ActiveX コントロールのプ ロパティとメソッドを呼び出す際に、ActiveX コントロールが変更され ないようにすることは、エラーの回避にもなります。 OLE カスタム コントロールの設定 PowerBuilder のカスタム コントロール コンテナには、どんな ActiveX コントロールにも適用するプロパティがあります。ActiveX コントロー ルは、ActiveX コントロール自身のプロパティを持っています。この節 では、それぞれの種類のプロパティの用途と設定方法について説明し ます。 PowerBuilder のプロ パティ 366 OLE カスタム コントロールのプロパティには、2 つの用途があります。 PowerBuilder 第 19 章 • アプリケーションにおける OLE の使い方 ほかのコントロールと同様に、コンテナの表示と動作の形態を設 定する [全般]プロパティ ページの標準設定([表示可能]、[使用可能] など)と同様に、表示位置、ポインタ、およびドラッグアンドド ロップの設定ができます。 • ActiveX コントロールが使用できるデフォルトの情報を提供する OLE コンテナのフォント情報や表示名をアンビエント プロパティ と呼びます。PowerBuilder が直接アンビエント プロパティを使用 して ActiveX コントロールにテキストを表示することはありませ ん。ActiveX コントロールがアンビエント プロパティを認識でき る場合は、ActiveX コントロールは、PowerBuilder のプロパティを 使用できます。ActiveX コントロールは、テキストを表示したり、 タイトル バーに OLE コンテナの名前を表示したりできます。 ❖ OLE カスタム コントロールの PowerBuilder プロパティを変更するには 1 OLE コントロールをダブルクリックするか、コントロールのポッ プアップ メニューから[プロパティ]を選択します。 OLE カスタム コントロール プロパティ シートが表示されます。 2 コントロールに名前を付けます。スクリプトではこの名前を使用 します。デフォルト名は「ole_」の接頭辞に数字を組み合わせたも のです。 3 [全般]プロパティ ページやほかのページにあるプロパティの値も 適切な値に設定します。 4 プロパティの設定が終わったら、 [OK]ボタンをクリックします。 コントロールの説明 ウィンドウまたはコントロールの[タグ]プロパティに、使用してい る ActiveX コントロールに関する説明を入力します。別の環境でこの ウィンドウを使用する際に ActiveX コントロールがインストールされ ていない場合、ウィンドウがどの ActiveX コントロールを使用してい たかを簡単に調べることができます。 ActiveX コントロール のプロパティ ActiveX コントロールは、通常、ActiveX コントロール自身のプロパ ティと、プロパティの値を設定するためのプロパティ シートを持って います。ActiveX コントロールのプロパティは、PowerBuilder の OLE コンテナではなく、ActiveX コントロールの表示と動作の形態を管理し ます。 アプリケーション テクニック 367 OLE カスタム コントロール ❖ OLE カスタム コントロール内の ActiveX コントロールのプロパティを設定 するには 1 コントロールのポップアップ メニューまたは[全般]プロパティ ページから、[OLE コントロール プロパティ]を選択します。 2 プロパティの値を設定したら、[OK]ボタンをクリックします。 OLE コントロールのプロパティ シートは、ActiveX コントロールのプ ロパティの一部しか提示していない場合があります。その場合、スク リプトで ActiveX コントロールのプロパティ シートにないプロパティ を設定できます。 ActiveX コントロールのプロパティについての詳細は、ActiveX コント ロールのマニュアルを参照してください。 ActiveX コントロールのプログラミング ActiveX コントロールのプロパティを設定したり、ActiveX コントロー ルの関数を呼び出すスクリプトを記述したりして、ActiveX コントロー ルの機能が使用できます。ActiveX コントロールの開発者が提供するイ ンタフェースによって、1 回の関数呼び出しで一連のアクティビティ または個々のプロパティ設定が起動される場合と、関数呼び出しで ユーザに ActiveX コントロールのアクションを制御させる場合があり ます。 ActiveX コントロールは常にアクティブです。開いたり、アクティブに したりする必要のあるオブジェクトを持っていません。つまり、エン ド ユーザは、OLE カスタム コントロールをダブルクリックして、OLE サーバを起動することはしません。しかし、ActiveX コントロールの処 理を開始する関数を呼ぶために、DoubleClicked イベントまたはほかの イベントに対するスクリプトを記述することができます。 スクリプトでのプロパ ティの設定 ActiveX コントロールのプログラミングは、挿入可能なオブジェクトの オートメーションをプログラムすることと同じです。ActiveX コント ロールのプロパティと関数を指定するには、コンテナの Object プロパ ティを使用します。 次の構文は、ActiveX コントロールのプロパティ値にアクセスします。 この構文は、式を記述できる箇所であれば、その使用箇所に制限はあ りません。この式のデータ型は Any です。式が評価されると、式の値 は、コントロール プロパティのデータ型の値になります。 olecontrol.Object.ocxproperty 368 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 次の構文は、ActiveX コントロールの関数を呼び出します。適切なデー タ型の変数で、戻り値を取得できます。 { value } = olecontrol.Object.ocxfunction ( { argumentlist } ) プロパティのアクセス 時のエラー PowerBuilder のコンパイラは、ActiveX コントロールのプロパティと関 数にアクセスするための正しい構文を認識しないため、Object プロパ ティの後の構文をチェックしません。これは、ActiveX コントロールの プログラミングに必要な柔軟性につながります。しかし、プロパティ や関数の名前が間違っていたり、不足していたりすると、アプリケー ションが実行時にエラーを起こす可能性があります。 PowerBuilder は、OLE のエラー処理をするため、ExternalException と Error という 2 つのイベントを用意しています。ActiveX control が組み 込みエラー イベントを定義した場合、PowerBuilder OLE コントロール コンテナには、追加イベントである ocx_event があります。これらのイ ベントを使用すると、割り込みの形でエラー処理ができ、SystemError イベントが起動してアプリケーションが終了することはありません。 また、例外ハンドラ TRY-CATCH も使用できます。 詳細については、390 ページの「エラー処理」を参照してください。 ActiveX コントロール のイベントの使い方 ActiveX コントロールには、ActiveX コントロール自身が持つイベント があります。PowerBuilder は、ActiveX コントロールのイベントと OLE カスタム コントロール コンテナのイベントをマージします。ActiveX コントロールのイベントは、PowerBuilder のイベントとともに、イベ ント リストビューに表示されます。PowerBuilder のイベントに対する スクリプトと同じように、PowerScript で ActiveX コントロールのイベ ントに対するスクリプトも記述できます。ActiveX コントロールのプロ パティとメソッドを参照するには、OLE カスタム コントロールの Object プロパティを使用します。 ActiveX コントロールのイベントと PowerBuilder のイベントの唯一の 違いは、イベントが起動されるタイミングです。ActiveX コントロール のイベントの詳細については、ActiveX コントロールのマニュアルを参 照してください。ActiveX コントロールの開発元が、ActiveX コント ロールのイベント、プロパティ、関数に関するマニュアルを提供して います。 ActiveX コントロールのプロパティとメソッドの一覧は、PowerBuilder オブジェクト ブラウザで参照できます。詳細については、400 ページ の「オブジェクト ブラウザでの OLE 情報」を参照してください。 アプリケーション テクニック 369 プログラム可能な OLE オブジェクト ActiveX コントロールの新規バージョン ActiveX コントロールの新規バージョンをインストールして、その ActiveX コントロールに新規のイベントがあった場合でも、ウィンドウ ペインタの[イベント]ドロップダウン リストボックスには新規のイ ベントが追加されません。新規のイベントを使用するには、既存のイ ベントのスクリプトとともに、OLE カスタム コントロールを削除して 再作成しなければなりません。新規のイベントを使用しない場合は、 コントロールをそのままにしておき、更新された既存の ActiveX コン トロール イベントを使用することができます。 プログラム可能な OLE オブジェクト OLE オブジェクトをスクリプトで操作するときは、必ずしも、ウィンド ウ上に OLE コントロールを配置しなくてもかまいません。PowerBuilder アプリケーションで表示する必要のない OLE オブジェクトは、コント ロールと無関係に作成し、サーバ アプリケーションに接続し、関数呼 び出しやプロパティを設定することができます。サーバ アプリケー ションが、関数を実行して、OLE オブジェクトのプロパティを変更し ます。つまり、OLE オブジェクトを変更します。 アプリケーションの中には、表示、非表示の指定が可能なものがあり ます。表示を指定すれば、エンド ユーザは、そのアプリケーションを アクティブ化し、サーバ アプリケーションのコマンドやツールを使用 して、OLE オブジェクトを操作できます。 OLEObject オブジェクト型 PowerBuilder の OLEObject オブジェクト データ型は、オートメーショ ン機能で用いるために設計されています。OLEObject 変数は動的オブ ジェクトの一種です。つまり、コンパイラは、このオブジェクトに対 するどのようなプロパティ名、関数名、パラメータ リストも受け入れ ます。PowerBuilder は、それらのプロパティと関数が有効かどうかを 知る必要がありません。このオブジェクトのメソッドの呼び出しやプ ロパティの設定は、そのオブジェクトを作成したサーバ アプリケー ションによって把握されています。これらの関数やプロパティが、ア プリケーション実行時に存在しない場合は、実行時エラーが起こりま す。 370 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 OLEObject 変数を使用する手順は次のとおりです。 1 変数を宣言して、インスタンスを作成します。 2 OLE オブジェクトに接続します。 3 OLE サーバのプロパティと関数を使用して、適切な OLE オブジェ クトを操作します。 4 OLE オブジェクトとの接続を解除して、インスタンスを破棄しま す。 これらの手順は、次に説明します。 OLEObject 変数の宣 言 OLEObject 変数を宣言して、メモリを割り当てる必要があります。 OLEObject myoleobject myoleobject = CREATE OLEObject OLE コンテナ コントロール (OLEControl や OLECustomControl)の Object プロパティは、OLEObject オブジェクト データ型です。 サーバへの接続 OLEObject オブジェクトと OLE サーバとの接続は、いずれかの ConnectToObject 関数を使用して行います。オブジェクトに接続すると、 適切なサーバが起動されます。 表 19-4: ConnectToObject 関数 選択条件 指定した OLE サーバで新たなオブジェクトを 作成する。この関数の機能は、OLE コント ロールの InsertClass 関数に似ている サーバのセキュリティにより作成権限があ り、新規オブジェクトが PowerBuilder の OLEObject 変数に関連付けられる場合は、指 定されたリモート サーバ アプリケーションに 新たな OLE オブジェクトを作成する 既存の OLE オブジェクトをファイルから開 く。OLE クラスを指定していない場合は、 PowerBuilder がファイルの拡張子を調べて、 起動するサーバを決める OLE オブジェクトを PowerBuilder の OLEObject 変数に関連付け、リモート サーバ アプリケーションを起動する 関数 ConnectToNewObject ConnectToNewRemoteObject ConnectToObject ConnectToRemoteObject 接続を確立したら、オートメーションのために用意されている一連の サーバ コマンドを使用して、オブジェクトの操作ができます(380 ペー ジの「スクリプトにおける OLE オブジェクト」を参照)。 アプリケーション テクニック 371 プログラム可能な OLE オブジェクト コマンドにアプリケーション修飾子を付ける必要はありません。アプ リケーション修飾子は、サーバに接続したときに、アプリケーション のクラスとしてすでに指定されています。たとえば、以下のコマンド は、OLEObject 変数を作成し、Microsoft Word の OLE インタフェース (word.application)に接続し、文書を開いて文書に関する情報を表示し、 テキストを挿入し、編集された文書を保存し、サーバをシャットダウ ンします。 OLEObject o1 string s1 o1 = CREATE oleobject o1.ConnectToNewObject("word.application") o1.documents.open("c:\temp\temp.doc") // オブジェクトを表示状態にし、 // MS Word ユーザ名とファイル名を表示します。 o1.Application.Visible = True s1 = o1.UserName MessageBox("MS Word ユーザ名 ", s1) s1 = o1.ActiveDocument.Name MessageBox("MS Word 文書名 ", s1) // 新規パラグラフ内にテキストを挿入します。 o1.Selection.TypeParagraph() o1.Selection.typetext(" このテキストを挿入 ") o1.Selection.TypeParagraph() // 最初のブックマークにテキストを挿入します。 o1.ActiveDocument.Bookmarks[1].Select o1.Selection.typetext("Hail!") // End と名前の付いたブックマークにテキストを挿入します。 o1.ActiveDocument.Bookmarks.item("End").Select o1.Selection.typetext("Farewell!") // 文書を保存し、サーバをシャットダウンします。 o1.ActiveDocument.Save() o1.quit() RETURN Microsoft Word の旧バージョンでは、 word.application のかわりに word.basic を使用してください。以下のコマンドは、Microsoft Word バージョン 7.0 の OLE インタフェース(word.basic)に接続し、文書を開き、ブッ クマークの位置まで移動し、指定されたテキストを挿入します。 myoleobject.ConnectToNewObject("word.basic") 372 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 myoleobject.fileopen("c:\temp\letter1.doc") myoleobject.editgoto("NameAddress") myoleobject.Insert(" 挿入するテキスト ") 修飾子として word.application や word.basic (ConnectToNewObject 関数 のクラス)は付けません。 // 不適切なコマンド修飾子 myoleobject.word.basic.editgoto("NameAddress") Microsoft Word バージョン 7.0 の使用上の注意 OLEObject 変数では、word.basic がサーバ アプリケーション Word バー ジョン 7.0 のクラス名となります。一方、コントロール内のオブジェ クトでは、application.wordbasic 修飾子を使用してオブジェクトの階層 構造をどのように移動して目的の wordbasic オブジェクトにアクセス するのかを、Word に知らせなければなりません。 サーバのシャットダウ ンおよび接続解除 オートメーションとともにアプリケーションを終了したら、明示的に シャットダウンすることをサーバに終了を知らせる必要があります。 また、サーバとの接続を解除して、オブジェクトのメモリを解放する 必要があります。 myoleobject.Quit() rtncode = myoleobject.DisconnectObject() DESTROY myoleobject ガベージ コレクションを使って OLEObject 変数を破棄できます。 OLEObject 変数を破棄すれば、サーバとの接続を自動的に解除します。 ガベージ コレクションを使って解除する方をお勧めしますが、OLEObject 変数が使用しているメモリをただちに解放したい場合で、さらにメモ リがアプリケーションのほかの部分で使用していないことが明らかな 場合は、上記のスクリプトでも示されているように、明示的に接続を 解除して、OLEObject 変数を破棄できます。 詳細については、49 ページの「ガベージ コレクションとメモリ管理」 を参照してください。 OLEControl、OLECustomControl、OLEObject データ型の代入 OLEObject 変数に OLE コントロール(OLEControl オブジェクト デー タ型)や ActiveX コントロール(OLECustomControl オブジェクト デー タ型)を直接代入することはできません。 アプリケーション テクニック 373 プログラム可能な OLE オブジェクト コントロールのベンダがプログラム識別子(vendor.application の形式) を公開している場合は、ConnectToNewObject 関数でこの識別子を指定す ることで、ビジュアル コントロールを使用せずに、プログラム可能な インタフェースに接続できます。しかし、ActiveX コントロールでは、 このテクニックを使用すると ActiveX コントロールのイベントが使用 できなくなります。ActiveX コントロールでは、このような使用法を考 慮していませんし、ほとんどの場合は役に立ちません。 OLE コントロールの Object プロパティの値を OLEObject 変数に代入し たり、関数の中で OLEObject 型として使用したりすることができます。 たとえば、ウィンドウに OLEControl の ole_1 と OLECustomControl の ole_2 があり、次のように変数を宣言したとします。 OLEObject oleobj_automate この場合、以下のように代入できます。 oleobj_automate = ole_1.Object oleobj_automate = ole_2.Object OLE コントロールの OLEObject プロパティは読み出し専用なので、 OLEObject 型のオブジェクトを代入することはできません。以下のよ うな代入はできません。 ole_1.Object = oleobj_automate // エラー ! OLEObject のイベン ト OLEObject を継承するユーザ オブジェクトを作成して、OLEObject の イベントが実装できます。PowerScript の SetAutomationPointer 関数は、 OLE オートメーションを使用できるように、OLE のオートメーション ポインタを子孫オブジェクトに割り当てます。 oleobjectchild は、OLEObject の子孫オブジェクトで、ExternalException や Error などのイベントを実装するものとします。以下に示すコード は、OLEObject と oleobjectchild のインスタンス(OLEObject の子孫とな るユーザ オブジェクト)を作成し、Excel に接続してからオートメー ション ポインタを oleobjectchild に割り当てます。 OLEObject ole1 oleobjectchild oleChild ole1 = CREATE OLEObject ole1.ConnectToNewObject( "Excel.Application") oleChild = CREATE oleobjectchild oleChild.SetAutomationPointer( ole1 ) これで、オートメーションで olechild を使用できます。 374 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 オートメーション オートメーションに関する各手順は、単一のスクリプトの中に含まれ ていたり、ウィンドウ上のいくつかのコントロールのアクションに分 離されていたりします。エンド ユーザをオートメーションによる処理 に関与させたい場合は、以下のようにします。 • OLE オブジェクトをウィンドウのインスタンス変数として宣言する • その変数のインスタンスを作成し、ウィンドウの Open イベントで サーバに接続する • エンド ユーザによるリストボックスからの選択やエディット ボッ クスへの入力に応答して、サーバにコマンドを送る • ウィンドウの Close イベントで、サーバとの接続を解除し、そのイ ンスタンスを破棄する エンド ユーザをオートメーションに関与させたくない場合は、すべて の処理を単一のスクリプトで行います。 例 : OLE を使用したレター フォームの生成 この例では、Microsoft Word で VBA スクリプティング を使用して、 データウィンドウ オブジェクトから名前と住所を、マルチラインエ ディットから手紙の本文を取り込み、手紙の作成と印刷を行います。 ❖ レター フォームの例をセットアップするには 1 4 つのブックマークがある CONTACT.DOC という名前の Word 文 書を作成し、PowerBuilder ディレクトリに保存します。 ブックマークは次のとおりです。 • name1 – 受取人の名前 • name2 – あいさつ文に入れる名前 • address1 – 受取人の住所(番地、市、県、郵便番号) • body – 手紙の本文 手紙の本文は次のとおりです。 Multimedia Promotions, Inc. 1234 Technology Drive Westboro, Massachusetts January 12, 2001 [bookmark name1] アプリケーション テクニック 375 プログラム可能な OLE オブジェクト [bookmark address1] Dear [bookmark name2]: [bookmark body] Sincerely, Harry Mogul President 会社名や自筆サインのロゴなどを付けて、手紙の形式を充実させ ることもできます。重要な項目は、ブックマークの名前と位置で す。 2 PowerBuilder では、d_maillist というデータウィンドウ オブジェクト を定義します。このデータウィンドウ オブジェクトには、以下の カラムがあります。 id first_name last_name street city state zip データウィンドウ オブジェクトに検索引数の指定 ダイアログ ボックスを表示して、エンド ユーザが手紙を受け取る顧客を選択 できるようにします。 376 PowerBuilder 第 19 章 3 アプリケーションにおける OLE の使い方 dw_mail という データウィンドウ コントロール、mle_body という マルチライン エディット、およびコマンドボタンやピクチャボタ ンなどを含むウィンドウを定義します。 4 データウィンドウ オブジェクト d_maillist をデータウィンドウ コ ントロール dw_mail に割り当てます。 5 データベースと接続し、データをデータウィンドウ オブジェクト に読み取るスクリプトをウィンドウの Open イベントに記述しま す。以下のコードは、SQL Anywhere データベースとの接続を行い ます。そのウィンドウが大規模なアプリケーションの一部の場合、 通常、この接続はアプリケーションの Open イベントに対するスク リプトで行われます。 /************************************************** トランザクション オブジェクトを INI ファイルからセットアップ します。 **************************************************/ SQLCA.DBMS=ProfileString("myapp.ini", & "Database", "DBMS", " ") SQLCA.DbParm=ProfileString("myapp.ini", & "Database", "DbParm", " ") /************************************************** データベースと接続し、その接続が正常かどうかを テストします。 **************************************************/ CONNECT USING SQLCA; IF SQLCA.SQLCode <> 0 THEN MessageBox(" 接続が失敗しました ", " データベースに " & + " 接続できません " + SQLCA.SQLErrText) アプリケーション テクニック 377 プログラム可能な OLE オブジェクト RETURN END IF /************************************************** トランザクション オブジェクトをデータウィンドウ コントロール に対して設定し、データを検索します。 **************************************************/ dw_mail.SetTransObject(SQLCA) dw_mail.Retrieve() 6 [新規メール]ボタンに対するスクリプトを記述します(スクリプ トについては以下を参照)。 スクリプトで、以下の作業をすべて行います。 • OLEObject 変数を作成する • サーバ アプリケーション(word.application)に接続する • データウィンドウ オブジェクトの各行に対して手紙を 1 通生 成する そのために、VBA 文を使用して表 19-5 の作業を実行する 表 19-5: スクリプトの作業 VBA 文 作業 open ブックマークを備えた文書を開く データウィンドウ オブジェクトの行から名前と住 所を抽出し、それを手紙内の適切な位置に挿入する エンドユーザが mle_body に入力したテキストを手 紙に挿入する 手紙を印刷する 手紙文書を保存せずに閉じる goto と typetext goto と typetext printout close • サーバ アプリケーションとの接続を解除する • OLEObject 変数を破棄する 7 [閉じる]ボタンに対してスクリプトを記述します。ここで必要な コマンドは次の 1 行だけです。 Close(Parent) レター フォームを生 成するスクリプト 以下のスクリプトで、レター フォームの生成と印刷を行います。 OLEObject contact_ltr integer result, n string ls_name, ls_addr /*************************************************** OLEObject 変数にメモリを割り当てます。 378 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 ***************************************************/ contact_ltr = CREATE oleObject /*************************************************** サーバに接続し、エラーをチェックします。 ***************************************************/ result = & contact_ltr.ConnectToNewObject("word.application") IF result <> 0 THEN DESTROY contact_ltr MessageBox("OLE エラー ", & "Microsoft Word に接続できません " & + " コード : " & + String(result)) RETURN END IF /*************************************************** データウィンドウ オブジェクトの各行で、 Word に顧客データを送り、手紙を印刷します。 ***************************************************/ FOR n = 1 to dw_mail.RowCount() /************************************************ ブックマークがある文書を開きます。 ************************************************/ contact_ltr.documents.open("c:\pbdocs\contact.doc") /************************************************ 名字と名前を 1 つの文字列にして、Word の name1 と name2 の各ブックマークに挿入します。 ************************************************/ ls_name = dw_mail.GetItemString(n, "first_name")& + " " + dw_mail.GetItemString(n, "last_name") contact_ltr.Selection.goto("name1") contact_ltr.Selection.typetext(ls_name) contact_ltr.Selection.goto("name2") contact_ltr.Selection.typetext(ls_name) /************************************************ 住所を 1 つの文字列にして、address1 の ブックマークに挿入します。 ************************************************/ ls_addr = dw_mail.GetItemString(n, "street") & + "~r~n" & + dw_mail.GetItemString(n, "city") & + ", " & + dw_mail.GetItemString(n, "state") & + " " & + dw_mail.GetItemString(n, "zip") contact_ltr.Selection.goto("address1") アプリケーション テクニック 379 スクリプトにおける OLE オブジェクト contact_ltr.Selection.typetext(ls_addr) /************************************************ 手紙本文のテキストを Word の body ブックマークに挿入します。 ***********************************************/ contact_ltr.Selection.goto("body") contact_ltr.Selection.typetext(mle_body.Text) /************************************************ 手紙を印刷します。 ************************************************/ contact_ltr.Application.printout() /************************************************ この文書を保存せずに閉じます。 ************************************************/ contact_ltr.Documents.close contact_ltr.quit() NEXT /*************************************************** サーバとの接続を解除し、OLEObject 変数のメモリを解放します。 ***************************************************/ contact_ltr.DisconnectObject() DESTROY contact_ltr 例の実行 例を実行するには、アプリケーション オブジェクトのスクリプトに、 ウィンドウを開くための記述をするか、パワーバーの[実行]ボタン をクリックします。 アプリケーションがウィンドウを開けば、エンド ユーザは検索引数を 指定して、手紙を受け取る顧客を選択できます。また、手紙本文のテ キストをマルチラインエディットに入力したら、 [新規メール]ボタン をクリックして、選択した各顧客への手紙を印刷することができます。 スクリプトにおける OLE オブジェクト この章では、ウィンドウやユーザ オブジェクトにおいて、以下の OLE の 3 つの使用方法について説明しました。学習した内容は以下のとお りです。 380 • OLE コントロールへのオブジェクトの挿入 • OLE カスタム コントロールへの ActiveX コントロールの配置 • OLEObject 変数の宣言と、OLE オブジェクトへの接続 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 スクリプトでは、OLE オートメーションを使用して、プロパティ値の 取得や設定、OLE サーバで定義されている関数の呼び出しなどのオブ ジェクトの操作ができます。前節では、オートメーションのコマンド の例が紹介されています。次の節では、PowerBuilder におけるオート メーションのインタフェースについて詳しく説明します。 オートメーションのインタフェース PowerBuilder では、OLEObject 変数が、OLE サーバや ActiveX コント ロール へのインタフェースとなります。OLEObject 変数を宣言して、 OLE オブジェクトに接続し、変数にドット(.)表記を使用して、サー バへ指示を送ることができます。その指示によって、プロパティ値の 取得や設定、関数の呼び出しができます。 OLEObject 変数の一般的なオートメーション構文は、次のとおりです。 oleobjectvar.serverinstruction OLE コントロールでは、Object プロパティが、OLE サーバや ActiveX コントロールへのインタフェースです。Object プロパティのデータ型 は、OLEObject 型です。 OLE コントロールの一般的なオートメーション構文は、次のとおりで す。 olecontrol.Object.serverinstruction OLE サーバへのコマンドを記述したスクリプトのコンパイル PowerBuilder コンパイラでは、サーバのコマンド セットを認識できな いので、OLEObject 変数に対してコントロールの Object プロパティと メソッドを指定したスクリプトをコンパイルする際に、Object プロパ ティの次に続くコマンドはチェックされません。実行時のエラーを回 避するには、構文が正しくなければなりません。 アプリケーションの実行テストを行って、サーバ アプリケーションの コマンドが正しいことを確認してください。 OLE サーバがサポー トするもの サーバのコマンドには、プロパティとメソッド(関数とイベント)が あります。 OLE サーバ アプリケーションには、オートメーションをサポートする コマンドが用意されています。詳細については、OLE サーバ アプリ ケーションのマニュアルを参照してください。 アプリケーション テクニック 381 スクリプトにおける OLE オブジェクト OLE カスタム コントロールとプログラム可能な OLE オブジェクトに ついては、PowerBuilder オブジェクト ブラウザでプロパティとメソッ ドのリストを参照できます。オブジェクト ブラウザにおける OLE 情 報についての詳細は、400 ページの「オブジェクト ブラウザでの OLE 情報」を参照してください。 プロパティの設定 以下の構文を使用すると、OLE コントロールの Object プロパティを介 して OLE コントロールのプロパティにアクセスできます。 olecontrolname.Object.{ serverqualifiers.}propertyname OLE オブジェクトの階層構造が複雑な場合は、そのオブジェクトの中 にさらにネストしたオブジェクトやプロパティがある場合がありま す。 たとえば、Excel スプレッドシート オブジェクトに対する以下のコマ ンドは、そのオブジェクトをアクティブ化し、セルの value プロパティ を設定します。 double value ole_1.Activate(InPlace!) ole_1.Object.cells(1.1).value ole_1.Object.cells(2.2).value ole_1.Object.cells(3.3).value ole_1.Object.cells(4.4).value = = = = 55 66 77 88 Excel バージョン 95 のスプレッドシートの場合は、セルの行と列の引 数を大カッコでなくカッコで囲みます。たとえば、次のようになりま す。 ole_1.Object.cells(1,1).value = 55 OLEObject 変数を使用してプロパティを指定する場合は、サーバ修飾 子とサーバのプロパティ名が OLEObject 変数の後ろに続きます。 oleobjectvar.{ serverqualifiers.}propertyname サーバ修飾子は、オブジェクトに接続する方法に応じて指定する必要 があります。詳細については、386 ページの「サーバ コマンドの修飾 子」を参照してください。 関数の呼び出し 以下の構文は、OLE コントロールの Object プロパティを使用して、 サーバの関数を呼び出すことができます。 382 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 olecontrolname.Object.{ serverqualifiers.}functionname ( { arguments } ) OLE オブジェクトの階層構造が複雑な場合は、そのオブジェクトの中 にさらにネストしたオブジェクトやプロパティがある場合がありま す。 カッコについて PowerScript では、サーバに対するコマンドをプロパティの設定か関数 のどちらかとみなします。メソッドをプロパティの設定と識別するた めに、メソッド名に続くパラメータをカッコで囲む必要があります。 パラメータがない場合でも、空のカッコを付加します。 引数と戻り値のデータ 型 PowerBuilder は、OLE データを PowerBuilder と互換性のあるデータ型 に変換します。引数に指定した値のデータ型は、OLE サーバで期待さ れているデータ型との互換性が必要ですが、データ型が一致する必要 はありません。 関数が戻り値を返すとき、戻り値を互換性のあるデータ型の変数に代 入することができます。 引数の参照渡し OLE サーバが値をスクリプトに渡して返すことができるように、引数 の参照渡しを要求する場合は、引数の前に REF キーワードを指定しま す。以下のように、外部関数における宣言で使用する REF キーワード と似ています。 olecontrol.Object.functionname ( REF argname ) 以下の例では、ls_string 引数と li_return 引数が参照渡しされているの で、サーバで値を変更することができます。 string ls_string integer li_return ole_1.Object.testfunc(REF ls_string, REF li_return) 以下の例では、OLEObject 変数を使用して、同じ関数の呼び出しを行 います。 OLEObject ole_obj ole_obj = CREATE OLEObject ole_obj.ConnectToNewObject("servername") ole_obj.testfunc(REF ls_string, REF li_return) アプリケーション テクニック 383 スクリプトにおける OLE オブジェクト タイムアウト時間の設定 PowerBuilder クライアントからサーバへの呼び出しは 5 分間でタイム アウトになります。特定の OLE リクエストにもっと長い時間をかけた い場合、PowerScript の SetAutomationTimeout 関数を使用してデフォルト のタイムアウト時間を変更できます。 Word とオートメー ション Microsoft Word バージョン 6.0 と 7.0 は、WordBasic のマクロ言語に似 たコマンド セットによってオートメーションをサポートしています。 このコマンド セットには、ステートメントと関数の両方が含まれ、名 前の付いたパラメータを使用できます。Microsoft Word バージョン 7.0 より後のバージョンでは Visual Basic for Applications(VBA)を使用し ており、オブジェクトの階層構造は、特定の一連のメソッドとプロパ ティを公開します。 WordBasic ステートメント WordBasic には、ステートメントと関数が あります。ステートメントと関数のうちのいくつかは、同じ名前です。 WordBasic 構文はステートメントと関数の呼び出しに違いがあります が、PowerBuilder にはありません。 ステートメントの呼び出しを指定する場合は、引数に AsStatement! (OLEFunctionCallType カタログ データ型の値)を渡すことができます。関 数と同じ名前の WordBasic ステートメントを呼び出すには、AsStatement! を使用する以外、方法はありません。ステートメントと関数の名前が 異なっていても、AsStatement! を指定した方が、効率的です。 olecontrol.Object.application.wordbasic.statementname ( argumentlist, AsStatement! ) ) たとえば、以下のコードでは、AppMinimize ステートメントを呼び出し ています。 ole_1.Object.application.wordbasic. & AppMinimize("",1,AsStatement!) 名前の付いたパラメータ PowerBuilder では、 WordBasic と Visual Basic の 名前の付いたパラメータをサポートしません。カッコの中には、パラ メータの名前ではなく、値だけを指定します。 たとえば、以下のステートメントは、Word バージョン 6.0 または 7.0 の文書中のブックマークにテキストを挿入します。 ole_1.Activate(InPlace!) Clipboard(mle_nameandaddress.Text) ole_1.Object.application.wordbasic.& fileopen("c:\msoffice\winword\doc1.doc") ole_1.Object.application.wordbasic.& 384 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 editgoto("NameandAddress", AsStatement!) ole_1.Object.application.wordbasic.& editpaste(1, AsStatement!) 最後の 2 行のコマンドは、WordBasic マクロでは以下のように記述さ れます。Destination は、名前の付いたパラメータです。 EditGoto.Destination = "NameandAddress" EditPaste PowerBuilder のスクリプトでは、Word バージョン 97 またはそれ以降 の文書にテキストを挿入するためには、次のような構文を使用します。 ole_1.Object.Selection.TypeText(" このテキストを挿入します。 ") 対応する Visual Basic ステートメントでは、Text という名前が付いたパ ラメータに、挿入する文字列を代入します。 Selection.TypeText Text:=" このテキストを挿入します。" オートメーションはマクロ プログラミングではありません 変数を宣言したり、実行の流れを制御したりするコマンド(IF THEN 文 など)をサーバ アプリケーションに送ることはできません。オート メーションは、ほかのコマンドとは独立して、一度に 1 つずつコマン ドを実行します。プログラムの流れを制御するには、PowerScript の条 件文やループ文を使用します。 PowerScript とサーバ コマンドを組み合わ せて使用する方法について説明します。以下のスクリプトは、Microsoft Word の OLE オブジェクトの中にあるブックマークの個数を数えて、 ブックマークの名前を表示します。 Word オートメーションの例 integer i, count string bookmarklist, curr_bookmark ole_1.Activate(InPlace!) count = ole_1.Object.Bookmarks.Count bookmarklist = "Bookmarks = " + String(count) + "~n" FOR i = 1 to count curr_bookmark = ole_1.Object.Bookmarks[i].Name bookmarklist = bookmarklist + curr_bookmark + "~n" END FOR MessageBox(" ブックマーク ", bookmarklist) アプリケーション テクニック 385 スクリプトにおける OLE オブジェクト Word オートメーションに関する参考事項 Word オートメーションに正しい構文を用いているかどうかをチェッ クするには、Word マクロ エディタが使用できます。Word でマクロ記 録を開始し、スクリプトで自動化したい手順を実行し、その後マクロ 記録を終了します。マクロ エディタを開いて作成された構文を調べる には、 〔Alt〕+〔F11〕を押します。PowerBuilder では、大カッコを配列 インデックスに使用していることに注意してください。 Word バージョン 6.0 と 7.0 のオートメーションの例 次 に 示 す ス ク リ プ トでは、Microsoft Word バージョン 6.0 と 7.0 の OLE オブジェクト中に あるブックマークの個数を数えて、ブックマークの名前を表示します。 integer i, count string bookmarklist, curr_bookmark ole_1.Activate(InPlace!) // ブックマークの個数を取得します。 count = ole_1.Object. & application.wordbasic.countbookmarks bookmarklist = "Bookmarks = " + String(count) + "~n" // 各ブックマークの名前を取得します。 FOR i = 1 to count curr_bookmark = ole_1.Object. & application.wordbasic.bookmarkname(i) bookmarklist = bookmarklist + curr_bookmark + "~n" END FOR MessageBox(" ブックマーク ", bookmarklist) サーバ コマンドの修飾子 サーバ コマンドにアプリケーション名を付けて修飾するかどうかは、 サーバと、オブジェクトが接続されている形式によって決まります。 各サーバは、オブジェクトの階層構造を独自のバージョンで実現して いるため、それをコマンドの構文に反映させる必要があります。たと えば、Microsoft Excel におけるオブジェクトの階層構造は図 19-2 のよ うになっています。 386 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 図 19-2: Microsoft Excel のオブジェクト階層 サーバが Excel の場合、以下のコマンドは同じ意味を持っているよう に見えますが、実行結果は異なります。Microsoft Excel バージョン 95 の場合、セルの行と列の引数には、大カッコでなくカッコを用います。 ole_1.Object.application.cells[1,2].value = 55 ole_1.Object.cells[1,2].value = 55 最初のステートメントは、アクティブな文書のセルを変更するもので す。このステートメントでは、Excel におけるオブジェクトの階層構造 をアプリケーション オブジェクトまで上ってから、開いているシート に下りてきます。その開いているシートが、PowerBuilder のコントロー ル上の文書と同じものかどうかは問題にしません。エンド ユーザが Excel に移行して別のシートをアクティブ化すると、スクリプトは、コ ントロール上の文書ではなくそのシートを変更してしまいます。した がって、この構文は使用すべきではありません。 2 番目のステートメントは、PowerBuilder のコントロール上の文書に対 してだけ作用します。ただし、その文書がアクティブ化されていない と、実行時エラーを起こしてしまいます。こちらのステートメントの 方が、別のデータに作用する危険がないだけ安全な構文といえます。 Microsoft Word バージョン 6.0 と 7.0 では、アプリケーションの階層構 造を独自に実現しています。そのため、コントロール上のオブジェク トを操作するときには、以下のように修飾子 application.wordbasic を必 要とします。オブジェクトはアクティブ化しておかなければなりませ ん。たとえば、次のようになります。 ole_1.Object.application.wordbasic.bookmarkname(i) Microsoft Word バージョン 7.0 より後のバージョンでは修飾子は必要あ りません。しかし、修飾子を指定しても有効です。以下のすべての構 文を使用できます。 ole_1.Object.Bookmarks.[i].Name ole_1.Object.Bookmarks.item(i).Name アプリケーション テクニック 387 スクリプトにおける OLE オブジェクト ole_1.Object.application.ActiveDocument. & Bookmarks.[i].Name コントロール上のオブジェクトではなく、PowerBuilder の OLEObject オブジェクト データ型のデータを操作しているときは、コマンドのア プリケーション修飾子を省略します。これは、オブジェクトに接続す るときに、すでに指定しているからです。OLEObject オブジェクト デー タ型についての詳細は、370 ページの「プログラム可能な OLE オブ ジェクト」を参照してください。 オートメーションと Any 型 PowerBuilder は、サーバ アプリケーションのコマンドや関数を知りま せん。したがって、スクリプトをコンパイルするときもサーバ関数の 戻り値やプロパティのデータ型は認識しません。プロパティにアクセ スし、関数を呼び出す式には Any 型の変数を使用します。Any 型の変 数にデータを代入すれば、データ型の変換エラーを回避できます。 実行時に、データが Any 型の変数に代入されると、その変数は、代入 されたデータと同じデータ型に転じます。ClassName 関数を用いて、 Any 型の変数のデータ型を調べて、適切な代入を行うことができます。 矛盾する代入を行うと、実行時エラーが起こります。 不必要な Any 型は使用しないでください サーバの関数が返すデータのデータ型がわかっている場合は、Any 型 を使用しないでください。返されたデータは、正しいデータ型に直接 代入してください。 以下のサンプル コードは、Excel から読み込んだデータを、そのデー タに応じたデータ型の PowerBuilder 変数に代入します。Excel バージョ ン 95 の場合、セルの行と列の引数には、大カッコでなくカッコを用い ます。 string stringval double dblval date dateval any anyval anyval = myoleobject.application.cells[1,1].value CHOOSE CASE ClassName(anyval) CASE "string" stringval = anyval CASE "double" 388 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 dblval = anyval CASE "datetime" dateval = Date(anyval) END CHOOSE 効率的な OLEObjects 変数の使い方 オートメーションのコマンドにサーバ修飾子が複数ある場合、つまり、 オブジェクトの階層構造のネストが深い場合は、オブジェクトの階層 構造をたどってオブジェクトを参照するため、アプリケーションの実 行に時間がかかります。オブジェクトの階層構造の同じ部分を繰り返 して参照する場合は、そのオブジェクトの参照部分を OLEObject 変数 に代入しておくとよいでしょう。オブジェクトの参照は一度だけ行わ れ、その後はその参照が再利用されます。 次のステートメントをプロパティごとに使用すると、同じオブジェク トを何度も参照することになります。 ole_1.Object.application.wordbasic.propertyname OLEObject 変数に、オブジェクトの参照部分を代入した場合、次のよ うになります。オブジェクトの参照は一度だけですみます。 OLEObject ole_wordbasic ole_wordbasic = ole_1.Object.application.wordbasic ole_wordbasic.propertyname1 = value ole_wordbasic.propertyname2 = value 例 : オブジェクトの参 照の解決 次の例は、OLEObject 変数を使用して、Microsoft Word のオブジェクト を参照します。オブジェクトが FOR ループ文で繰り返し参照されてい ます。オブジェクトの参照を OLEObject 変数に代入することによって、 そのオブジェクトへの参照は一度しか行われません。そのため、処理 が効率的になります。例では、OLEObject 変数が不要になったときに、 変数を破棄しています。 integer li_i, li_count string ls_curr_bookmark OLEObject ole_wb ole_1.Activate(InPlace!) ole_wb = ole_1.Object.application.wordbasic // ブックマークの個数を取得します。 li_count = ole_wb.countbookmarks // 各ブックマークの名前を取得します。 FOR li_i = 1 to count アプリケーション テクニック 389 スクリプトにおける OLE オブジェクト ls_curr_bookmark = ole_wb.bookmarkname(i) ... // リストにブックマークの名前を保存するためのコード END FOR エラー処理 PowerBuilder は、OLE サーバが実行できるオートメーションの構文を 知らないので、スクリプトをコンパイルしても、OLE サーバのプロパ ティを参照するステートメントはチェックされません。コンパイラは エラーをチェックすることができないので、OLE サーバが認識できな いプロパティや関数の名前および引数を指定すると、アプリケーショ ンを実行したときに実行時エラーが起きます。 OLE エラー時のイベ ントの連鎖 OLE コントロールまたは OLE サーバによりエラーが発生した場合、以 下の順で PowerBuilder のイベントが連続して起動されます。 1 組み込みエラー イベントを設定している ActiveX control によりエ ラーが発生した場合、PowerBuilder OLE コントロールの ocx_error イベントが起動されます。 2 それ以外の場合は、OLE オブジェクトの ExternalException イベン トが起動されます。 3 ExternalException イベントにスクリプトが記述されていないか、 ExternalException イベントの action 引数に ExceptionFail!(デフォル ト)が設定されている場合は、OLE オブジェクトの Error イベント が起動されます。 4 Error イベントにスクリプトが記述されていないか、Error イベント の action 引数に ExceptionFail!(デフォルト)が設定されている場合 は、RuntimeError またはその子孫オブジェクトのアクティブな例外 ハンドラが起動されます。 5 例外ハンドラが存在しない場合、または既存の例外ハンドラに よって例外が処理されない場合は、アプリケーション オブジェク トの SystemError イベントが発生します。 6 SystemError イベントにスクリプトが記述されていない場合は、ア プリケーションの実行時エラーが起こり、アプリケーションは終 了します。 これらのどのイベントでも、エラー処理ができます。また、TRY-CATCH ブロックを使用してスクリプト内でもエラーは処理できます。しかし、 SystemError イベントが起動された後も処理を継続することはよくあ りません。 390 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 例外処理についての詳細は、41 ページの「例外の処理」を参照してく ださい。 OLE エラーのイベン ト PowerBuilder の OLE オブジェクトと OLE コントロールには、エラー 処理を行う 2 つのイベントがあります。それらのイベントは以下のと おりです。 OLE サーバまたは OLE コントロール で、例外を送出するか、 (ocx_error イベントがない場合の)エラー イベントが起きたときに起動されます。OLE サーバから提供され た情報は、エラーの診断に役立ちます。 • ExternalException イベント • Error イベント 例外やエラー イベントを扱わないときに起動され ます。PowerBuilder のエラー情報は、スクリプトで使用できます。 OLE コントロールで組み込みエラー イベントを設定している場合、 PowerBuilder の OLE コントロール コンテナはイベントを追加します。 OLE サーバでエラー イベントが発生したときに起動 されます。OLE サーバから提供された情報は、エラーの診断に役 立ちます。 • ocx_error OLE コントロールの作成者は、Microsoft Foundation Classes(MFC)ク ラス ウィザードを使用してコントロールの組み込みエラー イベント を生成できます。PowerBuilder での ocx_error イベントの引数は、組み 込みエラー イベントに設定された引数にマップします。 OLE エラーに対する 対応 PowerBuilder の OLE コントロールに ocx_error イベントに対するスク リプトが記述されている場合、イベントの引数からそのエラーに関す る情報を取得して、適切な対応をとることができます。ocx_error の引 数のうちの 1 つは、Boolean 型の CancelDisplay です。CancelDisplay に TRUE を設定すれば、MFC のエラー メッセージの表示をキャンセルで きます。また、エラーについてのほかの表示を行うこともできます。 ExternalException イベントと Error イベントのどちらに対するスクリプ トでも、action 引数を適切な ExceptionAction カタログ データ型の値に 設定します。どの値を設定するかは、開発者が OLE エラーについて何 を知っており、OLE サーバ アプリケーションの少ない情報をいかにう まく取り扱えるかに依存します。 表 19-6: ExceptionAction カタログ データ型の値 ExceptionAction 値 効果 ExceptionFail! イベントにスクリプトが記述されていない場合と同 じ。エラーが発生すると、エラー イベントの起動順位 にしたがって、次のエラー イベントが起動される アプリケーション テクニック 391 スクリプトにおける OLE オブジェクト ExceptionAction 値 ExceptionIgnore! 効果 エラーを無視して、何もエラーが発生しなかったよう にして戻る 注意 OLE サーバのプロパティ値の取得や OLE 関数からの 戻り値がある場合は、異なるデータ型の代入が行われ るために別のエラーが発生する可能性がある ExceptionRetry! OLE サーバへコマンドを再び送る。OLE サーバの準備 ができていない場合に有効 注意 OLE サーバの関数名、プロパティ名、引数の指定が誤っ ていることがエラーの原因である場合、何度も再試行 するように設定すると、アプリケーションは無限ルー プに入る。再試行の回数を制限するため、アプリケー ションでカウンタを設定することができる ExceptionSubstitute ReturnValue! OLE サーバが返す関数の戻り値やプロパティ値のかわ りに、returnvalue 引数に指定した値を使用して、エラー を無視する OLE サーバを呼び出して、returnvalue 引数に適切な値 を代入する前に、アプリケーションをそのまま継続し ても問題ない値をインスタンス変数に設定しておく。 returnvalue 引数のデータ型は、Any 型である。Any 型は、 すべてのデータ型のデータを代入できる エラーが発生した後もアプリケーションを継続する場 合は、OLE サーバが返す正しくない値のかわりに、有 効な値を使用するため安全である 例 : ExternalException イベント ocx_error イベントと同様、ExternalException イベントは、OLE サーバ からのエラー情報を提供します。この情報は、アプリケーションをデ バッグするときに役立ちます。 たとえば、ウィンドウ オブジェクトに 2 つのインスタンス変数がある とします。1 つは、ExceptionAction 値を指定するための変数です。もう 1 つは、OLE サーバが返す値のかわりの値を保持するための Any 型の 変数です。OLE サーバのプロパティにアクセスする前に、適切な値を インスタンス変数に設定します。 ie_action = ExceptionSubstituteReturnValue! ia_substitute = 0 li_currentsetting = ole_1.Object.Value 392 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 OLE コマンドが失敗した場合は、ExternalException イベントに対する スクリプトで、OLE サーバによって指定されたヘルプ トピックが表示 されます。そして ExternalException イベントは、OLE サーバが返す値 のかわりに、準備してあった値に置き換えます。li_currentsetting 変数 への代入は、ともに互換性のあるデータ型なので、正しく行われます。 string ls_context // WinHelp のコンテキスト ID に切り替えるためのコマンド行 ls_context = "-n " + String(helpcontext) IF Len(HelpFile) > 0 THEN Run("winhelp.exe " + ls_context + " " + HelpFile) END IF Action = ExceptionSubstituteReturnValue! ReturnValue = ia_substitute このイベントに対するスクリプトは、すべてのオートメーション コマ ンドに対応しなければなりません。各オートメーション コマンドの前 に、インスタンス変数に適切な値を設定する必要があります。 Error イベント Error イベントは、エラーが発生したときの PowerBuilder のコンテキス トに関する情報を提供します。エラーの発生したオブジェクト名、ス クリプトの内容、エラーの発生したスクリプトの行番号、PowerBuilder のエラー番号、エラー メッセージなどを取得することができます。こ の情報は、アプリケーションをデバッグするときに役立ちます。 Action 引数と ReturnValue 引数の設定は、ExternalException イベントと 同じように Error イベントにも適用されます。 エラー処理を行うためのイベントについての詳細は、『PowerScript リ ファレンス』マニュアルを参照してください。 ホット リンクの作成 OLE サーバには、 プロパティの変更通知をサポートするものがあります。 つまり、OLE サーバのプロパティの変更直前と変更直後に、OLE サーバ は、OLE コントロールにプロパティの変更に関する情報を渡して通知し ます。これらのメッセージは、OLE コントロールの PropertyRequestEdit イベントと PropertyChanged イベントを起動します。 PropertyRequestEdit イベント OLE サーバのプロパティの変更直前に、PropertyRequestEdit イベント が起動されます。このイベントに対するスクリプトで、以下のような ことが可能です。 アプリケーション テクニック 393 スクリプトにおける OLE オブジェクト • PropertyName 引数から、変更されたプロパティの名前がわかる • 古いプロパティ値を取得して保存できる。 プロパティ値はまだ変更されていないので、標準の構文を使用し てその値にアクセスできる • PropertyChanged イ ベント CancelChange 引数の値を TRUE に変更して、変更をキャンセルで きる プロパティが変更されたときに、PropertyChanged イベントが起動されま す。このイベントに対するスクリプトで、以下のようなことが可能です。 • PropertyName 引数から、変更されたプロパティの名前がわかる • 新しいプロパティ値を取得する プロパティ値はすでに変更されているので、その変更はキャンセ ルできない PropertyName 引数の 使い方 PropertyName の引数は文字列のため、ドット(.)表記を使用して、OLE サーバのプロパティの値を取得することはできません。 value = This.Object.PropertyName // プロパティ値は取得でき ません。 そのかわりに、CHOOSE CASE 文または IF 文を使用して、プロパティ 名を調べて、そのプロパティの値を取得できます。 たとえば、PropertyChanged イベントの以下のスクリプトでは、3 つの プロパティ名を調べて、変更されたプロパティの新しい値を取得しま す。プロパティ値は、適切なデータ型の変数に代入します。 integer li_index, li_minvalue long ll_color CHOOSE CASE Lower(PropertyName) CASE "value" li_index = ole_1.Object.Value CASE "minvalue" li_minvalue = ole_1.Object.MinValue CASE "backgroundcolor" ll_color = ole_1.Object.BackgroundColor CASE ELSE ... // そのほかの処理 END CHOOSE 大規模な変更が発生し た場合 394 PropertyName 引数の値に空文字列("")が返る場合があります。これ は、もっと一般的な変更が発生したことを意味します。たとえば、複 数のプロパティに影響する変更が発生したことを意味します。 PowerBuilder 第 19 章 プロパティ通知がサ ポートされない場合 アプリケーションにおける OLE の使い方 OLE サーバがプロパティの変更通知をサポートしていない場合は、 PropertyRequestEdit イベントと PropertyChanged イベントは起動されな いので、それらのイベントに記述されたスクリプトは実行されません。 OLE サーバがプロパティの変更通知をサポートしているかどうかは、 OLE サーバのマニュアルを調べてください。 OLE サーバでプロパティの変更通知がサポートされていないが、アプ リケーションで新しいプロパティ値を知る必要がある場合は、プロパ ティを定期的にチェックする独自の関数を記述します。 PropertyRequestEdit イベントと PropertyChanged イベントについての詳 細は、 『PowerScript リファレンス』マニュアルを参照してください。 OLE サーバで使用できる言語 オートメーション コマンドを記述するとき、通常はコンピュータの地 域(locale)に一致するコマンドを使用します。開発者の地域とエンド ユーザの地域が異なる場合は、SetAutomationLocale 関数でオートメー ションで使用した言語を指定できます。 OLE コントロール、OLE カスタム コントロール、OLEObject オブジェ クトに対して SetAutomationLocale 関数を使用して、アプリケーション 中のオートメーション オブジェクトとは異なる地域を指定できます。 たとえば、開発者がドイツでアプリケーションを開発し、ヨーロッパ 全体に配布する場合は、オートメーションが使用する言語がドイツ語 であることを SetAutomationLocale 関数で指定できます。ole_1 という OLE コントロールには次の構文を使用します。 ole_1.Object.SetAutomationLocale(LanguageGerman!) oleobj_report という OLEObject には次の構文を使用します。 oleobj_report.SetAutomationlocale(LanguageGerman!) OLE サーバ アプリケーションにドイツ語のオートメーション インタ フェースがなければなりません。 エンド ユーザのコンピュータがサポートする言語 エンド ユーザが OLE サーバ アプリケーションをインストールすると き、 (特に Microsoft の OLE アプリケーションの場合)は、自国の言語 と英語のオートメーション インタフェースが提供されます。エンド ユーザが開発者と異なる言語を使用している場合は、開発者の自国語 でオートメーション コマンドを記述することは適当ではありません。 アプリケーション テクニック 395 スクリプトにおける OLE オブジェクト 詳細については、『PowerScript リファレンス』マニュアルの SetAutomationLocale 関数を参照してください。 OLE オブジェクトへの低レベル アクセス C または C++ で作成された DLL 内の外部関数を PowerBuilder から呼 び出して、OLE サーバへ低レベルのアクセスをする必要がある場合、 以下の関数を使用できます。 • GetNativePointer(OLEControl と OLECustomControl の場合) • GetAutomationNativePointer (OLEObject の場合) 処理が終了したら、ポインタを解放するため以下の関数を使用します。 • ReleaseNativePointer(OLEControl と OLECustomControl の場合) • ReleaseAutomationNativePointer(OLEObject の場合) 詳細については、 『PowerScript リファレンス』マニュアルを参照して ください。 データウィンドウ オブジェクトにおける OLE オブジェクト 前節では、OLE コントロールと OLE オブジェクトへのオートメーショ ン インタフェースについて説明しました。スクリプトを使って、デー タウィンドウ オブジェクトに埋め込まれた OLE オブジェクトの設定 も変更できます。また、外部の OLE オブジェクトのプロパティを通知 することもできます。 この節では、Object プロパティにドット(.)表記を使用してデータ ウィンドウ プロパティを設定する方法について説明します。また、 データウィンドウ オブジェクトの OLE オブジェクトに対するオート メーション コマンドの発行方法についても説明します。 OLE オブジェクトの 名前付け OLE オブジェクトにドット(.)表記を使用するために、オブジェクト に名前を付けます。オブジェクトのプロパティ シートの[全般]ペー ジで名前を指定します。 プロパティの設定 OLE コンテナ オブジェクトのプロパティは、データウィンドウ オブ ジェクトのほかのオブジェクトと同様に設定します。コントロールの Object プロパティは、データウィンドウ オブジェクト内のオブジェク トへのインタフェースとなります。 396 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 たとえば、次のステートメントでは、オブジェクト ole_word の Pointer プロパティに設定します。 dw_1.Object.ole_word.Pointer = "Cross!" コンパイラは、Object プロパティ以下の構文をチェックしないので注 意してください。プロパティの設定に誤りがあると実行時エラーが起 こります。 プロパティの設定、エラー処理、および OLE DWObject のプロパティ のリストについての詳細は、 『データウィンドウ リファレンス』マニュ アルを参照してください。 OLE オブジェクトと Modify 関数 Modify 関数の CREATE キーワードを使用して、データウィンドウ オブ ジェクト中の OLE オブジェクトを動的に作成することはできません。 OLE オブジェクトのバイナリ データは、Modify 関数の構文との互換性 がありません。 関数とプロパティ OLE DWObject を呼び出すために 4 つの関数が用意されており、いず れも OLE コントロールに対して同じ効果を及ぼします。その 4 つの関 数は以下のとおりです。 • Activate • Copy • DoVerb • UpdateLinksDialog これらの関数を呼び出すには、データウィンドウ オブジェクトのプロ パティの場合と同様に、データウィンドウ コントロールの Object プロ パティを使用します。 dw_1.Object.ole_word.Activate(InPlace!) ウィンドウの OLE コントロールに適用される 4 つのプロパティは、 OLE DWObject にも適用されます。 表 19-7: OLE コントロールと OLE DWObject に適用されるプロパティ プロパティ ClassLongName アプリケーション テクニック データ型 String 説明 (読み出し専用)OLE DWObject に関連付けら れたサーバ アプリケーションのための長い 名前 397 スクリプトにおける OLE オブジェクト プロパティ ClassShortName データ型 LinkItem String ObjectData String Blob 説明 (読み出し専用)OLE DWObject に関連付けら れたサーバ アプリケーションのための短い 名前 (読み出し専用)オブジェクトのリンク先項 目の完全なリンク名 たとえば、オブジェクトが C:\FILENAME.XLS!A1:B2 にリンクされてい る場合は、LinkItem は C:\FILENAME.XLS!A1:B2 となる オブジェクトが埋め込まれている場合は、オ ブジェクト自身が ObjectData プロパティの Blob 型データとして格納される オブジェクトがリンクされている場合は、こ のプロパティにはリンク情報と(表示用の) キャッシュ イメージが含まれる オートメーション ドット(.)表記を使用して OLE サーバにコマンドが送信できます。構 文には 2 つの Object プロパティが含まれます。 • データウィンドウ コントロールの Object プロパティ OLE コ ン テ ナ の DWObject などのデータウィンドウ オブジェクトへアクセスで きる • OLE DWObject の Object プロパティ オートメーション オブジェク トへアクセスできる 構文は次のとおりです。 dwcontrol.Object.oledwobject.Object.{ serverqualifiers. }serverinstruction たとえば、次のステートメントでは、WordBasic の Insert 関数を使用し て、Word 文書のデータ テーブルの最初に報告書タイトルを追加しま す。 dw_1.Object.ole_word.Object.application.wordbasic.& Insert("Report Title " + String(Today())) アプリケーションにおける OLE カラム データウィンドウ オブジェクトの OLE カラムを使用して、データベー スの Blob 型データを格納、検索、修正できます。アプリケーションで OLE カラムを使用するには、ウィンドウに データウィンドウ コント ロールを配置し、データウィンドウ オブジェクトとの関連付けを行い ます。 398 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 SQL Server のユーザに関する注意 SQL Server データベースを使用している場合は、OLE を使用するため にはトランザクション処理を終了する必要があります。データウィン ドウ コントロールで使用されているトランザクション オブジェクト では、AutoCommit 関数に TRUE を設定します。 データウィンドウ オブジェクトの OLE カラムの作成方法については、 PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください。 OLE サーバ アプリ ケーションのアクティ ブ化 エンド ユーザは、開発者が データウィンドウ ペインタで前もって扱っ たのとまったく同じように Blob 型を扱えます。つまり、Blob 型をダブ ルクリックするだけで、サーバ アプリケーションを呼び出すことがで きます。また、開発者がサーバ アプリケーションを呼び出すには、ス クリプトで OLEActivate 関数を使用できます。OLEActivate 関数を呼び出 すのは、設定された Blob 型をダブルクリックするのと同じことです。 OLEActivate 関数の構文は次のとおりです。 dwcontrol.OLEActivate (row, columnnameornumber, verb ) バーブの設定 OLEActivate 関数を使用する場合は、OLE サーバ アプリケーションに渡 すアクションがわかっている必要があります。Windows では、このア クションのことをバーブと呼びます。通常、文書を編集したい場合は、 大部分のサーバでは、バーブに 0 を設定します。 特定の OLE サーバ アプリケーションでサポートされているバーブを 取得するには、Windows のレジストリ エディタ ユーティリティの高度 なインタフェース(REGEDT32 /V)を実行します。 レジストリ エディタについての詳細は、Windows のオンライン ヘルプ の REGEDT32.HLP を参照してください。 例 たとえば、ボタンに対する Clicked スクリプトで OLEActivate 関数を使 用して、エンド ユーザがダブルクリックできる Blob 型アイコンを知 らなくても OLE を使用できるようにする場合を考えます。 次のステートメントは、データウィンドウ コントロールの dw_1 の現 行の行にある OLE カラムのため、OLE サーバ アプリケーションを呼 び出します。ここでは、データウィンドウ オブジェクトの 2 番目のカ ラムが OLE カラムであると仮定しています。 dw_1.OLEActivate(dw_1.GetRow(), 2, 0) 詳細情報 データウィンドウ オブジェクトにおける OLE の使い方についての詳 細は、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してく ださい。 アプリケーション テクニック 399 オブジェクト ブラウザでの OLE 情報 オブジェクト ブラウザでの OLE 情報 OLE サーバ アプリケーションと OLE カスタム コントロール(OCX) をインストールすると、そのオブジェクトの情報がレジストリに登録 されます。 PowerBuilder は、レジストリを読み込んで、登録されたすべての OLE サーバと OCX のレジストリ情報を表示します。 ❖ OLE 情報を表示するには 1 パワーバーの[オブジェクト ブラウザ]ボタンをクリックします。 2 オブジェクト ブラウザの[OLE]タブをクリックします。 表 19-8 に示す OLE オブジェクトの 3 つのカテゴリが表示されます。 表 19-8: OLE オブジェクトのカテゴリ OLE オブジェクトの カテゴリ 挿入可能なオブジェ クト OLE カスタム コント ロール OLE オートメーショ ン オブジェクト 説明 OLE コンテナにオブジェクトをリンクまたは埋め 込むことができる OLE サーバ。挿入可能なオブジェ クトをサポートする OLE サーバには、ビジュアル コンポーネントが必要 OLE コンテナに含めることができる ActiveX コン トロール。さらに ActiveX コントロールは、挿入可 能なオブジェクトであることもできる。ActiveX コ ントロールが挿入可能なオブジェクトの場合、挿入 可能なオブジェクトのリストに表示される オートメーションをサポートする OLE サーバ。オー トメーション オブジェクトは、非表示のオブジェク トの場合もある。つまり、オートメーションだけを サポートしており、挿入可能なオブジェクトはサ ポートしていないということである これらのカテゴリを展開すると、インストールされた個々の OLE サー バが参照できます。これらの OLE サーバはさらに展開できます。提供 される情報は、カテゴリに依存します。 クラス情報 すべてのカテゴリは、OLE サーバに関するクラス情報を提供します。 クラス情報にはレジストリ キーのリストが表示されます。キーには、 キー自身に意味があるものや、キーに対する値があるものがあります。 キーの値やキーの有無によって、OLE サーバの検索方法と OLE サーバ が何をサポートするかを知らせます。 表 19-9 は、いくつかのキーとその説明です。 400 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 表 19-9: OLE レジストリ キー レジストリ キー GUID TypeLib - GUID ProgID VersionIndependentProgID InprocServer32 ToolboxBitmap32 DefaultIcon Version Insertable Control Verb 値 OLE サーバのグローバル一意識別子 ActiveX コントロールのタイプ ライブラリのグ ローバル一意識別子 OLE サーバや ActiveX コントロールを識別する 文字列。通常、バージョン番号が含まれる OLE サーバや ActiveX コントロールを識別する 文字列だが、バージョン番号を含まない 32 ビット版 ActiveX コントロールのファイル名 開発環境でツールバーやツールボックスに 32 ビットの ActiveX コントロールを表示するため に使用するビットマップ ファイル名 OLE サーバや ActiveX コントロールをアイコン で表示するときに使用されるアイコン ファイル 名。または、アイコンを含む実行ファイル OLE サーバまたは ActiveX コントロールのバー ジョン番号名 値なし – エントリが挿入可能なオブジェクトを サポートする OLE サーバであることを表す 値なし – エントリが ActiveX コントロールであ ることを表す 値なし – エントリがバーブをコマンドとして受 け入れることを表す レジストリの情報に加えて、PowerBuilder オブジェクト ブラウザは、 ActiveX コントロールとオートメーション オブジェクトのプロパティ とメソッドも表示します。OLE の情報を提供するために、PowerBuilder は レ ジ ス ト リ の 情 報 を 使 用 し て ActiveX コ ン ト ロ ー ル を 検 索 し、 ActiveX コントロールのプロパティとメソッドを取得します。この情報 には、引数とデータ型があります。 スクリプトを記述するとき、PowerBuilder オブジェクト ブラウザを使 用して、プロパティ名や関数名を検索し、スクリプトに貼り付けるこ とができます。PowerBuilder オブジェクト ブラウザは、プロパティを アクセスするため構文を提供します。 スクリプト記述時の PowerBuilder オブ ジェクト ブラウザ ❖ OLE の情報をスクリプトに貼り付けるには 1 ブラウザを開きます。 2 [OLE]タブをクリックします。 アプリケーション テクニック 401 OLE オブジェクトの高度な操作 3 オブジェクトを検索するためにリストを展開します。たとえば、ある ActiveX コントロール プロパティを検索するために、その ActiveX コントロール のリストをさらに展開します。 4 プロパティをハイライト表示して、ポップアップ メニューから[コ ピー]を選択します。 5 スクリプト ビューで挿入ポイントを決めて、ポップアップ メニュー から[貼り付け]を選択します。 オブジェクト ブラウザは、以下のようにスクリプトに構文を挿入 します。 OLECustomControl.Object.NeedlePosition OLECustomControl を実際のコントロール名に変更した後は、スク リプトで NeedlePosition プロパティを正しく設定してください。 オブジェクト ブラウザがスクリプトに貼り付ける内容は、選択した内 容によって異なります。オブジェクト(階層構造におけるプロパティ の 1 つ上のレベル)を選択した場合は、PowerBuilder はオブジェクト の ProgID を貼り付けます。ConnectToNewObject 関数で ProgID を使用で きます。 オートメーションとレジストリについての詳細は、第 20 章「PowerBuilder のランタイム オートメーション サーバ」を参照してください。 OLE オブジェクトの高度な操作 PowerBuilder は、コントロール上の OLE オブジェクトとオートメー ションに対するオブジェクトのほかにも、基本的な OLE データ スト レージに対するインタフェースを提供しています。 OLE データは、ストリームと呼ばれるオブジェクトに保持されていま す。また、ストリームは、ストレージと呼ばれるオブジェクトの中に 存在します。ストリームとストレージは、ファイル システムにおける ファイルとディレクトリの関係に似ています。ストリームやストレー ジを開き、読み取り、書き込み、保存、削除することにより、OLE オ ブジェクトの作成、結合、削除を行うことができます。PowerBuilder では、OLEStorage オブジェクトと OLEStream オブジェクトの 2 つの データ型を用いて、ストレージやストリームへのアクセスを行います。 402 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 OLE コントロールと OLEObject 変数を定義すれば、サーバ アプリケー ションやオートメーションのすべての機能にアクセスでき、これだけ でも、OLE の機能を活用することができます。したがって、保持され ているデータの構造が複雑でなければ、PowerBuilder のストレージ オ ブジェクトやストリーム オブジェクトは必要ありません。 ほかのアプリケーションのストレージ ファイル この節では、PowerBuilder アプリケーションが作成した OLE ストレー ジ ファイルについて説明します。ほかの PowerBuilder アプリケーショ ンも、PowerBuilder で作成したストレージ ファイル内のオブジェクト を開くことができます。Excel、Word、およびそのほかのサーバ アプ リケーションは、それらのネイティブ データを OLE ストレージに保 持しますが、各ファイルに独自の形式があるため、それらをストレー ジ ファイルとして直接開くことはお勧めしません。Word や Excel など のファイルは、 (InsertFile 関数を用いて)コントロール上に挿入するか、 (ConnectToObject 関数を用いて)コントロールとオートメーションを接 続した方がよいでしょう。 OLE ストレージの構造 OLE ストレージは、OLE データのリポジトリです。ストレージは、ディ スクのディレクトリ構造に似ています。ストレージは、1 つの OLE オ ブジェクトである場合や、ほかのストレージやサブストレージに格納 されている複数の OLE オブジェクトを格納している場合もあります。 図 19-3 に示すように、サブストレージは、ディレクトリ内のファイル のように、独立した要素の個別の OLE オブジェクトにもでき、画像を 含む文書などの大規模な OLE オブジェクトも形成できます。 図 19-3: OLE ストレージの構造 アプリケーション テクニック 403 OLE オブジェクトの高度な操作 OLE オブジェクトを含むストレージやサブストレージでは、それが特 定のサーバ アプリケーションに属していることを示すタグを付けて 情報を識別しています。これにより、その下位レベルの各コンポーネ ントは、そのサーバ アプリケーションでしか操作されなくなります。 なお、サーバのオブジェクトを格納しているストレージを開いて、そ の中からオブジェクトを取り出すことができますが、そのストレージ は変更すべきではありません。 OLE オブジェクトを格納しているストレージは、オブジェクトの表示 情報を持っています。表示情報がストレージに属しているので、OLE は、オブジェクトを表示するためにサーバ アプリケーションを起動す る必要がありません。 OLE オブジェクトを含まず、単にほかのストレージを格納しているだ けのストレージもあります。この場合は、挿入するオブジェクトがな いので、そのストレージをコントロール上で開くことはできません。 ストレージとストリームに対するオブジェクト データ型 PowerBuilder は、OLE ファイルのストレージとストリームに対するオ ブジェクト データ型を 2 種類用意しています。 • OLEStorage • OLEStream これらのオブジェクトは、トランザクション オブジェクトやメッセー ジ オブジェクトと同じようなクラス ユーザ オブジェクトです。これ らのオブジェクト データ型の変数を宣言し、そのインスタンスを作成 してから、ストレージを開きます。ストレージを使った作業を終了し たら、ストレージを閉じ、変数を破棄して、OLE サーバと変数に割り 当てられていたメモリを解放します。 ストレージを開くと、OLEStorage 変数とディスク上のファイルが関連 付けられます。このファイルは、現行セッションのための一時的なファ イルであったり、OLE オブジェクトを含む既存のファイルであったり します。ファイルが存在しない場合は、PowerBuilder が作成します。 OLE オブジェクトをストレージに格納するには、SaveAs 関数を使用し ます。また、ウィンドウ上の OLE コントロールとストレージとの接続 の確立は、OLE コントロールに対する Open 関数を呼び出して行いま す。 404 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 ストリームは、OLE オブジェクトではないので、コントロール上で開 くことはできません。しかし、ストリームを使用すると、オブジェク トに関する独自の情報をストレージ フィルに格納しておくことがで きます。ストリームは、ストレージまたはサブストレージ内部から開 き、ファイルと同様に、データの入出力を行うことができます。 パフォーマンスに関するヒント ストレージは、OLE データを効率よく表示することができます。サー バ アプリケーションで作成したファイルをコントロールに挿入する ときに、OLE は、そのサーバを起動して、オブジェクトを表示しなけ ればなりません。しかし、OLE ストレージに格納されたオブジェクト を開くときは、サーバを起動するというオーバーヘッドがありません。 OLE は、ストレージが保持している表示情報を使用して、オブジェク トを表示します。エンド ユーザがそのオブジェクトをアクティブにし ない限り、サーバを起動する必要がありません。 ストレージを開く、保存する PowerBuilder は、ストレージを管理するための関数をいくつか用意し ています。もっとも重要な関数は、Open、Save、および SaveAs です。 Open 関数の使い方 ファイル内の OLE データにアクセスする場合は、Open 関数を呼び出 します。ストレージ ファイルの構造によっては、Open 関数の呼び出し が複数回必要となることがあります。 以下のコードは、コントロールの中でファイルのルート ストレージを 開きます。この Open の構文では、ルート ストレージは、ほかのスト レージを格納しているだけのコンテナではなく、OLE オブジェクトで なければなりません。必ず戻り値を調べて、OLE 関数が成功したかど うかを確認してください。 result = ole_1.Open("MYFILE.OLE") コントロールへファイルのサブストレージを開きたい場合は、Open 関 数を 2 回呼び出す必要があります。1 回目は OLEStorage 変数へファイ ルを開くために、2 回目はコントロールへサブストレージを開くため に行います。Stg_data は、CREATE 関数を使って宣言して、インスタン スを作成した OLEStorage 変数です。 result = stg_data.Open("MYFILE.OLE") result = ole_1.Open(stg_data, "mysubstorage") アプリケーション テクニック 405 OLE オブジェクトの高度な操作 Save 関数の使い方 エンド ユーザが、コントロール上のオブジェクトをアクティブにし て、編集するものとします。この場合、サーバは、変更内容をメモリ 上のデータに保持し、DataChange イベントを PowerBuilder アプリケー ションで起動します。アプリケーションでは、Save 関数を呼び出して、 ストレージ ファイルのデータを変更しなければなりません。 result = ole_1.Save() IF result = 0 THEN result = stg_data.Save() SaveAs 関数の使い方 SaveAs 関数を使用して、コントロール上のオブジェクトをほかのスト レージ変数かファイルに保存することもできます。以下のコードは、 コントロールでストレージ ファイルを開き、さらに別のストレージ ファイルを開いた後、そのストレージ ファイルでサブストレージを開 きます。次いで、オリジナルのオブジェクトを 3 階層のネストしたサ ブ ストレージとしてコントロールに保存します。 OLEStorage stg_data, stg_subdata stg_data = CREATE OLEStorage stg_subdata = CREATE OLEStorage ole_1.Open("FILE_A.OLE") stg_data.Open("FILE_B.OLE") stg_subdata.Open("subdata", stgReadWrite!, & stgExclusive!, stg_data) ole_1.SaveAs(stg_subdata, "subsubdata") 以下の図は、ネストしたストレージを順に開き、SaveAs 関数を実行す るまでのプロセスを示しています。ファイルやストレージが存在しな い場合は、Open 関数や SaveAs 関数によって作成されます。SaveAs 関 数を呼び出す前に、コントロールに対して Save 関数を呼び出すと、コ ントロールのオブジェクトが FILE_A ファイルに保存されます。SaveAs 関数を呼び出した後に Save 関数を呼び出すと、オブジェクトは FILE_B ファイルの subsubdata に保存されます。 図 19-4: ネストした OLE ストレージ 406 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 次の例に、第 3 レベルにストレージを作成せずにサブレベルのスト レージを作成する簡単な方法を示します。この場合、第 3 レベルでス トレージをネストしたり、オブジェクトを保存するためにサブスト レージを開いたりする必要がありません。 OLEStorage stg_data, stg_subdata stg_data = CREATE OLEStorage stg_subdata = CREATE OLEStorage ole_1.Open("FILE_A.OLE") stg_data.Open("FILE_B.OLE") ole_1.SaveAs(stg_data, "subdata") ストレージのメンバーに関する情報の取得 ストレージを開くと、以下のメンバー関数を使用して、そのストレー ジ内のサブ ストレージとストリームに関する情報の取得や変更を行 うことができます。 表 19-10: OLE ストレージのメンバー関数 関数 機能 MemberExists 指定したメンバーがストレージ内に存在するかどうか を調べる MemberDelete MemberRename メンバーは、ストレージかストリームのいずれかであ る。各メンバー名は、一意でなければならない。した がって、ストレージやストリームに同じ名前は付けられ ない。メンバーは、空のまま存在してもかまわない ストレージからメンバーを削除する ストレージのメンバーの名前を変更する 以下のコードは、subdata ストレージが stg_data ストレージ内に存在す るかどうかを調べてから、そのストレージを開きます。このコードで は、stg_data と stg_subdata が宣言され、インスタンスが作成されてい るものと想定しています。 boolean lb_exists result = stg_data.MemberExists("subdata", lb_exists) IF result = 0 AND lb_exists THEN result = stg_subdata.Open(stg_data, "subdata") END IF ストレージのメンバー IOle10Native に対して MemberExists 関数を実行 するには、次のように記述します。 ole_storage.memberexists(char(1) + 'Ole10Native', & lb_boolean) アプリケーション テクニック 407 OLE オブジェクトの高度な操作 char(1) が必要なのは、Microsoft の DocFile Viewer などのユーティリ ティでストレージを見たときに、IOle10Native の "I" は I ではないから です。 ストリームを開く場合も同じように記述する必要があります。たとえ ば、次のようになります。 ole_stream.open(ole_storage, char(1) + 'Ole10Native', & StgReadWrite!, StgExclusive!) 例 : ストレージの作成 たとえば、描画ツールで描かれた製品イメージ図を、データウィンド ウ オブジェクトの製品レコードに対応させて表示するものとします。 データベース レコードにはその画像の識別子が格納されています。ア プリケーションでは、この識別子をファイル名として用いて InsertFile 関数を呼び出します。しかし、サーバ アプリケーションを呼び出して 画像を表示するには比較的時間がかかります。 以下の図のように、ストレージ ファイルを作成し、すべての図を保持 しておくことにします。アプリケーションで画像を表示したいときは、 適切なサブ ストレージが開かれるようにします。 図 19-5: OLE ストレージ ファイル サーバ アプリケーションからファイルをコントロールに挿入せずに、 このようにストレージ ファイルを使用すると、処理速度が速くなるう え、すべての画像を単一のファイルにまとめることができて扱いやす くなります。どの画像を表示するにもストレージ ファイルを 1 つだけ 開けばよく、サーバ アプリケーションの起動も必要としないので、画 像が速く表示できるようになります。 408 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 ストレージ内の OLE オブジェクト この例で示すストレージ ファイルは、画像だけを格納していますが、 ファイル内のストレージが同一のサーバ アプリケーションによるも のである必要はありません。作成するアプリケーションの用途に応じ て、ストレージ ファイルに、任意の OLE サーバ アプリケーションの オブジェクトを格納することができます。 ここに示す例は、ストレージ ファイルを作成するユーティリティ アプ リケーションです。このユーティリティ アプリケーションは、データ ウィンドウ オブジェクトと OLE コントロールが 1 つずつある単一の ウィンドウです。 dw_prodid というこのデータウィンドウ オブジェクトには、製品コード カラムが 1 つ設けられています。データベース テーブルの設定を行っ て、製品コードと製品画像ファイル名とが対応付けられるようにしま す。なお、画像は ole_product という OLE コントロール上に表示します。 スクリプトの記述例 この例は、3 つのメイン スクリプトを必要とします。 • ウィンドウの Open イベントに対するスクリプトでは、ストレージ 変数のインスタンスを作成し、ストレージ ファイルを開いて、デー タウィンドウ オブジェクトのデータを読み取る。データベースと の接続は、アプリケーションの Open イベントで行う • データウィンドウ オブジェクトの RowFocusChanged イベントに 対するスクリプトで、画像を開き、ストレージ ファイルに格納する • ウィンドウの Close イベントに対するスクリプトでは、ストレージ ファイルを保存し、ストレージ変数を破棄する ウィンドウにコント ロールを追加する 最初に、dw_prodid コントロールと ole_product コントロールをウィンド ウに追加します。 アプリケーションの Open イベントに対す るスクリプト アプリケーションの Open イベントで、データベースと接続し、ウィ ンドウを開きます。 インスタンス変数 OLEStorage 変数をウィンドウのインスタンス変数として宣言します。 OLEStorage stg_prod_pic アプリケーション テクニック 409 OLE オブジェクトの高度な操作 ウィンドウの Open イ ベントに対するスクリ プト ウィンドウの Open イベントに対する以下のコードは、OLEStorage 変 数のインスタンスを作成し、その変数で PICTURES.OLE ファイルを開 きます。 integer result stg_prod_pic = CREATE OLEStorage result = stg_prod_pic.Open("PICTURES.OLE") dw_prod.SetTransObject(SQLCA) dw_prod.Retrieve() Retrieve 関数で RowFocusChanged イベントを呼び出す ストレージ変数を作成し、ストレージ ファイルを開くコードを Retrieve 関 数の 前に 記述 してお くこ とは 重要 なこと です。Retrieve 関 数は、 RowFocusChanged イベントを起動し、そのイベントによって OLEStorage 変数が参照されることになります。したがって、Retrieve 関数を呼び出 す前に、ストレージ ファイルを開いておかなければなりません。 RowFocusChanged イベントに対するスク リプト InsertFile 関数によって、画像が OLE コントロール上に表示されます。 RowFocusChanged イベントに対するスクリプトでは、データウィンド ウ オブジェクトの prod_id カラムから製品コードを取得し、それを用い て製品画像のファイル名を作成して、InsertFile 関数を呼び出します。最 後に、表示した画像をストレージに保存します。 integer result string prodid // データウィンドウから製品コードを取得します。 prodid = this.Object.prod_id[currentrow] // 製品コードを用いてファイル名を作成します。そのファイル // のオブジェクトをコントロール上に挿入します。 result = ole_product.InsertFile( & GetCurrentDirectory() + "\" + prodid + ".gif") // OLE オブジェクトをストレージに保存し、 // 同じ製品コードを用いてそのストレージに名前を付けます。 result = ole_product.SaveAs( stg_prod_pic, prodid) Close イベントに対す るスクリプト ウィンドウの Close イベントに対するコードでは、ストレージを保存 し、OLE ストレージをサーバから解放して、さらに OLEStorage 変数 のメモリを解放します。 integer result result = stg_prod_pic.Save() DESTROY stg_prod_pic 410 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 戻り値のチェック OLE 関数を呼び出したら、必ず戻り値をチェックしてください。この チェックを行わないと、アプリケーションは、操作が正常終了したか どうかを把握できません。例では、関数の実行が失敗するとスクリプト を中断して戻りますが、エラー メッセージを表示することもできます。 ユーティリティ アプ リケーションの実行 製品画像の識別子をデータベース テーブルに設定して、製品コードご とに画像を作成したら、アプリケーションを実行します。データウィ ンドウ オブジェクトをスクロールすると、対応するファイルが開き、 その OLE オブジェクトがストレージに保存されます。 ストレージ ファイル の使い方 ストレージに格納した画像をアプリケーションで使用するためには、 prod_id カラムをデータウィンドウ オブジェクトに配置し、その製品 コードを用いて PICTURES.OLE ファイル内のストレージを開きます。 以下のコードは、 現行の行に対する画像を OLE コントロールの ole_product に表示します。通常、このコードは、上述のユーティリティ アプリ ケーションのように、いくつかのイベントに分けて使用します。 OLEStorage stg_prod_pic // ストレージ変数をインスタンス化して、ファイルを開きます。 stg_prod_pic = CREATE OLEStorage result = stg_prod_pic.Open("PICTURES.OLE") // データウィンドウからストレージ名を取り出します。 // データウィンドウの rowfocuschanging イベントに // 追加されていると仮定しています。 prodid = this.Object.prod_id[newrow] // 製品の画像をコントロール上に開きます。 result = ole_product.Open( stg_prod_pic, prodid ) 実際のアプリケーションでは、開いているストレージを閉じて、スト レージ変数を破棄するコードも記述しておきます。 ストリームを開く ストリームには、OLE オブジェクトの生データが入っているので、サー バ アプリケーションで作成したストリームを変更することはまずあ りません。しかし、ストリームをストレージ ファイルに追加してスト レージに関する情報を格納することができます。たとえば、各ストレー ジに対するラベルを付けたり、ストレージのメンバーのリストを表示 したりするようなストリームを記述できます。 アプリケーション テクニック 411 OLE オブジェクトの高度な操作 OLE のストレージ ファイルのストリームにアクセスするには、 ストリー ム変数を定義し、そのインスタンスを作成して、すでに開いているスト レージからストリームを開きます。ストリームを開くと、ストリーム変 数とストレージ内のストリーム データとの接続を確立します。 以下のコードでは、OLEStorage 変数と OLEStream 変数を宣言し、スト レージを開いてから、ストリームを開きます。 integer result OLEStorage stg_pic OLEStream stm_pic_label /*************************************************** ストレージ変数とストリーム変数にメモリを割り当てます。 ***************************************************/ stg_pic = CREATE OLEStorage stm_pic_label = CREATE OLEStream /*************************************************** ストレージを開き、戻り値をチェックします。 ***************************************************/ result = stg_prod_pic.Open("picfile.ole") IF result <> 0 THEN RETURN /*************************************************** ストリームを開き、戻り値をチェックします。 ***************************************************/ result = stm_pic_label.Open( stg_prod_pic, & "pic_label", stgReadWrite!) IF result <> 0 THEN RETURN PowerBuilder は、ストリームの開閉や、ストリームに対する情報の入 出力に用いるストリーム関数をいくつか用意しています。 412 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 表 19-11: ストリーム関数 関数 Open Length Seek Read Write Close 例 : ストリームの読み 書き 機能 指定した OLEStream 変数にストリームを開く。このストリー ムを格納しているストレージは、あらかじめ開いておかなけ ればならない ストリームのサイズをバイト単位で取得する シーク ポインタをストリーム内に配置する。次の読み書き操 作は、このポインタから行われる ストリームからのデータの読み取りをシーク ポインタの位置 から開始する ストリームへのデータの書き込みをシーク ポインタの位置か ら開始する ポインタがストリームの終わりを指していない場合は、Write 関数は既存データを上書きする。書き込むデータがストリーム の現行サイズより大きくなる場合は、そのサイズが拡張される ストリームを閉じ、OLEStream 変数との接続を解除する 以下の例は、製品の在庫データをデータウィンドウ オブジェクトの dw_product に表示するときに、その製品の画像を OLE コントロール ole_product に表示します。 ここでは、前述のユーティリティ アプリケー ションで構築したファイルを使用します(408 ページの「例 : ストレー ジの作成」を参照)。画像は、OLE ストレージ ファイルに格納されて います。また、各画像のストレージの名前はデータベース テーブルの 製品コードと同一です。この例では、各画像にラベル情報を追加し、 製品コードに接尾辞 _lbl を付けた名前のストリームに格納します。 図 19-6 はファイルの構造を示しています。 アプリケーション テクニック 413 OLE オブジェクトの高度な操作 図 19-6: OLE ストレージ ファイルの構造 この例は、3 つのスクリプトを必要とします。 • ウィンドウの Open イベントに対するスクリプトでは、ストレージ ファイルを開いて、データウィンドウ オブジェクトのデータを読 み取る。データベースとの接続は、アプリケーションの Open イベ ントで行う • データウィンドウ オブジェクトの RowFocusChanged イベントに 対するスクリプトでは、画像を表示する。また、その画像のラベ ルを持つストリームを開き、そのラベルを StaticText に表示する。 ストリーム名は、製品コードに接尾辞 _lbl を付けたものとなる ラベルが空(サイズがゼロ)の場合は、ラベルをスクリプトで記 述します。このとき記述するデータは、処理を簡単にするために ストリーム名と同じにします。ラベルは、ファイルの作成時に記 述し、ファイルの表示時に読み取るものですが、ここでは、説明 のために、ストリームの読み書きの両方について示しています。 • ウィンドウの Close イベントに対するスクリプトでは、ストレージ ファイルを保存し、ストレージ変数を破棄する OLEStorage 変数 stg_prod_pic は、ウィンドウのインスタンス変数です。 OLEStorage stg_prod_pic ウィンドウの Open イベントに対するスクリプトは以下のとおりです。 integer result stg_prod_pic = CREATE OLEStorage 414 PowerBuilder 第 19 章 アプリケーションにおける OLE の使い方 result = stg_prod_pic.Open( is_ole_file) dw_prod の RowFocusChanged イベントに対するスクリプトは以下のと おりです。 integer result string prodid, labelid, ls_data long ll_stmlength OLEStream stm_pic_label /*************************************************** OLEStream 変数を作成します。 ***************************************************/ stm_pic_label = CREATE OLEStream /*************************************************** データウィンドウから製品コードを取り出します。 ***************************************************/ this.Object.prod_id[currentrow] /*************************************************** ストレージ ファイルの画像をコントロール上に開きます。 ストレージ名は製品コードと同じです。 ***************************************************/ result = ole_prod.Open(stg_prod_pic, prodid) IF result <> 0 THEN RETURN /*************************************************** 製品ラベルのストリーム名を作成し、そのストリームを 開きます。 ***************************************************/ labelid = prodid + "_lbl" result = stm_pic_label.Open( stg_prod_pic, & labelid, stgReadWrite! ) IF result <> 0 THEN RETURN /*************************************************** ストリームのサイズを求めます。データがあれば (サイズが 0 より大きければ)、そのデータを読み取り、データがなけれ ば、ラベルを記述します。 ***************************************************/ result = stm_pic_label.Length(ll_stmlength) IF ll_stmlength > 0 THEN result = stm_pic_label.Read(ls_data) IF result <> 0 THEN RETURN // ストリーム データを st_label に表示します。 st_label.Text = ls_data ELSE result = stm_pic_label.Write( labelid ) IF result < 0 THEN RETURN // 記述したデータを st_label に表示します。 アプリケーション テクニック 415 OLE オブジェクトの高度な操作 st_label.Text = labelid END IF /**************************************************** ストリームを閉じ、ストリーム変数のメモリを解放します。 ***************************************************/ result = stm_pic_label.Close() DESTROY stm_pic_label ウィンドウの Close イベントに対するスクリプトは以下のとおりです。 integer result result = stg_prod_pic.Save() DESTROY stg_prod_pic ストレージを使用する際のストラテジ データをストレージに格納することとデータベースに格納することは 異なります。ストレージ ファイルでは、ストレージを好きなように編 成できるので、データを編成する必要がありません。たとえば、スト レージ ファイルをネストさせて階層的なシステムを設計することが できます。また、アプリケーションの配布やバックアップを簡単にす るために、ストレージ ファイルのルート レベルにいくつかのサブスト レージを一緒に格納しておくだけでもかまいません。また、1 つのファ イルの中に、さまざまな OLE サーバ アプリケーションで作成したス トレージを格納することができます。 使用している DBMS が Blob 型をサポートしていない場合や、データ ベース管理者が大きな Blob 型データをデータベースのログに残さな いようにしている場合は、OLE データを保持する別の手段として、ス トレージを使用できます。 ストレージの構造の遷移を記録しておくこともできます。ストレージ ファイル内のメンバー名(ストレージやストリーム)のリストを表示 するストリームをルート レベルで記述したり、ストリームにストレー ジのラベルやデータベースのキー情報を記述してストレージの説明文 書として利用したりすることができます。 416 PowerBuilder 第 2 0 章 PowerBuilder のランタイム オート メーション サーバ この章について この章では、オートメーションを使用して PowerBuilder のクラス ユーザ オブジェクトにアクセスする方法について説明します。 PowerBuilder オブジェクトは、OLE サーバとして使用できます。 PowerBuilder や OLE に対応した開発ツールは、PowerBuilder オブ ジェクトのメソッドやプロパティにアクセスできます。 内容 アプリケーション テクニック 項目 ランタイム オートメーション サーバの使い方 ユーザ オブジェクトをオートメーション サーバとして使用 する方法 PowerBuilder をオートメーション サーバとして使用する方法 名前付きサーバの作成と使用 ユーザ オブジェクトとレジストリについての詳細 オートメーション サーバを使用するアプリケーションの配布 オートメーション サーバ リファレンス PowerBuilder.Application サーバ オブジェクト CreateObject 関数 GenerateGUID 関数 GenerateRegFile 関数 GenerateTypeLib 関数 例外コード レジストリ更新ファイルのサンプル ページ 418 423 428 433 435 443 445 445 447 450 452 455 459 460 417 ランタイム オートメーション サーバの使い方 ランタイム オートメーション サーバの使い方 PowerBuilder COM サーバの使い方 この章では、PowerBuilder ランタイム オートメーション サーバの使い 方に重点を置いて説明します。COM 準拠のサーバを構築する際には、 PowerBuilder の COM/COM+ サーバ生成がよく用いられます。 PowerBuilder のオートメーション サーバ テクノロジは、将来のリリー スでは廃止される可能性があります。 カスタム クラス ユーザ オブジェクトから PowerBuilder COM オブジェ クトを生成する方法の詳細については、第 27 章「COM/COM+ コンポー ネントの構築」を参照してください。 第 19 章「アプリケーションにおける OLE の使い方」では、OLE オブ ジェクトとカスタム コントロールのコンテナの提供方法と、OLE オブ ジェクトのメソッドとプロパティにアクセスするためのオートメー ションの使用方法について説明しました。 OLE オブジェクトの機能は、 サーバ アプリケーションによって提供されます。データを操作するた めのコマンドをサーバ アプリケーションに送ります。 オートメーション サーバについて PowerBuilder オートメーション サーバは、挿入可能でビジュアルなオ ブジェクトではなく、プログラミング可能なオブジェクトに対応した OLE サーバです。PowerBuilder オートメーション サーバは、PowerBuilder ライブラリ内のクラス ユーザ オブジェクト(非ビジュアル ユーザ オ ブジェクト)へのアクセスを提供します。ユーザ オブジェクトにアク セスするには、オートメーション サーバとのセッションを確立して ユーザ オブジェクトのインスタンスを作成します。次に、オートメー ションの構文を使用してコマンドをユーザ オブジェクトに送ります。 クラス ユーザ オブジェクトは、ほかのオブジェクトのインスタンスを 作成できます。サーバは、これらのオブジェクトの参照をクライアン トに渡すことができます。 418 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ 図 20-1: サーバはクラス ユーザ オブジェクトの参照をクライアントに渡す クライアント アプリ ケーション オートメーションとプログラミング可能なオブジェクトをサポートす るクライアント アプリケーションは、PowerBuilder オートメーション サーバ にアク セスで きます。クライ アント アプリ ケーシ ョンは、 PowerBuilder、Visual C++、Visual Basic などの COM 準拠のツールで作 成できます。 実行時のオーバーヘッ ド オートメーション サーバに接続する度に、PowerBuilder の実行環境の インスタンスが起動します。ただし、サーバのランタイム セッション とクライアントのランタイム セッションはシステム クラスの定義を 共有するため、オーバーヘッドにはなりません。 ユーザ クラスの定義は、共有されません。したがって、複数のランタ イム セッションごとに、同じ大きさのオブジェクトを作成した場合、 オブジェクトのメモリ使用量はランタイム セッションの数の倍にな ります。アプリケーションを再編成して 1 つのサーバ セッションにオ ブジェクトを作成するようにすれば、アプリケーションはメモリを効 率的に使用できます。 ランタイム オートメーションの用途 機能をカプセル化してアクセス情報を提供するクラス ユーザ オブ ジェクトは、オートメーション サーバとして使用できます。クライア ント アプリケーションからアクセスする情報は、パブリックのインス タンス変数に保持するか、関数の戻り値や引数(参照渡し)で使用で きるようにする必要があります。 オートメーション サーバの例として、以下のユーザ オブジェクトがあ ります。 アプリケーション テクニック 419 ランタイム オートメーション サーバの使い方 • データストア オブジェクトを作成して、検索したデータの統計を レポートするユーザ オブジェクト • データの妥当性チェックを行うなど、ビジネス ルールが定義され たユーザ オブジェクト 3 つのアクセス方法 PowerBuilder ユーザ オブジェクトにアクセスするには、3 つの方法が あります。以下にその方法を示します。 オートメーション サーバとしてのユーザ オブジェクト • 定義および登録した PowerBuilder クラス ユーザ オブジェクトにア クセスする • PowerBuilder 自身をサーバとしてアクセスする。その後、指定した ライブラリにあるあらゆる定義済みのオブジェクトのインスタン スを生成できる • PowerBuilder サーバへのアクセスを提供すると同時に、ビジネスに 適した名前を使用できる名前付きサーバにアクセスする クラス ユーザ オブジェクトを定義し、レジストリに登録できます。ク ライアント アプリケーションで提供されている外部オブジェクトに アクセスするための関数を使用すれば、ユーザ オブジェクトのプロパ ティと関数にアクセスできます。オートメーションでは、ユーザ オブ ジェクトのインスタンス変数をプロパティとしてアクセスします。 ユーザ オブジェクトをオートメーション サーバとしてレジストリに 登録する利点は、以下のとおりです。 420 • レジストリに登録されたユーザ オブジェクトの情報を取得できる ので、ほかの開発者はそのユーザ オブジェクトを使用したプログ ラムを簡単に作成できる • ユーザ オブジェクトにアクセスするためのクライアント アプリ ケーションのコードが単純になる • クライアント アプリケーションは、レジストリに登録されたクラ スだけにアクセスできる。したがって、アクセスするユーザ オブ ジェクトの関数の戻り値やインスタンス変数を制限できる PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ 図 20-2: サーバとしてのクラス ユーザ オブジェクトとクライアントの対話 個々のユーザ オブジェクトにアクセスするには、アクセスするすべて のユーザ オブジェクトをレジストリに登録する必要があります。 OLEObject オブジェクト データ型の変数を用いてユーザ オブジェク トに接続し、オートメーションを使用してユーザ オブジェクトのメ ソッドやプロパティ(インスタンス変数)にアクセスします。ユーザ オブジェクトを関連付けると、PowerBuilder のランタイム セッション が起動します。 ランタイム セッション内でユーザ オブジェクトにアクセスする場合 は、そのユーザ オブジェクトのインスタンスを作成します。ユーザ オ ブジェクトの 1 つのインスタンスを作成するたびに、PowerBuilder の ランタイム セッションが起動します。登録オブジェクトごとに、追加 のランタイム セッションのオーバーヘッドがかかります。 ユーザ オブジェクトをレジストリに登録して使用するための操作手 順については、423 ページの「ユーザ オブジェクトをオートメーショ ン サーバとして使用する方法」を参照してください。 オートメーション サーバとしての PowerBuilder PowerBuilder をインストールすると、PowerBuilder をオートメーション サーバとして使用できるように、レジストリに PowerBuilder.Application キーが登録されます。複数のクラス ユーザ オブジェクトのインスタン スを作成し、それぞれのプロパティやメソッドにアクセスできます。 オートメーションでは、ユーザ オブジェクトのインスタンス変数をプ ロパティとしてアクセスします。 PowerBuilder.Application サーバ オブジェクトを使用する利点は、以下 のとおりです。 • アプリケーション テクニック PowerBuilder の実行環境を複数起動することがないので、その分の オーバーヘッドがかからない。1 つのサーバ セッションで複数の ユーザ オブジェクトにアクセスできる 421 ランタイム オートメーション サーバの使い方 • 指定したライブラリ リスト内のすべてのシステム クラスと、プラ イベート クラスに直接アクセスできる。これらのクラスは PowerBuilder.Application サーバ オブジェクトの CreateObject 関数を 使用してインスタンスを作成できる PowerBuilder.Application サーバ オブジェクトに接続した後で、アクセ スするランタイム ライブラリを指定します。ライブラリ内のユーザ オ ブジェクトやシステム クラスは、同じサーバ セッションに複数のイン スタンスを作成できます。 クライアント アプリケーションで作成した各オブジェクトのインス タンスは、クライアントの OLEObject オブジェクトとして扱います。 OLEObject オブジェクトに対してオートメーションを使用すると、そ れぞれのオブジェクトにアクセスできます。クライアント アプリケー ションが、同じランタイム セッションでサーバ オブジェクトの参照を 別のサーバ オブジェクトに渡す場合、その渡されたオブジェクトの参 照は、PowerBuilder では PowerBuilder オブジェクト データ型として認 識されます。これによって、クライアントからのオートメーション コ マンドに制限されずに、同じサーバ セッションで 2 つのオブジェクト を相互に操作できるようになります。 図 20-3: 1 つのサーバ セッション内で対話するオブジェクト PowerBuilder.Application を設定して使用するための操作手順について は、428 ページの「PowerBuilder をオートメーション サーバとして使 用する方法」を参照してください。 422 PowerBuilder 第 20 章 名前付きオートメー ション サーバ PowerBuilder のランタイム オートメーション サーバ ビジネス上の理由で、エンド ユーザに PowerBuilder.Application サーバ オブジェクトを参照できないようにするが、このサーバ オブジェクト が提供する機能(たとえば、1 つのサーバ セッションで複数のユーザ オブジェクトのインスタンスを作成するような場合)は利用するとし ます。 レジストリに PowerBuilder.Application サーバ オブジェクトを参照する もう 1 つのエントリを登録すると、そのビジネスに適切な OLE オート メーション サーバの名前を付けることができます。 名前付きオートメーション サーバを設定するための操作手順につい ては、433 ページの「名前付きサーバの作成と使用」を参照してくだ さい。 ユーザ オブジェクトをオートメーション サーバとして 使用する方法 レジストリに登録されたユーザ オブジェクトをオートメーション サーバとしてアクセスするには、以下の操作手順に従います。 1 クラス ユーザ オブジェクトを作成します。 2 クラス ユーザ オブジェクトのランタイム ライブラリを構築します。 3 クラス ユーザ オブジェクトをレジストリに登録します。 4 クライアント アプリケーションで、クラス ユーザ オブジェクトに 接続するオートメーション コマンドを記述します。 サーバとなるクラス ユーザ オブジェクトの作成 ユーザ オブジェクトをオートメーション サーバとして使用するため にどのような定義を行うかは、アプリケーションの設計に依存します。 ユーザ オブジェクトは、カスタム クラス ユーザ オブジェクトでなけ ればなりません。ユーザ オブジェクトのインスタンス変数と関数を定 義します。ユーザ オブジェクトは、PowerBuilder のほかのオブジェク トを宣言してそのオブジェクトのインスタンスを作成できます。 アプリケーション テクニック 423 ユーザ オブジェクトをオートメーション サーバとして使用する方法 ビジュアル オブジェクトは参照しない オートメーション サーバとして使用するクラス ユーザ オブジェクト は、メッセージ ボックスやウィンドウなどのビジュアル オブジェクト への参照を含むことができません。 クライアント アプリ ケーションにおけるオ ブジェクト クライアント アプリケーションの任意のオブジェクトは、クラス ユー ザ オブジェクトを参照できます。ユーザ オブジェクトを参照するに は、OLEObject オブジェクト データ型を使用します。クライアント ア プリケーションのオブジェクトは、オートメーションの構文を使用し てそのユーザ オブジェクトのプロパティやメソッドにアクセスでき ます。オートメーションでは、ユーザ オブジェクトのインスタンス変 数をプロパティとしてアクセスします。 ユーザ オブジェクト のテスト ユーザ オブジェクトをオートメーション サーバとしてアクセスする 前に、簡単なテスト環境で、そのユーザ オブジェクトが問題なく機能 するかどうかをテストしてください。ローカルでユーザ オブジェクト をテストするためのアプリケーションを構築できます。 ユーザ オブジェクトのランタイム ライブラリの構築 ユーザ オブジェクトを定義した後は、ライブラリ ペインタを使用して 動的ライブラリ(PBD)かコンパイルされたライブラリ(DLL)を構 築します。Pcode かマシン コードのどちらかを選択する理由は、どの PowerBuilder アプリケーションを構築するときでも同じです。 詳細については、832 ページの「コンパイラの基本事項」を参照して ください。 ユーザ オブジェクトとユーザ オブジェクト内でインスタンスを作成 するオブジェクトだけを 1 つのライブラリに格納するように、ライブ ラリ ペインタを使用してライブラリを再編成します。使用されないオ ブジェクトを残したままにしておくと、ランタイム ライブラリが必要 以上に大きくなります。 ライブラリ ペインタで動的ライブラリを構築するには、以下の操作を 行います。 1 ライブラリ ペインタで、ライブラリ名を選択します。 2 [エントリ|ライブラリ|動的ライブラリの構築]を選択します。 3 424 PBD ファイルと DLL ファイルのいずれを作成するかに応じて、 [マシン コード]チェックボックスをオンまたはオフにします。 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ 動的ライブラリの構築 ダイアログボックスのほかのオプションは、 このプロセスでは不要です。ほかのオプションの詳細については、 [ヘルプ]ボタンを選択して、説明を参照するか、PowerBuilder の 『ユーザーズ ガイド』マニュアルを参照してください。 4 [OK]ボタンをクリックしてランタイム ライブラリを構築します。 レジストリに登録するディレクトリに、ランタイム ライブラリを 移動します。 5 ユーザ オブジェクトの登録 ユーザ オブジェクトをオートメーション サーバとして使用するには、 レジストリに登録する必要があります。また、ユーザ オブジェクトの プロパティと関数についての情報を提供するタイプ ライブラリを作 成して、ブラウザ アプリケーションを登録することもできます。 詳細については、435 ページの「ユーザ オブジェクトとレジストリに ついての詳細」を参照してください。 オートメーション サーバ プロジェクト ウィザードを使用すれば、タ イプ ライブラリの登録と作成が簡単にできます。 ❖ レジストリ情報を作成してユーザ オブジェクトを登録するには 1 新規作成 ダイアログボックスの[プロジェクト]タブから[オー トメーション サーバ ウィザード]を選択します。 2 ウィザード内のすべてのページを完成します。 表 20-1 を参考にしてください。 表 20-1: オートメーション サーバ ウィザードのページ ページ [コンポーネン トの選択] [プログラム識 別子の指定] アプリケーション テクニック 指定する内容 オートメーション サーバとして使用するオブジェク トを選択する。オブジェクトは 1 つだけ選択できる。 PowerBuilder.Application を指定するタイミングについ ては、433 ページの「名前付きサーバの作成と使用」 を参照 Mycompany.Myapp など、オブジェクトの識別子を指定 する。バージョン番号は指定しない。PowerBuilder は、 別の画面で指定されたバージョン番号を使用して、 バージョンに依存するエントリを構築する。識別子に 使用できる文字数の上限は 39 文字である。ベンダと アプリケーション間のピリオド以外に句読文字は使 用できない。先頭に数字は使用できない 425 ユーザ オブジェクトをオートメーション サーバとして使用する方法 ページ [レジストリ ファイルとオブ ジェクト GUID の指定] 指定する内容 [オブジェクト クラスの GUID]テキストボックスが 空である場合には、[新規]をクリックして新規のグ ローバル一意識別子(GUID)を生成する。新規の GUID は、オブジェクトのクラス識別子(CLSID)に なる。既存のプログラム識別子を指定した場合は、そ の GUID がテキストボックスに表示される。既存の GUID を再利用しない場合は、新規の GUID を作成。 GUID の再利用の詳細については、444 ページの「複 数のバージョンとアップデート」を参照 レジストリ更新ファイルは、レジストリの更新情報を 格納するテキスト ファイルである。一般に、このファ イルはライブラリと同じ名前を持ち、拡張子は REG である [タイプ ライブ タイプ ライブラリを作成する必要があるのは、オブ ラリの作成] ジェクトのプロパティとメソッドに関する情報を OLE ブラウザで表示する場合のみ [構築オプショ PBD ファイルのかわりに DLL を構築した場合には、 ンの指定] [マシン コード DLL の使用]チェックボックスをオン にする 3 メニューバーから[ファイル|開く]を選択してウィザードによっ て作成されたプロジェクトを選択するか、ToDo リストの「... プロ ジェクトを構築する」をダブルクリックします。 4 プロジェクト ペインタでメニューバーから[デザイン|プロジェ クトの配布]を選択し、レジストリ ファイルとタイプ ライブラリ ファイルを生成します。 5 レジストリ ファイルを実行して、レジストリに情報を追加します。 レジストリおよび独自の登録ツールの記述方法の詳細については、439 ページの「レジストリ情報の作成」を参照してください。 ユーザ オブジェクトにアクセスするクライアント アプリケーションの コードの記述 レジストリに登録されたユーザ オブジェクトにアクセスするクライ アント アプリケーションのコードは、PowerBuilder.Application サーバ にアクセスするコードよりも簡単に記述できます。ライブラリ リスト とマシン コードのプロパティは、すでにレジストリに登録されていま す。 ユーザ オブジェクトのプロパティやメソッドにアクセスするには、 ユーザ オブジェクトに接続して、オートメーションを使用します。 426 PowerBuilder 第 20 章 クライアント アプリ ケーションとしての PowerBuilder PowerBuilder のランタイム オートメーション サーバ ユーザ オブジェクトにアクセスするためにオートメーション サーバ のセッションを確立するには、以下のようにします。 1 ユーザ オブジェクトに接続するための OLEObject オブジェクト データ型の変数を宣言します。 OLEObject ole_analyze 2 ユーザ オブジェクトのプログラム識別子(ProgID)を使用してユー ザ オブジェクトに接続し、接続が確立されたことをチェックしま す。ステータス 0 は、セッションの確立が成功したことを示しま す。 ole_analyze = CREATE OLEObject li_status = ole_analyze.ConnectToNewObject & ("MyCompany.Analyze") IF li_status < 0 THEN MessageBox(" サーバが存在しません ", & "MyCompany.Analyze に接続できません。") RETURN END IF 3 オートメーション構文を使用してユーザ オブジェクトの関数やプ ロパティにアクセスします。 ld_avg = ole_analyze.uof_average() ole_analyze.Projection = TRUE li_status = ole_analyze.uof_RTFreport(REF ls_rpt) OLEObject の ExternalException イベントと Error イベントでエラーを処 理したい場合には、OLEObject 変数を宣言するかわりに、OLEObject か ら継承したユーザ オブジェクトを使用します。 1 ユーザ オブジェクト ペインタを開き、OLEObject オブジェクトを 継承した標準クラス ユーザ オブジェクトを作成します。 2 Error イベントと ExternalException イベントのスクリプトを記述し ます。 3 OLEObject オブジェクトのかわりに、新しいクラス名を宣言文で使 用します。 uo_oleobject ole_analyze クライアントとしての Visual Basic Visual Basic でも、同様のコードを使用して、レジストリに登録された ユーザ オブジェクトに接続できます。 1 ユーザ オブジェクトに接続するためのオブジェクト型の変数を宣 言します。 Dim ole_analyze As Object アプリケーション テクニック 427 PowerBuilder をオートメーション サーバとして使用する方法 2 ユーザ オブジェクトのプログラム識別子(ProgID)を使用してユー ザ オブジェクトに接続し、接続が確立されたことをチェックしま す。 Set ole_analyze = CreateObject("MyCompany.Analyze") If ole_analyze Is Nothing Then REM エラー処理 End If 3 オートメーション構文を使用してユーザ オブジェクトの関数やプ ロパティにアクセスします。 ld_avg = ole_analyze.uof_average() ole_analyze.Projection = TRUE li_status = ole_analyze.uof_RTFreport(REF ls_rpt) PowerBuilder をオートメーション サーバとして使用する 方法 オートメーション サーバとして PowerBuilder.Application サーバ オブ ジェクトを使用するには、以下の手順が必要です。 1 アクセスするクラス ユーザ オブジェクトを定義します。 2 作成したオブジェクトのためのランタイム ライブラリを構築しま す。 3 クライアント アプリケーションで、PowerBuilder に接続し、ユー ザ オブジェクトのインスタンスを作成し、ユーザ オブジェクトの メソッドやプロパティにアクセスするコードを記述します。 アクセスするユーザ オブジェクトの作成 ユーザ オブジェクトをオートメーション サーバとして使用するため にどのような定義を行うかは、アプリケーションの設計に依存します。 ユーザ オブジェクトは、カスタム クラス ユーザ オブジェクトでなけ ればなりません。ユーザ オブジェクトのインスタンス変数と関数を定 義します。ユーザ オブジェクトは、PowerBuilder のほかのオブジェク トを宣言してそのオブジェクトのインスタンスを作成できます。 428 PowerBuilder 第 20 章 オートメーションを使 用して作成されたオブ ジェクト PowerBuilder のランタイム オートメーション サーバ クライアント アプリケーションが、同じサーバ ランタイム セッショ ンに複数のオブジェクトのインスタンスを作成した場合、オブジェク トの参照を別のオブジェクトに渡してこれらのオブジェクトを一緒に 処理できます。 オブジェクトの参照を渡すと、クライアント アプリケーションで作成 した PowerBuilder オブジェクトのインスタンスが、ほかのオブジェク トを認識できます。オブジェクトのインスタンスが同じサーバ セッ ションにある場合、PowerBuilder はその OLE オブジェクトの参照と PowerBuilder オブジェクト データ型を認識します。どの PowerBuilder アプリケーションでも、オブジェクトの参照は、オブジェクトのプロ パティとメソッドへのアクセスを提供します。 ユーザ オブジェクトの関数は、クライアント アプリケーションから渡 されたオブジェクトの参照を受け入れたり、正しいオブジェクト デー タ型の変数にオブジェクトの参照を代入したりすることができます。 また、PowerBuilder オブジェクトのインスタンスの参照を扱うことも できます。 ランタイム ライブラリの構築 ユーザ オブジェクトを定義した後は、ライブラリ ペインタを使用し て、PowerBuilder 動的ライブラリ(PBD)またはコンパイルされたラ イブラリ(DLL)を構築します。同じ PowerBuilder.Application サーバ セッションでアクセスされるランタイム ライブラリは、すべて同じ種 類(PBD か DLL のどちらか)でなければなりません。Pcode かマシン コードのどちらかを選択する理由は、どの PowerBuilder アプリケー ションを構築するときでも同じです。 ライブラリ ペインタでランタイム ライブラリを構築するには、以下の 操作を行います。 1 ライブラリ ペインタで、ライブラリ名を選択します。 2 [エントリ|ライブラリ|動的ライブラリの構築]を選択します。 3 PBD ファイルと DLL ファイルのいずれを作成するかに応じて、 [マシン コード]チェックボックスをオンまたはオフにします。 動的ライブラリの構築 ダイアログボックスのほかのオプションは、 このプロセスでは不要です。ほかのオプションの詳細については、 [ヘルプ]ボタンを選択して、説明を参照するか、PowerBuilder の 『ユーザーズ ガイド』マニュアルを参照してください。 4 [OK]ボタンをクリックしてランタイム ライブラリを構築します。 アプリケーション テクニック 429 PowerBuilder をオートメーション サーバとして使用する方法 5 PowerBuilder.Application サーバ オブジェクトの LibraryList プロパ ティに指定した各ライブラリに対して、操作 1 ~ 4 を繰り返しま す。 6 構築された PBD ファイルまたは DLL ファイルを適切なディレク トリへ移動します。クライアント アプリケーションでは、オート メーション サーバがランタイム ファイルの場所を確認できるよ うに、ランタイム ファイルのパスを指定します。 プロジェクト ペインタでのプロジェクトの構築の詳細については、 PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください。 PowerBuilder とユーザ オブジェクトにアクセスするクライアント アプ リケーションのコードの記述 クライアント アプリケーションで、PowerBuilder.Application サーバ セッションを確立するには、以下の記述を行います。 • オートメーション サーバへの関連付け • オートメーション サーバのプロパティの設定 • ユーザ オブジェクトのインスタンスの作成 • ユーザ オブジェクトへのアクセス サーバ セッションの確立は失敗することもあるので、プロセスのすべ ての手順でエラー チェックを行う必要があります。 以下の例は、その方法を表しています。最初に、PowerBuilder のクラ イアント アプリケーションのコードを示します。次に、Visual Basic の 例を示します。 クライアント アプリ ケーションとしての PowerBuilder PowerBuilder.Application サーバ セッションを確立してオブジェクトに アクセスするには、以下のようにします。 1 PowerBuilder.Application サーバ オブジェクトに接続するために、 OLEObject オブジェクト データ型の変数を 1 つ宣言します。次に、 ユーザ オブジェクトのインスタンスを作成するために、OLEObject オブジェクト データ型の変数を追加宣言します。 OLEObject ole_pba, ole_analyze OLEObject オブジェクトの ExternalException イベントと Error イベ ントでエラーを扱う場合は、OLEObject オブジェクトを継承した標 準クラス ユーザ オブジェクトを使用します。 430 PowerBuilder 第 20 章 2 PowerBuilder のランタイム オートメーション サーバ オートメーション サーバを起動して、接続が確立されたことをチェッ クします。ステータス 0 は、サーバ セッションが成功したことを 示します。 ole_pba = CREATE OLEObject li_status = ole_pba.ConnectToNewObject & ("PowerBuilder.Application") IF li_status < 0 THEN MessageBox(" サーバが存在しません ", & "PowerBuilder.Application に接続できません。") RETURN END IF 3 アクセスするランタイム ライブラリを設定するために、 PowerBuilder.Application サーバ オブジェクトのプロパティを設定 します。ユーザ オブジェクトのインスタンスを作成した後では、 これらのプロパティの値を変更することはできません。 ole_pba.LibraryList = & "c:\pbobjs\myobj\serv1.dll;c:\pbobjs\myobj\serv2. dll" ole_pba.MachineCode = TRUE 4 ユーザ オブジェクトのインスタンスを作成し、インスタンスの作 成が成功したかどうかをチェックします。このとき、ランタイム ライブラリ内にあるユーザ オブジェクトの名前を指定します。 ole_analyze = ole_pba.CreateObject("uo_analyze") IF IsNull(ole_analyze) THEN MessageBox(" オブジェクトが存在しません ", & " オブジェクト uo_analyze を作成できません。") RETURN END IF 5 オートメーションの構文を使用してオブジェクトの関数やプロパティ にアクセスします。以下にプロパティとメソッドの例を示します。 ld_avg = ole_analyze.uof_average() ole_analyze.Projection = TRUE li_status = ole_analyze.uof_RTFReport(REF ls_rpt) 6 アクセスが終了したら、PowerBuilder.Application サーバ オブジェ クトとの接続を解除し、ユーザ オブジェクトのインスタンスを破 棄します。また、この処理は、アプリケーションを終了して実行 することもできます。 DESTROY ole_analyze ole_pba.DisconnectObject() DESTROY ole_pba アプリケーション テクニック 431 PowerBuilder をオートメーション サーバとして使用する方法 クライアント アプリ ケーションとしての Visual Basic 以下に、PowerBuilder.Application サーバ オブジェクトを使用する Visual Basic クライアントのコードを示します。コードの内容は、PowerBuilder と同じです。 1 PowerBuilder.Application サーバ オブジェクトに接続するために、オ ブジェクト型の変数を宣言します。また、インスタンスを作成す るオブジェクトのために、オブジェクト型の変数を追加宣言しま す。 Dim ole_pba As Object Dim ole_analyze As Object 2 オートメーション サーバを起動して、接続が確立されたことをチェッ クします。ステータス 0 は、サーバ セッションが成功したことを 示します。 Set ole_pba = CreateObject_ ("PowerBuilder.Application") If ole_pba Is Nothing Then REM エラー処理 End If 3 アクセスするランタイム ライブラリを設定するために、 PowerBuilder.Application サーバ オブジェクトのプロパティを設定 します。ユーザ オブジェクトのインスタンスを作成した後では、 これらのプロパティの値を変更することはできません。 ole_pba.LibraryList = _ "c:\pb\myobj\serv1.dll;c:\pb\myobj\serv2.dll" ole_pba.MachineCode = TRUE 4 ユーザ オブジェクトのインスタンスを作成し、インスタンスの作 成が成功したかどうかをチェックします。このとき、ランタイム ライブラリ内にあるユーザ オブジェクトの名前を指定します。 Set ole_analyze = ole_pba.CreateObject _ ("uo_analyze") If ole_analyze Is Nothing Then REM エラー処理 End If 5 オートメーションの構文を使用してオブジェクトの関数やプロパ ティにアクセスします。以下にプロパティとメソッドの例を示し ます。 ld_avg = ole_analyze.uof_average() ole_analyze.Projection = TRUE li_status = ole_analyze.uof_RTFreport(REF ls_rpt) 432 PowerBuilder 第 20 章 6 PowerBuilder のランタイム オートメーション サーバ オブジェクトのインスタンスを破棄します。アプリケーションを 終了しても同じ結果が得られます。 Set ole_analyze = Nothing Set ole_pba = Nothing PowerBuilder.Application サーバ オブジェクトの関数とプロパティの詳 細については、445 ページの「オートメーション サーバ リファレンス」 を参照してください。 名前付きサーバの作成と使用 名前付きサーバを使用するには、以下のようにします。 アクセスするユーザ オブジェクトの作成 1 アクセスするクラス ユーザ オブジェクトを定義します。 2 作成したオブジェクトのためのランタイム ライブラリを構築しま す。 3 レジストリにサーバを登録します。 4 サーバとの接続、オブジェクトの作成、およびオブジェクトのメ ソッドとプロパティへのアクセスを行うクライアント アプリケー ションのコードを記述します。 名前付きサーバにおけるユーザ オブジェクトの定義は、 PowerBuilder.Application サーバ オブジェクトと同じです。 詳細については、428 ページの「アクセスするユーザ オブジェクトの 作成」を参照してください。 ランタイム ライブラ リの構築 名前付きサーバにおけるランタイム ライブラリの構築は、 PowerBuilder.Application サーバ オブジェクトと同じです。 詳細については、429 ページの「ランタイム ライブラリの構築」を参 照してください。 サーバの登録 425 ページの「ユーザ オブジェクトの登録」で説明したように、サー バを登録するには、オートメーション サーバ プロジェクト ウィザー ドを使用します。 1 つのユーザ オブジェクトではなく、サーバを登録するには、コンポー ネントとして PowerBuilder.Application を選択します。425 ページの 「ユーザ オブジェクトの登録」で説明したように操作を行い、レジス トリにレジストリ更新ファイルを取り込みます。名前付きサーバのタ イプ ライブラリ ファイルを作成する必要はありません。 アプリケーション テクニック 433 名前付きサーバの作成と使用 サーバとユーザ オブ ジェクトをアクセスす るクライアント アプ リケーションのコード の記述 クライアント アプリケーションで、名前付きサーバのセッションを確 立するには、以下の記述を行います。 • 名前付きサーバへの接続 • ユーザ オブジェクトのインスタンスの作成 • ユーザ オブジェクトへのアクセス 以下の例は、その方法を表しています。例は、PowerBuilder のクライ アント アプリケーションのコードです。サーバ セッションの確立は失 敗することもあるので、プロセスのすべての手順でエラー チェックを 行う必要があります。 1 名前付きサーバに接続するために、OLEObject オブジェクト デー タ型の変数を 1 つ宣言します。次に、ユーザ インスタンスを作成 するために、OLEObject オブジェクト データ型の変数を追加宣言 します。 OLEObject ole_server, ole_analyze OLEObject オブジェクトの ExternalException イベントと Error イベ ントでエラーを扱う場合は、OLEObject オブジェクトを継承した標 準クラス ユーザ オブジェクトを使用します。 2 名前付きサーバを起動し、接続が確立されたことをチェックしま す。ステータス 0 は、セッションの確立が成功したことを示しま す。 ole_server = CREATE OLEObject li_status = ole_server.ConnectToNewObject & ("MyCompany.MyServer") IF li_status < 0 THEN MessageBox(" サーバが存在しません ", & " サーバに接続できません。") RETURN END IF 3 ユーザ オブジェクトのインスタンスを作成し、インスタンスの作 成が成功したかどうかをチェックします。このとき、ランタイム ライブラリ内にあるユーザ オブジェクトの名前を指定します。 ole_analyze = & ole_server.CreateObject("uo_analyze") IF IsNull(ole_analyze) THEN MessageBox(" オブジェクトが存在しません ", & " オブジェクト uo_analyze を作成できません。") RETURN END IF 434 PowerBuilder 第 20 章 4 PowerBuilder のランタイム オートメーション サーバ オートメーションの構文を使用してオブジェクトの関数やプロパ ティにアクセスします。以下にプロパティとメソッドの例を示し ます。 ld_avg = ole_analyze.uof_average() ole_analyze.Projection = TRUE li_status = ole_analyze.uof_RTFReport(REF ls_rpt) 5 アクセスが終了したら、サーバとの接続を解除し、ユーザ オブジェ クトのインスタンスを破棄します。また、この処理は、アプリケー ションを終了して実行することもできます。 DESTROY ole_analyze ole_server.DisconnectObject() DESTROY ole_server ユーザ オブジェクトとレジストリについての詳細 レジストリは、登録されたオブジェクトをアクセスするために、プロ グラムが必要とするレジストリ情報を格納しています。この情報は登 録データベースに格納されています。レジストリを更新するには、レ ジストリ エディタでレジストリ更新ファイル(REG)を読み取り、レ ジストリ情報を更新します。 識別子について GUID と CLSID グローバル一意識別子(GUID)は、128 ビットの整数で一意であることが 保証されています。 PowerBuilder.Application オブジェクトの GenerateGUID 関数を使用すると、独自に GUID を生成することもできます。GUID は、時刻、日付、使用しているネットワーク カードの固有の番号に基 づいて生成されます。ネットワーク カードを使用していない場合は、 Microsoft に 256 セットの GUID を問い合わせることができます。 GUID は、オブジェクトとタイプ ライブラリを一意に識別するための クラス識別子(CLSID)として使用されます。CLSID は、プログラム が使用するオブジェクトを確実に識別することができます。 ProgID プログラム識別子(ProgID)は、ローカルの環境で一意です。ProgID に使用でいる文字数の上限は 39 文字で、ピリオド以外の区切り記号を 使用したり、先頭文字に数字を使用したりすることはできません。 ProgID には、2 つの種類があります。 アプリケーション テクニック 435 ユーザ オブジェクトとレジストリについての詳細 • バージョン非依存 (Vergion-independent) ProgID ProgID にバージョ ン番号を含まない applicationname.objectname たとえば、MyApp.Application、MyApp.AnalysisUserObject などです。 • バージョン依存 (Vergion-dependent) ProgID ProgID に バ ー ジ ョ ン 番号を含む applicationname.objectname.versionnumber たとえば、MyApp.Application.1、MyApp.AnalysisUserObject.1 などです。 ほかの開発者がオブジェクト間の関係を理解できるように、アプリ ケーションとオブジェクトの命名規約は、一貫性があるようにする必 要があります。 レジストリに登録したオブジェクトに接続するために、ProgID を使用 します。バージョン非依存 ProgID を指定した場合、レジストリは現行 のバージョンのオブジェクトを呼び出します。 PowerBuilder.Application オブジェクトの GenerateRegFile 関数を使用す るときに、バージョン非依存 ProgID を引数に指定すると、関数の引数 に指定したバージョン番号を使用してバージョン番号のある ProgID が作成されます。 オブジェクトに関する情報の登録場所 オブジェクトに関する情報は、レジストリの以下のサブキーに登録さ れます。以下のセクションがあります。 • CLSID • Version-dependent ProgID • Version-independent ProgID • TypeLib(オプション) オブジェクトがどのように起動されても、このサブキーの参照によっ て、オブジェクトに関する情報が必ず見つかるようになっています。 キーとサブキー 436 PowerBuilder.Application オブジェクトの関数は、HKEY_CLASSES_ROOT キーを更新します。レジストリのほかのキーに対してもこの情報が反 映されます。 PowerBuilder 第 20 章 サブキー PowerBuilder のランタイム オートメーション サーバ オブジェクトの情報は、キーの下位レベルにあるサブキーに登録され ます。サブキーには、ファイル名などの値が含まれているものや、 NotInsertable などのように存在するだけで意味のあるものもあります。 各エントリとそのサブキーについては、以下で説明します。 ProgID 登録された ProgID の一覧は、レジストリの以下のキーの下にあります。 マイ コンピュータ \HKEY_LOCAL_MACHINE\SOFTWARE\CLASSES バージョン依存 ProgID とバージョン非依存 ProgID が表示されます。 ProgID は、オブジェクトの CLSID への相互参照です。 表 20-2: ProgID サブキー サブキー \CLASSES\ProgID \CLASSES\ProgID\CLSID 値 オブジェクトのコメント オブジェクトの CLSID バージョン依存 ProgID \CLASSES\ProgID\CurVer(バー ジョン 非依存 ProgID のみ) \CLASSES\ProgID\NotInsertable 空の文字列 CLSID CLASSES キーの下には、レジストリに登録されたすべての CLSID の 一覧を表示するサブキー CLSID があります。各 CLSID は、登録され たオブジェクトに関するすべての情報を記録しています。 マイ コンピュータ \HKEY_LOCAL_MACHINE\SOFTWARE\CLASSES\CLSID 表 20-3: CLSID サブキーの内容 サブキー \CLASSES\CLSID\{guid} \CLASSES\CLSID\{guid}\InProcServer32 \CLASSES\CLSID\{guid}\NotInsertable \CLASSES\CLSID\{guid}\PowerBuilder \CLASSES\CLSID\{guid}\Programmable \CLASSES\CLSID\{guid}\ProgID \CLASSES\CLSID\{guid}\TypeLib \CLASSES\CLSID\{guid}\ VersionIndependentProgID アプリケーション テクニック 値 オブジェクトの GUID PowerBuilder のランタイム DLL ファイル名とパス名 "" 何も設定されない。サブキーは、 オブジェクトの環境に関する情 報を格納する(次表を参照)。 "" 現行のバージョン番号が指定さ れたバージョン依存 ProgID タイプ ライブラリの CLSID バージョン非依存 ProgID 437 ユーザ オブジェクトとレジストリについての詳細 表 20-4: PowerBuilder サブキーの内容 \CLASSES\CLSID の下の PowerBuilder サブキー {guid}\PowerBuilder\BinaryType {guid}\PowerBuilder\LibraryList {guid}\PowerBuilder\ClassName TypeLib 値 ランタイム ライブラリの種類。 コンパイルされたマシン コード (MCODE)か Pcode オブジェクトを格納しているラ ンタイム ライブラリの名前 ランタイム ライブラリ内のオブ ジェクトの名前 CLASSES キーの下には、タイプ ライブラリのためのサブキーがあり ます。 マイ コンピュータ \HKEY_LOCAL_MACHINE\SOFTWARE\CLASSES TypeLib 438 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ 表 20-5: TypeLib サブキーの内容 サブキー \CLASSES\TypeLib\{guid} \CLASSES\TypeLib\{guid}\ VersionNum \CLASSES\TypeLib\{guid}\FLAGS \CLASSES\TypeLib\{guid}\HELPDIR 値 タイプ ライブラリの GUID タイプ ライブラリのバージョン番号 いくつかの言語に対応したタイプ ラ イ ブ ラ リ を 登 録 で き る よ う に、 バージョン番号から下にサブキー のツリーがある VersionNum\LanguageID\Win32 は、 32 ビットの Windows オペレーティ ング システム用タイプ ライブラリ ファイルのパスと名前を指定する 0 ヘルプ ファイルがあるディレクトリ レジストリ情報の作成 クライアント アプリケーションは、ユーザ オブジェクトにアクセスす るために必要な情報を取得するために、レジストリを使用します。レ ジストリは、PowerBuilder の実行環境とランタイム ライブラリがある ディレクトリのパス名を格納しています。また、オブジェクトのプロ パティとメソッドの情報を提供するタイプ ライブラリ ファイルの GUID と、そのディレクトリのパス名をレジストリに登録できます。タ イプ ライブラリが登録されていれば、エンド ユーザに OLE ブラウザ の機能を持つアプリケーションで、ユーザ オブジェクトを調べること ができます。ユーザ オブジェクトのインスタンス変数は、OLE ブラウ ザではプロパティとして表示されます。 PowerBuilder.Application サーバ オブジェクトには、レジストリ情報を 生成する機能があります。レジストリにオブジェクトを登録するには、 レジストリ更新ファイルが必要です。このファイルには、システムの 登録データベースに追加される情報が格納されます。タイプ ライブラ リの作成は任意です。ほかの開発者が、OLE ブラウザでオブジェクト のプロパティやメソッドを調べる場合に必要です。 以下の関数を使用するには、PowerBuilder.Application サーバ オブジェ クトに接続するクライアント アプリケーションを実行する必要があ ります。開発環境で、クライアント アプリケーションを実行すること ができます。 アプリケーション テクニック 439 ユーザ オブジェクトとレジストリについての詳細 以下の関数は、レジストリ情報を生成します。 • GenerateGUID 関数 グローバル一意識別子(GUID)を生成します。 GUID は、オブジェクトやそのオブジェクトのタイプ ライブラリ の CLSID として使用します。 レジストリ エディタ(REGEDT32.EXE)で 取り込めるレジストリ更新ファイルを生成します。レジストリ更 新ファイルには、PowerBuilder.Application サーバ オブジェクトの プロパティ、ユーザ オブジェクトの GUID、クラス名などが記述 されています。 • GenerateRegFile 関数 • GenerateTypeLib 関数 タイプ ライブラリ ファイルを生成します。 タイプ ライブラリは、ユーザ オブジェクトのメソッドやプロパ ティ情報などが記述されています。 開発者は、以下の例で示されるように、これらの関数を使用できます。 また、InstallShield のようなインストール アプリケーションを使用して レジストリ情報を作成することもできます。 配布とレジストリ ローカル マシンで作成したレジストリ ファイルは、ローカル マシン にオブジェクトを登録するために使用できます。ファイル(オブジェ クトが格納されているライブラリとタイプ ライブラリ)のパス名はマ シン固有で、ほかのマシンには適用できません。オブジェクトを配布 する場合は、エンド ユーザがインストールするときに指定するディレ クトリに応じて、レジストリ更新ファイルを修正するか、レジストリ 自身を更新する関数を呼び出す必要があります。 443 ページの「オートメーション サーバを使用するアプリケーション の配布」を参照してください。 レジストリ情報を生成 するためのスクリプト のサンプル このスクリプトは、いくつかのシングルライン エディット コントロー ルとチェックボックスから情報を取得し、レジストリ更新ファイルと タイプ ライブラリを生成します。スクリプトではバージョン情報を直 接指定していますが、エディット ボックスなどを使用してエンド ユー ザに入力させることもできます。 例で使用されているシングルライン エディット コントロールとチェッ クボックスは、表 20-6 のとおりです。 440 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ 表 20-6: シングルライン エディット コントロールとチェックボックスの例 データ入力用の コントロール sle_object sle_progid sle_desc sle_regfile sle_typelibfile sle_library cbx_machinecode 入力されるデータ PowerBuilder ライブラリ内のユーザ オブジェクトの名前 プログラム識別子 レジストリに表示されるオブジェクトのコメント 生成するレジストリ更新ファイルの名前 生成するタイプ ライブラリ ファイルの名前 オブジェクトを格納している PowerBuilder ランタイム ラ イブラリの名前 ランタイム ライブラリが、マシン コードと Pcode のどち らで作成されているか 以下のプログラムは、レジストリ更新ファイルとタイプ ライブラリを 生成します。 oleObject ole_pb string ls_reg_guid, ls_tlb_guid long ll_result, ll_res2 // PowerBuilder.Application サーバ オブジェクトとの接続 ole_pb = CREATE oleObject ll_result = ole_pb.ConnectToNewObject & ("PowerBuilder.Application") IF ll_result < 0 THEN MessageBox( " 接続できません ", & "PowerBuilder.Application への接続エラー ") RETURN END IF // 値となる PowerBuilder.Application サーバ オブジェクトの // プロパティの設定 ole_pb.LibraryList = sle_library.Text ole_pb.MachineCode = cbx_machinecode.Checked // オブジェクトとタイプ ライブラリの GUID の取得 ll_result = ole_pb.GenerateGUID( REF ls_reg_guid) ll_res2 = ole_pb.GenerateGUID( REF ls_tlb_guid) IF ll_result < 0 THEN MessageBox( "GUID を取得できません ", & " レジストリ ファイルの GUID の生成に失敗しました。") RETURN アプリケーション テクニック 441 ユーザ オブジェクトとレジストリについての詳細 ELSEIF ll_res2 < 0 THEN MessageBox( "GUID を取得できません ", & " タイプ ライブラリ ファイルの GUID の生成に失敗しました。 ") RETURN END IF // レジストリ更新ファイルを生成するために、エンド ユーザが // 入力した情報を使用 // GenerateRegFile 関数の引数 : // 有効な GUID // PB ライブラリのユーザ オブジェクトの名前 // レジストリにおける ProgID // メジャー バージョン、マイナー バージョン // コメント // レジストリ ファイルの名前 ll_result = ole_pb.GenerateRegFile( & ls_reg_guid, & sle_object.Text, & sle_progid.Text, & 1, 0, & sle_desc.Text, & sle_RegFile.Text ) IF ll_result < 0 THEN MessageBox(" レジストリ ファイルを生成できません ", & " 結果コードは " + String(ll_result) ) RETURN END IF // タイプ ライブラリを生成するために、レジストリ更新ファイルと // 一致する情報を使用 // GenerateTypeLib 関数の引数 : // // レジストリ ファイル内の GUID // PB ライブラリのユーザ オブジェクトの名前 // レジストリ ファイルにおける ProgID // ロケール、メジャー バージョン、マイナー バージョン // コメント // ヘルプ コンテキスト、ヘルプ ファイル // タイプ ライブラリの GUID // タイプ ライブラリ ファイルの名前 // レジストリ ファイルの名前 ll_result = ole_pb.GenerateTypeLib( & ls_reg_guid, & 442 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ sle_object.Text, & sle_progid.Text, & 0, 1, 0, & sle_desc.Text, & 0, "", & ls_tlb_guid, & sle_typelibfile.text, & sle_regfile.text) IF ll_result < 0 THEN MessageBox(" タイプ ライブラリ ファイルを生成できません ", & " 結果コードは " + String(ll_result) ) RETURN END IF オートメーション サーバを使用するアプリケーションの 配布 オブジェクトを配布する場合、すべてのファイルのインストール先の ディレクトリのパス名をレジストリに登録する必要があります。 PowerBuilder ランタ イム ファイル PowerBuilder.Application サーバ オブジェクトとオートメーション サー バとして登録されたユーザ オブジェクトを実行するには、エンド ユー ザのマシンに PowerBuilder の実行環境を配布する必要があります。 PowerBuilder の配布および必要なファイルの詳細については、第 9 部 「配布のテクニック」を参照してください。 レジストリは、実行環境を起動するために PowerBuilder の仮想マシン DLL(PBVM110.DLL)を PowerBuilder の実行ファイルのかわりに検索 します。配布時に、このファイルのディレクトリのパス名がレジスト リに登録されます。レジストリの情報が無効になるので、別のレジス トリにこのファイルを移動しないでください。 オブジェクトが格納さ れたライブラリとタイ プ ライブラリ レジストリは、オブジェクトが格納されているライブラリとタイプ ラ イブラリのディレクトリのパス名を登録します。 ローカル マシンでレジストリ更新ファイルを生成すると、パス情報は そのマシンの現行のファイルのパスを反映します。配布するときに、 以下のことができます。 アプリケーション テクニック 443 オートメーション サーバを使用するアプリケーションの配布 • レジストリ更新ファイルをカスタマイズする(レジストリ更新 ファイルは、編集可能なテキスト ファイル) • レジストリ更新ファイルを更新した後で、レジストリを変更する レジストリの変更には、PowerBuilder または Windows SDK の関数 をプログラムで使用する方法と、レジストリ エディタを使用して 手動で取り込む方法がある 複数のバージョンとアップデート 新しいバージョンのオブジェクトを再配布する場合、以前のバージョ ンの CLSID を再利用できます。また、新しい GUID を CLSID として レジストリに登録することもできます。どちらを選択するかは、バー ジョン間の互換性に依存します。 表 20-7: CLSID オプション CLSID のオプション GUID の再利用 新しい GUID の割り当て 条件 オブジェクトのインタフェースが同じで、既存の アプリケーションが古いバージョンと同じプロ パティと関数にアクセスできる場合 オブジェクトのインタフェースが変更され、既存 のアプリケーションが新しいバージョンをアク セスすると、アプリケーションがエラーを発生す る場合 既存のアプリケーションが古いオブジェクトをそのまま使用できるよ うに、新しい GUID を割り当てた場合は、新しい ProgID も必要になり ます。既存のアプリケーションがバージョン非依存 ProgID を参照して いて、新しいバージョンのオブジェクトも同じ ProgID である場合、既 存のアプリケーションは新しいオブジェクトに接続します。 サーバ オブジェクトを設計する場合は、そのオブジェクトの将来の発 展を考慮して現行のアプリケーションを設計する必要があります。 444 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ オートメーション サーバ リファレンス この節では、PowerBuilder.Application サーバ オブジェクトのプロパ ティと関数について説明します。 • PowerBuilder.Application サーバ オブジェクト • CreateObject 関数 • GenerateGUID 関数 • GenerateRegFile 関数 • GenerateTypeLib 関数 • 例外コード • レジストリ更新ファイルのサンプル PowerBuilder.Application サーバ オブジェクト 説明 PowerBuilder.Application サーバ オブジェクトは、オートメーション サーバです。オートメーション サーバを起動する OLE クライアント アプリケーションは、オートメーションとオートメーション オブジェ クト型をサポートする PowerBuilder やほかのクライアントになりま す。 以下のようにして、オート メーションを使用して PowerBuilder オブジェクトにアクセスできま す。 サーバを使用したオブジェクトへのアクセス 1 PowerBuilder をサーバ アプリケーションとして起動するように、 OLEObject オブジェクト データ型(クライアント アプリケーショ ンに用意されている同等のオブジェクト データ型)の変数を PowerBuilder.Application サーバ オブジェクトに接続します。 2 アクセスする PowerBuilder ランタイム ライブラリを指定するため に、PowerBuilder.Application サーバ オブジェクトのプロパティを 設定します。 3 ライブラリでクラス ユーザ オブジェクト(非ビジュアル)のイン スタンスを作成する関数を呼び出し、別の OLEObject オブジェク ト データ型の変数に、作成したインスタンスを代入します。 4 オートメーション構文を使用してユーザ オブジェクトのプロパティ と関数にアクセスします。 アプリケーション テクニック 445 PowerBuilder.Application サーバ オブジェクト レジストリにおけるオートメーション オブジェクト PowerBuilder.Application サーバ オブジェクトは、PowerBuilder システ ム オブジェクトの階層構造にあるクラスではありません。Windows の レジストリに登録されたオートメーション オブジェクトです。オブ ジェクト ブラウザで参照するには、 [OLE]タブを選択し、 [OLE オー トメーション オブジェクト]カテゴリを展開します。 プロパティ 表 20-8: PowerBuilder.Application のプロパティ プロパティ LibraryList MachineCode データ型 説明 String ランタイム ファイル(DLL か PBD)をセ ミコロン(;)で区切ったファイル名の一 覧。PowerBuilder.Application サーバ セッ ションでアクセスするオブジェクトが格 納されている Boolean すべてのランタイム ライブラリは、同じ 実行形式(マシン コードか Pcode)でなけ ればならない LibraryList プロパティの設 定は、オブジェクトのインスタンスを作成 する前だけに有効である。オブジェクトの インスタンスを作成した後で変更しても、 設定は無視される ランタイム ライブラリがマシン コードと Pcode のどちらで生成するかを指定する 値は以下のとおり • TRUE –(デフォルト)ライブラリはマ シン コードで生成される。デフォルト のファイル名の拡張子は DLL • FALSE – ライブラリは Pcode で生成さ れる。デフォルトのファイル名の拡張 子は PBD MachineCode プロパティの設定は、オブ ジェクトのインスタンスを作成する前だ けに有効である。オブジェクトのインスタ ンスを作成した後で変更しても、設定は無 視される 446 PowerBuilder 第 20 章 関数 PowerBuilder のランタイム オートメーション サーバ 表 20-9: PowerBuilder.Application の関数 関数 戻り値の データ型 CreateObject OLEObject GenerateGUID Long GenerateRegFile Long GenerateTypeLib Long 説明 OLE サーバ セッションに、クラス ユーザ オブジェクトのインスタンスを作成する。 クライアント セッションにオブジェクト の参照が戻る。クライアント アプリケー ションは、オートメーションの構文を使用 してオブジェクトのプロパティと関数に アクセスできる グローバル一意識別子(GUID)を生成し て文字列として返す。文字列は参照によっ て渡される文字列変数で識別される この関数を使用するには、ネットワーク カードが必要 レジストリ更新ファイルを生成する。レジ ストリ ファイルの内容は、オートメー ション サーバとして配布する PowerBuilder のオブジェクトに関する情報である タイプ ライブラリ ファイルを生成する。 タイプ ライブラリは、オートメーション サーバとして配布する PowerBuilder のオ ブジェクトに関する情報をほかの開発者 に提供する CreateObject 関数 機能 PowerBuilder.Application OLE サーバ セッションで、PowerBuilder クラ スのインスタンスを作成します。 対象 PowerBuilder.Application(オートメーション サーバ) 構文 { automationobject.}CreateObject ( classname ) 引数 automationobject アプリケーション テクニック 説明 PowerBuilder が OLE クライアント アプリケーションの 場合は、PowerBuilder.Application サーバ オブジェクトと 関連付けられた OLEObject オブジェクト データ型のイ ンスタンス変数。PowerBuilder 以外の OLE クライアン ト アプリケーションの場合は、そのアプリケーション が提供する同じ機能を持つ関数を呼び出すために、適切 な構文を使用する 447 CreateObject 関数 引数 classname 説明 作成するクラスの名前を指定した文字列。 PowerBuilder.Application サーバ オブジェクトの LibraryList プロパティで指定したライブラリ内に定義 されたクラスでなければならない 戻り値 OLEObject 型。オートメーションで有効なオブジェクトのインスタン スを返します。オブジェクトのインスタンスが作成できなかった場合、 CreateObject 関数は NULL 値を返します。 解説 OLE クライアント アプリケーションが Visual Basic の場合は、キーワー ド nothing を使用して CreateObject 関数が成功したかどうかを確認でき ます。 ランタイム ライブラリに格納されたオブジェクトの実行形式が指定 した MachineCode プロパティに対応しない場合、CreateObject 関数は NULL 値を返します。1 つの PowerBuilder.Application サーバ セッショ ンで作成されたすべてのオブジェクトのインスタンスは、同じ実行形 式(Pcode ま た は マ シ ン コ ー ド)で な け れ ば な り ま せ ん。1 つ の PowerBuilder.Application サーバ セッションで、複数のオブジェクトの インスタンスを作成する場合、作成したオブジェクトの参照を、ほか のオブジェクトの関数の引数に渡すことができます。 CreateObject 関数を呼び出す前に、CREATE 文を使用して OLEObject 型 のインスタンスを作成する必要はありません。 例 以下の例は、PowerBuilder.Application サーバ オブジェクトを起動し、 MYLIBRARY.DLL に格納されているオブジェクトを作成する PowerBuilder のスクリプトです。オブジェクトの作成が成功した場合は、 関数 uf_calc を呼び出します。この関数は、計算結果を変数 ld_result に 代入して、ステータス コードとして Long 型の戻り値を返します。 OLEObject PBObject, PBNVObject long ll_status double ld_result PBObject = CREATE OLEObject ll_status = PBObject.ConnectToNewObject & ("PowerBuilder.Application") IF ll_status = 0 THEN // エラー処理 ELSE PBObject.LibraryList = "c:\myappl\mylibrary.dll" PBObject.MachineCode = TRUE PBNVObject = CREATE OLEObject 448 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ PBNVObject = & PBObject.CreateObject("nvo_myobject") IF IsNull(PBNVObject) THEN // エラー処理 ELSE ll_status = PBNVObject.uf_calc & (12, 14, REF result) END IF DESTROY PBNVObject PBObject.DisconnectObject( ) END IF DESTROY PBObject 以下の例は、上記の PowerBuilder スクリプトと同じことを行う Visual Basic スクリプトです。 Dim Dim Dim Dim PBObject as object PBNVObject as object status as long result as double Set PBObject = _ CreateObject("PowerBuilder.Application") If PBObject is nothing then REM エラーの取り扱い Else PBObject.LibraryList = "c:\myappl\mylibrary.dll" Set PBNVObject = _ PBObject.CreateObject("nvo_myobject") If PBNVObject is nothing then REM エラーの取り扱い Else status = PBNVObject.uf_calc(12, 14, REF result) Set PBNVObject = nothing End if Set PBObject = nothing End if 関連項目 ConnectToNewObject アプリケーション テクニック 449 GenerateGUID 関数 GenerateGUID 関数 機能 グローバル一意識別子(GUID)を生成します。GUID は、オブジェク トとそのタイプ ライブラリを Windows のレジストリに登録するとき に、クラス識別子(CLSID)として使用します。オブジェクトとその タイプ ライブラリに対して、それぞれ GUID があります。 対象 PowerBuilder.Application(オートメーション サーバ) 構文 { automationobject.}GenerateGUID ( REF guidvariable ) 引数 automationobject REF guidvariable 説明 PowerBuilder が OLE クライアント アプリケーションの 場合は、PowerBuilder.Application サーバ オブジェクトと 関連付けられた OLEObject オブジェクト データ型のイ ンスタンス変数。PowerBuilder 以外の OLE クライアン ト アプリケーションの場合は、そのアプリケーション が提供する同じ機能を持つ関数を呼び出すために、適切 な構文を使用する 参照渡し(reference)の String 型変数。生成された GUID を文字列として返す GenerateGUID 関数は、構文がコンパイラによって チェックされていないオートメーションの関数として 呼び出されているので、guidvariable を参照渡しで渡す ために REF を指定する必要がある 戻り値 解説 450 Long 型。エラーが発生したかどうかを表すステータス コードを返しま す。値は以下のとおりです。 0 GUID は正常に生成されました。 -1 GenerateGUID 関数を呼び出すために必要な DLL をロードするこ とができませんでした。 -2 ネットワーク カードが見つからなかったので、GUID を生成する ことができませんでした。 -3 GUID の生成が失敗しました。 -9 予期せぬエラーが発生しました。 GenerateGUID 関数を使用する場合、以下のものが必要です。 • RPCRT4.DLL ファイル。この DLL ファイルの UuidCreate 関数を呼 び出します。DLL ファイルは、現行のパスに存在する必要があり ます。 • ネットワーク カード。関数は固有の値を生成するため、ネットワー ク カードの識別情報を使用します。 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ これらの条件が満たされないときは、Microsoft から GUID を入手して ください。 GUID は、書式(8-4-4-4-12 桁の数字)の文字列として表現できる Long 型の 16 進数の数値です。 {xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx} GUID は、アプリケーションが使用するオブジェクトを識別するため に、Windows レジストリで使用されます。レジストリに登録されたオ ブジェクトとそのタイプ ライブラリには、それぞれに対応する GUID があります。 オブジェクトがレジストリに登録されるまでは、PowerBuilder のオブ ジェクトに対してオートメーションを実行することはできません。 GenerateGUID 関数は、必要なレジストリ情報の作成を補助する関数です。 生成された GUID は、レジストリ更新ファイルを作成する GenerateRegFile 関数と GenerateTypeLib 関数に渡します。各ユーザのマシンの更新ファ イルを使用して、レジストリにオブジェクトを登録します。 オブジェクトに対して、新しい GUID を生成してレジストリを更新す ると、新しいレジストリ エントリが作成されます。レジストリ更新 ファイルに前と同じ GUID を使用した場合は、現行のレジストリのオ ブジェクトの情報は、新しい情報に置き換えられます。 オブジェクトを更新して配布する場合に、同じ GUID を使用して新し いオブジェクトに対するレジストリ更新ファイルを生成することがで きます。新しく更新されたオブジェクトのインタフェース(そのオブ ジェクトのプロパティと関数のシグネチャ)が更新前のオブジェクト と互換性がある場合、現行のアプリケーションは新しいオブジェクト に正常にアクセスできます。ただし、オブジェクトのインタフェース を変更した場合は、更新したオブジェクトに対する新しい GUID を使 用する必要があります。新しい GUID を使用すると、既存のアプリケー ションは、引き続き更新前のオブジェクトにアクセスできます。また、 新しいアプリケーションは新しいオブジェクトにアクセスできるの で、変更または新しい機能を使用できます。 PowerBuilder ツールを使用してユーザ オブジェクトを登録する方法に ついては、425 ページの「ユーザ オブジェクトの登録」を参照してく ださい。 例 以下の例では、PowerBuilder.Application サーバ オブジェクトと関連付 けを行い、GUID を生成します。 oleObject PBObject string ls_GUID long ll_result アプリケーション テクニック 451 GenerateRegFile 関数 PBObject = CREATE oleObject result = PBObject.ConnectToNewObject & ("PowerBuilder.Application") IF result < 0 THEN // エラー処理 ELSE ll_result = PBObject.GenerateGUID(REF ls_GUID) END IF 関連項目 GenerateRegFile GenerateTypeLib GenerateRegFile 関数 機能 オートメーション サーバとして配布するための PowerBuilder オブジェ クトに対するレジストリ更新ファイルを生成します。 対象 PowerBuilder.Application(オートメーション サーバ) 構文 { automationobject.}GenerateRegFile ( guid, classname, progid, majorversion, minorversion, description, outputfilename ) 引数 automationobject guid 説明 PowerBuilder が OLE クライアント アプリケーションの場 合は、PowerBuilder.Application サーバ オブジェクトと関 連付けられた OLEObject オブジェクト データ型のインス タンス変数。PowerBuilder 以外の OLE クライアント アプ リケーションの場合は、そのアプリケーションが提供す る同じ機能を持つ関数を呼び出すために、適切な構文を 使用する String 型。オブジェクトのグローバル一意識別子(GUID) 以下のように、生成された GUID を指定できる • GenerateGUID 関数の呼び出しによって生成 • 以前に生成された GUID を再利用(このオブジェクト は以前のバージョンを置き換える) classname 452 • マイクロソフト社から取得 String 型。オートメーション サーバとなるクラス ユーザ オブジェクトの名前。オブジェクトは LibraryList プロパ ティで指定したランタイム ライブラリ内になければなら ない PowerBuilder 第 20 章 引数 progid majorversion minorversion description outputfilename 戻り値 解説 PowerBuilder のランタイム オートメーション サーバ 説明 String 型。サーバ オブジェクトに接続するために使用す るプログラム識別子 Integer 型。サーバ オブジェクトのメジャー バージョン番号 Integer 型。サーバ オブジェクトのマイナー バージョン番号 String 型。サーバ オブジェクトのコメント。コメントは、 レジストリ エディタや OLE ブラウザ機能のあるアプリ ケーションで表示される String 型。OLE GenerateRegFile 関数が生成するレジスト リ更新ファイルの名前。レジストリが認識できるデフォ ルトのファイル名の拡張子は REG Long 型。エラーが発生したかどうかを表すステータス コードを返しま す。値は以下のとおりです。 0 レジストリ更新ファイルが正常に生成されました。 -1 メモリ割り当てのエラーが発生しました。 -2 出力ファイル名が指示されていません。 -3 出力ファイルが開けません。 -9 予期せぬエラーが発生しました。 GenerateRegFile 関数を呼び出す前に、PowerBuilder.Application サーバ オブジェクトと関連付け、その LibraryList プロパティと MachineCode プロパティに値を設定する必要があります。また、オブジェクトのク ラス識別子(CLSID)に使用する GUID も必要です。GUID の書式の詳 細については、450 ページの「GenerateGUID 関数」を参照してください。 レジストリ更新ファイルを生成した後は、オブジェクトのメソッドと プロパティの情報を提供するタイプ ライブラリ ファイルも生成する ことができます。455 ページの「GenerateTypeLib 関数」を参照してく ださい。 レジストリ更新ファイルのデフォルトの拡張子は、REG です。レジス トリ更新ファイルをダブルクリックすると、レジストリにオブジェク トを登録できます。オブジェクトが格納されているランタイム ライブ ラリとタイプ ライブラリ ファイルのディレクトリのパス名など、オブ ジェクトに関する情報がレジストリに登録されます。PowerBuilder ツールを使用してユーザ オブジェクトを登録する方法については、 425 ページの「ユーザ オブジェクトの登録」を参照してください。 例 以下の例では、GenerateRegFile 関数を呼び出しています。ご使用のア プリケーションでは、この GUID を使用しないでください。 long ll_result アプリケーション テクニック 453 GenerateRegFile 関数 ll_result = GenerateRegFile( & "{12345678-1234-1234-1234-123456789012}", & "uo_salary_formulas", "MyCompany.SalaryFormulas", & 1, 0, & "PowerBuilder functions for calculating salaries", & "c:\pbds\bizrules.reg") 以下の例では、PowerBuilder.Application サーバ オブジェクトと関連付 けを行い、レジストリ更新ファイルを生成するために必要なすべての プロパティ値を設定しています。 oleObject PBObject string ls_GUID long ll_result PBObj = CREATE oleObject result = & PBObj.ConnectToNewObject("PowerBuilder.Application") IF result < 0 THEN // エラー処理 ELSE PBObject.LibraryList = "c:\myappl\mylibrary.pbd" PBObject.MachineCode = FALSE ll_result = PBObject.GenerateGUID(REF ls_GUID) IF ll_result < 0 THEN // エラー処理 ELSE ll_result = PBObject.GenerateRegFile( ls_GUID, & "uo_myserverobject", "MyCompany.Object", & 1, 0, "My object's description", & "c:\myappl\object.reg") IF ll_result < 0 THEN // エラー処理 ELSE // タイプ ライブラリの生成 END IF END IF END IF 関連項目 454 GenerateGUID GenerateTypeLib PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ GenerateTypeLib 関数 機能 オートメーション サーバとして配布する PowerBuilder オブジェクトの タイプ ライブラリ ファイルを生成します。 対象 PowerBuilder.Application(オートメーション サーバ) 構文 { automationobject.}GenerateTypeLib ( classguid, classname, progid, localeid, majorversion, minorversion, description, helpcontext, helpfile, typelibguid, typelibfilename, registryfilename ) 引数 automationobject classguid classname progid localeid 説明 PowerBuilder が OLE クライアント アプリケーションの 場合は、PowerBuilder.Application サーバ オブジェクトと 関連付けられた OLEObject オブジェクト データ型のイ ンスタンス変数。PowerBuilder 以外の OLE クライアン ト アプリケーションの場合は、そのアプリケーション が提供する同じ機能を持つ関数を呼び出すために、適切 な構文を使用する String 型。オブジェクトのレジストリ ファイルを生成す るときに指定したグローバル一意識別子(GUID) String 型。PowerBuilder ランタイム ライブラリに格納さ れているオブジェクトの名前。指定したオブジェクトの タイプ ライブラリが生成される classname は、レジストリ ファイルを生成したときに指 定した名前と同じ名前でなければならない String 型。サーバ オブジェクトに接続するために使用す るプログラム識別子 progid は、レジストリ ファイルを生成したときに指定 した値と同じ値にする必要がある Long 型。オブジェクトの国別言語のためのロケール識 別子(LCID)。言語 ID(LANGID)は、マイクロソフト 株式会社が提供するマニュアルに定義されている PowerBuilder のカタログ データ型 LanguageID の値を指 定することも可能 majorversion Integer 型。サーバ オブジェクトのメジャー バージョン 番号 minorversion Integer 型。サーバ オブジェクトのマイナー バージョン 番号 description helpcontext String 型。サーバ オブジェクトのコメント Long 型。helpfile のヘルプ トピックのためのコンテキス ト ID。ヘルプ ファイルの目次ページを表示するには、 0 を指定する アプリケーション テクニック 455 GenerateTypeLib 関数 引数 helpfile typelibguid typelibfilename registryfilename 説明 String 型。サーバ オブジェクトのヘルプ トピックを格 納しているヘルプ ファイルの名前 String 型。レジストリに登録するタイプ ライブラリに対 するグローバル一意識別子(GUID) String 型。GenerateTypeLib 関数が生成するタイプ ライ ブラリ ファイルの名前。レジストリが認識できるデ フォルトのファイル名の拡張子は TLB String 型。GenerateRegFile 関数によって生成されたレジ ストリ更新ファイルの名前 タイプ ライブラリ ファイルだけを生成する場合は、 registryfilename に空の文字列を指定する 戻り値 Long 型。エラーが発生したかどうかを表すステータス コードを返しま す。値は以下のとおりです。 0 レジストリ更新ファイルが正常に生成されました。 2 出力ファイル名が指示されていません。 3 タイプ ライブラリの生成に失敗しました。 4 無効な名前か名前の設定中にエラーが発生しました。 5 無効なロケール識別子かロケール識別子の設定中にエラーが発生 しました。 6 タイプ ライブラリの GUID を CLSID に変換中にエラーが発生しま した。 7 無効な GUID か GUID を設定中にエラーが発生しました。 8 コメントの設定中にエラーが発生しました。 9 バージョンの設定中にエラーが発生しました。 10 ヘルプ コンテキストの設定中にエラーが発生しました。 11 ヘルプ ファイル名の設定中にエラーが発生しました。 14 LibraryList プロパティに指定したランタイム ライブラリには、ク ラスを見つけることができませんでした。 18 オブジェクトの GUID を CLSID に変換中にエラーが発生しまし た。 30 標準タイプ ライブラリのロード中にエラーが発生しました(OLE が正しくインストールされていません)。 31 IUnknown インタフェースにアクセス中にエラーが発生しました (OLE が正しくインストールされていません)。 456 PowerBuilder 第 20 章 解説 PowerBuilder のランタイム オートメーション サーバ 32 IDispatch インタフェースにアクセス中にエラーが発生しました (OLE が正しくインストールされていません)。 36 このタイプ ライブラリに関連付けられているレジストリ更新ファ イルを開いているときにエラーが発生しました。 タイプ ライブラリの登録は任意です。オブジェクトのプロパティとメ ソッドに関する情報を、OLE ブラウザ機能のあるアプリケーションで 表示する場合は、タイプ ライブラリが必要です。 タイプ ライブラリを登録する場合は、タイプ ライブラリ ファイルを 作成する前に、オブジェクトを登録するレジストリ更新ファイルが存 在する必要があります。タイプ ライブラリを生成する過程で、レジス トリ更新ファイルに情報を追加します。 レジストリ更新ファイルの生成については、452 ページの 「GenerateRegFile 関数」を参照してください。 GenerateTypeLib 関数の引数に指定する値は、すでに生成されたレジス トリ更新ファイルの値と同じでなければなりません。レジストリ更新 ファイルと同じ値を使用しない場合、どのオブジェクトにも関連付け られていない TypeLib サブキーがレジストリに作成されます。 GenerateTypeLib 関数を呼び出す前に、PowerBuilder.Application サーバ オ ブジェクトと関連付けを行い、 その LibraryList プロパティと MachineCode プロパティの値を設定する必要があります。さらに、オブジェクトの CLSID として使用される GUID(レジストリ更新ファイルを生成したと きに指定した GUID)とタイプ ライブラリの GUID が必要です。GUID の書式の詳細については、450 ページの「GenerateGUID 関数」を参照 してください。 レジストリ更新ファイルとタイプ ライブラリ ファイルを生成した後 は、オブジェクトをレジストリに登録できます。 オブジェクトをレジストリに登録すると、ライブラリ ファイルとタイ プ ライブラリ ファイルのディレクトリのパス名が格納されます。 LibraryList プロパティの値は、オブジェクトが格納されているランタ イム ファイルがあるディレクトリのパス名です。オブジェクトを登録 するときは、タイプ ライブラリ ファイルが、指定したディレクトリに ある必要があります。 例 以下の例は、GenerateTypeLib 関数を呼び出しています。ご使用のアプ リケーションでは、この GUID を使用しないでください。 long ll_result ll_result = GenerateTypeLib( & "{12345678-1234-1234-1234-123456789012}", & "uo_salary_formulas", "MyCompany.SalaryFormulas", & アプリケーション テクニック 457 GenerateTypeLib 関数 0, 1, 0, & "PowerBuilder functions for calculating salaries", & 0, "c:\pbds\bizrules.hlp", & "{12345679-1234-1234-1234-123456789012}", & "c:\pbds\bizrules.tlb", "c:\pbds\bizrules.reg") 以下の例は、PowerBuilder.Application サーバ オブジェクトと関連付け を行い、レジストリ更新ファイルを生成するために必要なすべての値 を設定しています。 oleObject PBObject string ls_GUID, ls_typelibGUID long ll_result PBObject = CREATE oleObject result = PBObject.ConnectToNewObject & ("PowerBuilder.Application") IF result < 0 THEN // エラー処理 RETURN -1 END IF PBObject.LibraryList = "c:\myappl\mylibrary.pbd" PBObject.MachineCode = FALSE // オブジェクトの CLSID のための GUID ll_result = PBObject.GenerateGUID(REF ls_GUID) IF ll_result < 0 THEN // エラー処理 RETURN -1 END IF // オブジェクトのタイプ ライブラリのための GUID ll_result = PBObject.GenerateGUID(REF ls_typelibGUID) IF ll_result < 0 THEN // エラー処理 RETURN -1 END IF // レジストリ更新ファイルの生成 ll_result = PBObject.GenerateRegFile( ls_GUID, & "uo_myserverobject", "MyCompany.Object", & 1, 0, "My object's description", & "c:\myappl\object.reg") IF ll_result < 0 THEN // エラー処理 458 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ RETURN -1 END IF // タイプ ライブラリの生成 ll_result = PBObject.GenerateTypeLib( ls_GUID, & uo_myserverobject", "MyCompany.Object", 0, 1, 0, & "My object's description", 0, & "c:\myappl\myhelp.hlp", ls_typelibGUID, & "c:\myappl\object.tlb", "c:\myappl\object.reg") IF ll_result < 0 THEN // エラー処理 RETURN -1 END IF 関連項目 GenerateGUID GenerateRegFile 例外コード PowerBuilder オートメーション サーバにアクセスするオートメーション クライアントでは、ある状況で、OLE の例外が発生する場合がありま す。エンド ユーザのアクションが例外を発生させた場合、PowerBuilder は例外の種類を識別する例外コードを、呼び出し元から渡された EXCEPINFO 構造体に値を設定します。PowerBuilder のクライアント ア プリケーションに対しては、ExternalException イベントの引数に例外 コードが渡されます。 クライアント アプリケーションは、PowerBuilder オートメーション サーバから、以下の例外コードを受け取ります。 表 20-10: PowerBuilder オートメーション サーバの例外コード コード 1001 1002 1003 1004 1005 1006 1007 1008 アプリケーション テクニック 意味 メモリの割り当てに失敗しました。 要求されたオブジェクトが、ライブラリ リストにありませんでした。 オブジェクトの作成に失敗しました。 バイナリ書式がバージョンと一致しないか、期限が過ぎています。 配列としてアクセスされたプロパティは、配列ではありませんでした。 スクリプトの実行中に予期せぬエラーが発生しました。 要求された名前と引数のデータ型に一致するメソッドが、1 つも 見つかりませんでした。 Variant 型の引数を変換することができませんでした。 459 レジストリ更新ファイルのサンプル レジストリ更新ファイルのサンプル 以下のレジストリ ファイルのサンプルには、uo_salarydata という名前 のクラス ユーザ オブジェクトの登録情報があります。 REGEDIT4 ;;;;;;;;;;;;;;;; ; ; MyCompany.SalaryData のためのレジストリ エントリ ; ; CLSID = {E022EF01-6789-11CF-92BF-00805F9236E9} ; ; PowerBuilder が生成したレジストリ ファイル ;;;;;;;;;;;;;;;; ; バージョン番号のないエントリ: [HKEY_CLASSES_ROOT\MyCompany.SalaryData] @="DataStore with functions returning salary statistics" [HKEY_CLASSES_ROOT\MyCompany.SalaryData\CLSID] @="{E022EF01-6789-11CF-92BF-00805F9236E9}" [HKEY_CLASSES_ROOT\MyCompany.SalaryData\CurVer] @="MyCompany.SalaryData.1" [HKEY_CLASSES_ROOT\MyCompany.SalaryData\NotInsertable" @="" ; バージョン番号に特定のエントリ: [HKEY_CLASSES_ROOT\AppID\{E022EF01-6789-11CF-92BF-00805F9236E9}] @="DataStore with functions returning salary statistics" [HKEY_CLASSES_ROOT\MyCompany.SalaryData.1] @="DataStore with functions returning salary statistics" [HKEY_CLASSES_ROOT\MyCompany.SalaryData.1\CLSID] @="{E022EF01-6789-11CF-92BF-00805F9236E9}" [HKEY_CLASSES_ROOT\MyCompany.SalaryData.1\NotInsertable] @="" ; CLSID エントリ: [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF00805F9236E9}] @="DataStore with functions returning salary statistics" "AppID"="{E022EF01-6789-11CF-92BF-00805F9236E9}" [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF-0805F9236E9}\ProgID] @="MyCompany.SalaryData.1" [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF00805F9236E9}\VersionIndependentProgID] @="MyCompany.SalaryData" [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF00805F9236E9}\InProcServer32] @="pbVM110.dll" 460 PowerBuilder 第 20 章 PowerBuilder のランタイム オートメーション サーバ "ThreadingModel"="Apartment" [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF 00805F9236E9}\NotInsertable] @="" [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF-00805F9236E9}\Programmable] @="" [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF00805F9236E9}\PowerBuilder\ClassName] @="uo_salarydata" [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF00805F9236E9}\PowerBuilder\LibraryList] @="D:\\pbserver.pbd" [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF00805F9236E9}\PowerBuilder\BinaryType] @="PCODE" ; タイプ ライブラリ登録エントリ: [HKEY_CLASSES_ROOT\CLSID\{E022EF01-6789-11CF-92BF-00805F9236E9}\TypeLib] @="{E022EF02-6789-11CF-92BF-00805F9236E9}" [HKEY_CLASSES_ROOT\TypeLib\{E022EF02-6789-11CF-92BF-00805F9236E9}\1.0] @="Type Library for DataStore with functions returning salary statistics" [HKEY_CLASSES_ROOT\TypeLib\{E022EF02-6789-11CF-92BF00805F9236E9}\1.0\9\Win32] @="D:\\pbserver.tlb" アプリケーション テクニック 461 レジストリ更新ファイルのサンプル 462 PowerBuilder 第 2 1 章 MAPI の使い方 この章について この章では、PowerBuilder アプリケーションで MAPI(Messaging Application Program Interface)を使用して電子メールを送受信する 方法について説明します。 内容 項目 MAPI について MAPI の使い方 ページ 463 464 MAPI について PowerBuilder は MAPI(Messaging Application Program Interface)を サポートします。これにより、アプリケーションは MAPI 準拠の 任意の電子メール システムを使用してメッセージを送受信できま す。 たとえば、PowerBuilder アプリケーションは以下を実行できます。 MAPI サポートの実装方法 アプリケーション テクニック • アプリケーションが実行した解析の結果をメールで送信する • ユーザが特定の操作を実行したときにメールを送信する • 情報を要求するメールを送信する • アプリケーションのユーザが必要とする情報を含むメールを 受け取る MAPI をサポートするために、PowerBuilder は 表 21-1 に示す項目 を提供します。 463 MAPI の使い方 表 21-1: PowerBuilder の MAPI サポート 項目 メール関連のシステム オブ ジェクト メール関連の構造体 名前 MailSession MailFileDescription MailMessage MailRecipient MailSession オブジェクトのオ ブジェクト関数 MailAddress MailDeleteMessage MailGetMessages MailHandle MailLogoff MailLogon MailReadMessage MailRecipientDetails MailResolveRecipient MailSaveMessage MailSend カタログデータ型 MailFileType MailLogonOption MailReadOption MailRecipientType MailReturnCode MAPI の使い方 MAPI を使うには、MailSession オブジェクトを作成してから、MailSession 関数を使用してそのオブジェクトを管理します。 例 MailSession PBmail PBmail = CREATE MailSession PBmail.MailLogon(...) ... // セッションの管理処理 : たとえば、メッセージの送信、 ... // メッセージの受信など PBmail.MailLogoff() DESTROY PBmail 464 PowerBuilder 第 21 章 MAPI の使い方 オブジェクト ブラウザを使用して、MailSession システム オブジェク トのプロパティと関数、メール関連の構造体のプロパティ、およびメー ル関連のカタログデータ型として有効な値についての詳細を取得でき ます。 オブジェクト ブラウザの使い方の詳細については、PowerBuilder の 『ユーザーズ ガイド』マニュアルを参照してください。MailSession 関 数の詳細については、 『PowerScript リファレンス』マニュアルを参照 してください。MAPI についての詳細は、各 MAPI に準拠したメール アプリケーションのマニュアルを参照してください。 アプリケーション テクニック 465 MAPI の使い方 466 PowerBuilder 第 2 2 章 外部関数とそのほかの拡張処理機能 の使い方 この章について この章では、PowerBuilder における外部関数の使い方とそのほか の拡張処理機能について説明します。 内容 項目 外部関数の使い方 ユーティリティ関数の使い方 Windows メッセージの送信 メッセージ オブジェクト コンテキスト情報 ページ 467 474 476 478 480 外部関数の使い方 外部関数は、PowerScript 以外の言語で記述され、ダイナミック ラ イブラリに保存されている関数です。Windows 上では、外部関数 はダイナミック リンク ライブラリ( DLL: Dynamic LinkLibrary)に 保存されます。 32 ビット プラットフォーム用の標準呼び出しシーケンスをサポー トする、任意の言語で書かれた外部関数を使用できます。 自分で書いたライブラリ内の関数を呼び出す場合は、その関数を エクスポートしなければならないので注意してください。このエ クスポートは、使用コンピュータによって関数プロトタイプまた はリンカ定義(DEF)ファイルで行います。 アプリケーション テクニック 467 外部関数の使い方 Use _stdcall 規約 C と C++ コンパイラは、通常いくつもの呼び出し規約をサポートしま す。呼び出し規約には、_cdecl (C プログラム用のデフォルトの呼び出 し規約)、_stdcallA(Windows API 呼び出し用の標準規約)、_fastcall、お よび thiscall があります。PowerBuilder は、多くのほかの Windows 開発 ツールのように、WINAPI(_stdcall)形式を使用してエクスポートされ るようにする外部関数を要求します。異なる呼び出し規約を使用する と、アプリケーション クラッシュを引き起こします。 PowerBuilder で使用される関数を含む独自の C や C++ DLL を作成する 時には、Windows API 呼び出し用の標準規約を使用することを確認し てください。たとえば、関数定義をエクスポートするために DEF ファ イルを使用している場合は、以下のように関数を宣言します。 LONG WINAPI myFunc() { ... }; PBNI の使い方 外部関数は PowerBuilder エクステンションでも呼び出せます。 PowerBuilder エクステンションは PowerBuilder Native Interface(PBNI) を使用して作成されます。PowerBuilder エクステンションの作成につ いての詳細は、『PowerBuilder ネイティブ インタフェース プログラ マーズ ガイドとリファレンス』マニュアルを参照してください。 PowerBuilder エクステンションの使い方についての詳細は、 『PowerBuilder エクステンション機能リファレンス』マニュアルを参 照してください。 外部関数の宣言 外部関数は、スクリプトで使用する前に宣言しておかなければなりま せん。 2 種類の外部関数 468 2 種類の外部関数が宣言できます。 • グローバル外部関数この関数は、アプリケーション内のどこから でも使用できます。 • ローカル外部関数この関数は、特定のウィンドウ、メニュー、ま たはユーザ オブジェクトに対して定義されます。 PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 ローカル外部関数はオブジェクトの定義の一部となるので、その オブジェクト自身のスクリプトの中で使用できます。さらに、こ の関数をほかのスクリプトで使用することも可能です。 外部関数の引数のデー タ型 外部関数を宣言するときは、引数のデータ型がその関数のソース定義 の中で宣言されたデータ型と一致しなければなりません。 外部関数のデータ型と PowerBuilder 内のデータ型の比較については、 『PowerScript リファレンス』マニュアルの外部関数の宣言と呼び出し に関する章を参照してください。 ❖ 外部関数を宣言するには 1 ローカル外部関数を宣言する場合には、関数を宣言したいオブ ジェクトを開きます。 2 スクリプト ビューでは、最初のドロップダウン リストから 「(Decleare)」を選択し、2 番目のドロップダウン リストから 「Global External Functions」または「Local External Functions」を選 択します。 3 関数宣言をスクリプト ビューに入力します。 使用する構文については、 『PowerScript リファレンス』マニュアル または下記の例を参照してください。 4 オブジェクトを保存します。 PowerBuilder は宣言をコンパイルします。構文エラーが存在する場 合には、エラー ウィンドウが開きます。その場合には、エラーを 修正しなければ、宣言を保存できません。 既存の関数の変更 スクリプト ビューでは、既存の外部関数の宣言を修正することもでき ます。 外部関数の宣言例 ここで、文字列と構造体の 2 つのパラメータを受け取る SimpleFunc と いう関数を保持する SIMPLE.DLL という C 言語のダイナミック ライ ブラリを作成したとします。以下のステートメントは、この参照で引 数を渡す関数を PowerBuilder で宣言します。 FUNCTION int SimpleFunc(REF string lastname, & REF my_str pbstr) LIBRARY "simple.dll" アプリケーション テクニック 469 外部関数の使い方 デフォルトでは、PowerBuilder は文字列引数を処理し、値を Unicode エ ンコーディングが使用されているものとして返します。SimpleFunc 関 数が引数として ANSI 文字列を渡す場合は、次の構文で関数を宣言す る必要があります。 FUNCTION int SimpleFunc(REF string lastname, & REF my_str pbstr) LIBRARY "simple.dll" & ALIAS FOR "SimpleFunc;ansi" Windows API 関数の 宣言 Windows の API には、 PowerBuilder から呼び出し可能な関数が 1,000 個 以上あります。以下の例は、32 ビットの Windows API ライブラリ KERNEL32.DLL、GDI32.DLL、および USER32.DLL の中の関数の宣言 例です。 Windows API の呼び出し いくつかの 32 ビット関数名の最後には、A(ANSI の略)または W(ワ イドの略)が付いています。PowerBuilder ではワイド関数名を使用し ます。 Windows の API 関数の全リストについては、Microsoft Windows ソフト ウェア開発キット(SDK)のマニュアルを参照してください。 PowerBuilder の宣言構文とスクリプトの例については、Sybase の Technical Documents のサイト http://www.sybase.com/support/techdocs/ で Windows API call を検索してみてください。 以下のステートメントは、名前で呼び出される任意のウィンドウのハ ンドルを取得する関数と、開いたオブジェクトのハンドルを解放する 関数を宣言します。 FUNCTION ulong FindWindowW(ulong classname, & string windowname) LIBRARY "User32.dll" FUNCTION boolean CloseHandle(ulong w_handle) & LIBRARY "Kernel32.dll" 以下のステートメントは、受け取った座標に基づいて円グラフを描く 関数を宣言します。 FUNCTION boolean Pie(ulong hwnd,long x1,long y1, & long x2,long y2,long x3,long y3,long x4, & long y4) LIBRARY "Gdi32.dll" 以下のステートメントは、IsZoomed という外部 C 関数を宣言します。 FUNCTION boolean IsZoomed(Ulong handle) LIBRARY "User32.DLL" 470 & PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 外部関数 IsZoomed を使用するスクリプトは、474 ページの「ユーティ リティ関数の使い方」に例として記載してあります。 これらの関数についての詳細は、MSDN Library のサイト http://msdn.microsoft.com/library/default.asp にある Microsoft のマニュアル を参照してください。 引数の受け渡し PowerBuilder では、外部関数を定義する際に、引数の受け渡しを参照 か値のどちらで行うかを指定できます。引数を参照(reference)で渡 す場合、外部関数はその引数のポインタを受け取るため、引数の内容 を変更できます。そして変更後の内容を、PowerBuilder に返します。一 方、引数を値(value)によって渡す場合、外部関数はその引数のコ ピーを受け取るため、そのコピーの内容しか変更できません。この場 合に変更されるのはローカル コピーだけで、オリジナルの引数の内容 は変更されません。 参照によって渡される引数の構文は以下のとおりです。 REF datatype arg 値によって渡される引数の構文は以下のとおりです。 datatype arg 数値データ型の受け渡し 以下のステートメントは、PowerBuilder で外部関数 TEMP を宣言しま す。この関数は整数値を返し、参照によって渡される整数値の引数を 必要とします。 FUNCTION int TEMP(ref int degree) LIBRARY "LibName.DLL" このステートメントは、C で記述すると以下のようになります。 int _stdcall TEMP(int * degree) 引数は参照によって渡されるため、この関数が引数の内容を変更する と、その変更内容は、PowerBuilder のオリジナルの変数値に直接影響 します。たとえば、C のステートメント *degree = 75 は、degree とい う引数を 75 に変更して、PowerBuilder に 75 を返します。 以下のステートメントは、PowerBuilder で外部関数 TEMP2 を宣言しま す。この関数は Integer 型を返し、値によって渡される Integer 型の引数 を必要とします。 アプリケーション テクニック 471 外部関数の使い方 FUNCTION int TEMP2(int degree) LIBRARY "LibName.DLL" このステートメントは、C で記述すると以下のようになります。 int _stdcall TEMP2(int degree) 引数は値によって渡されるため、関数は引数の内容を変更できます。 変更はすべて引数のローカル コピーに対して行われるので、 PowerBuilder の変数への影響はありません。 文字列の受け渡し PowerBuilder は、すべての文字列引数と戻り値が Unicode エンコーディ ングを使用するものとします。関数が ANSI エンコーディングの文字 列を使用する場合は、関数宣言に ALIAS FOR 句を追加して、セミコロ ンの後に ansi キーワードを付ける必要があります。たとえば、次のよ うになります。 FUNCTION string NAME(string CODE) LIBRARY "LibName.DLL" ALIAS FOR "NAME;ansi" 値による受け渡し 以下のステートメントは、PowerBuilder で C の外部 関数 NAME を宣言します。この関数は、値によって渡される Unicode エンコーディングの String 型の引数を取ります。 FUNCTION string NAME(string CODE) LIBRARY "LibName.DLL" C による同様のステートメントでは、この String 型が保持されている バッファをポインタで示します。 char * _stdcall NAME(char * CODE) この String 型は値によって渡されるため、この C 関数が変更できるの は引数 CODE のローカル コピーの内容だけで、PowerBuilder のオリジ ナルの変数には影響しません。 参照渡し PowerBuilder は自身のメモリにのみアクセスできます。した がって、外部関数は PowerBuilder に文字列のポインタを返すことがで きません(メモリ アドレスを返すことができません)。 値渡し、参照渡しにかかわらず、外部関数に文字列を渡すと、その文 字列のポインタが渡されます。値渡しでは、外部関数がその文字列に 行った変更内容は、PowerBuilder からアクセスすることができません。 しかし、参照渡しでは変更内容にアクセスすることができます。 以下のステートメントは、PowerBuilder で C の外部関数 NAME2 を宣言 したものです。この関数は、参照によって引き渡される String 型変数 を取り、String 型を返します。 472 PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 FUNCTION string NAME2(ref string CODE) LIBRARY "LibName.DLL" & C 言語によってこれを記述すると、引数が値で渡されるステートメン トと同じになります。 char * _stdcall NAME2(char * CODE) この場合、String 型引数は参照によって渡されるので、C の関数は引数 の内容とともに、PowerBuilder のオリジナルの変数の内容も変更でき ます。たとえば、Strcpy(CODE,STUMP) は CODE の内容を変数 STUMP に変更し、呼び出し側の PowerBuilder のスクリプトの変数の値も変数 STUMP の内容に変更します。 前例の関数 NAME2 でユーザ ID を引数として取って、それをそのユー ザの名前に置き換えるものとします。このとき、PowerScript の String 型変数 CODE が、返される値を保持するのに十分な大きさでなければ なりません。十分な大きさを確保するために、String 型変数を宣言した 後で、Space 関数を使用して、NAME2 関数が返す最大文字数と同数の ブランク(空白文字)をこの String 型変数に与えておきます。 ユーザ名に許される最大文字数が 40 バイトで、ユーザ ID が常に 5 バ イト である場合には、NAME2 関数を呼び出す前に、String 型変数 CODE に 35 個のブランクを追加しておきます。 String CODE CODE = ID + Space(35) . . . NAME2(CODE) Space 関数の詳細については、 『PowerScript リファレンス』マニュアル を参照してください。 C の関数への文字の受け渡し C の外部関数に渡された Char 型の変数は、 渡される前に C の Char 型に変換されます。Char 型変数の配列は、C の 同等の Char 型変数の配列に変換されます。 構造体に埋め込まれた Char 型変数の配列は、C の構造体に埋め込まれ た配列に変換されます。これは、埋め込みの String 型(C の構造体の String への埋め込みポインタとなります)とは異なります。 注意 可能なときは必ず、関数からの戻り値として String 型の変数を PowerBuilder に返してください。 アプリケーション テクニック 473 ユーティリティ関数の使い方 UNIX での外部関数とプログラムの呼び出し PowerBuilder カスタム クラス ユーザ オブジェクトを UNIX プラット フォーム上に EAServer コンポーネントとして配布する場合、サーバが 動作するオペレーティング システムでコンパイルされた共有ライブ ラリの外部関数を呼び出すことができます。ただし、Windows API の 呼び出しが発生する外部関数や、グラフィカル プロセスに依存する外 部関数を呼び出すことはできません。 UNIX 共有ライブラリにある関数を宣言するには、標準の PowerScript 構文を使用できます。たとえば、次のステートメントでは、Solaris の 標準 C ライブラリにある関数 getcwd を宣言します。 FUNCTION string getcwd(REF string buff, & unsigned int size) LIBRARY "/usr/lib/libc.so" アプリケーションでスクリプトから関数を呼び出す方法は、ほかの関 数を呼び出す方法と同じです。次の例では、space 関数は、getcwd に よって返されたディレクトリ名を保持するのに十分な領域を割り当て ます。 string ls_return, ls_directory ls_directory = space(100) . . . ls_return = getcwd(ls_directory, 100) ロード ライブラリ パスの更新 UNIX でコンポーネントが外部関数を呼び出す場合には、コンポーネ ントは、その関数が置かれている共有ライブラリを検出できなければ なりません。そのためには、ライブラリ パス環境変数を更新して、そ の共有ライブラリが置かれているディレクトリを追加する必要があり ます。 ユーティリティ関数の使い方 ユーティリティ関数は、Windows の情報を入手して外部関数に渡す手 段を提供するので、PowerScript の Send 関数の引数として使用できま す。表 22-1 に、PowerScript のユーティリティ関数を示します。 474 PowerBuilder 第 22 章 5 つのユーティリティ 関数 外部関数とそのほかの拡張処理機能の使い方 表 22-1: ユーティリティ関数 関数 戻り値 Handle UnsignedInt IntHigh UnsignedInt 目的 指定されたオブジェクトのハンドルを返す 指定された Long 型数値の上位ワードを返す UnsignedInt この関数は、外部関数やメッセージ オブジェク トの LongParm プロパティによって入手される Windows パラメータの値をデコードするときに 用いる 指定された Long 型数値の下位ワードを返す IntLow Long Long LongLong LongLong この関数は、外部関数やメッセージ オブジェク トの LongParm プロパティによって入手される Windows パラメータの値をデコードするときに 用いる 下位ワードと上位ワードを連結して、Long 型数 値にする Long 関数は、外部関数に値を渡すときに用いる 下位ワードと上位ワードを連結して、LongLong 型数値にする LongLong 関数は、外部関数に値を渡すときに用 いる 例 以下のスクリプトは、外部関数 IsZoomed を使用して、現行ウィンドウ のサイズが最大になっているかどうかテストします。このスクリプト は、Handle 関数を使用して、ウィンドウ ハンドルを IsZoomed に渡しま す。また、その結果を、sle_output という名前のシングルライン エディッ トに表示します。 boolean Maxed Maxed = IsZoomed(Handle(parent)) if Maxed then sle_output.Text = " 最大表示 " if not Maxed then sle_output.Text = " 通常の表示 " 以下のスクリプトは、ウィンドウ オブジェクトのハンドルを外部関数 FlashWindow に渡して、ウィンドウのタイトル バーを使用不可にし、し ばらくして使用可能に戻します。 // ループのカウンタ変数とウィンドウ オブジェクトのハンドルを // 宣言します。 int nLoop uint hWnd // PowerBuilder のウィンドウのハンドルを入手します。 hWnd = handle(This) // タイトル バーを使用不可にします。 FlashWindow (hWnd, TRUE) アプリケーション テクニック 475 Windows メッセージの送信 // しばらくそのままにします。 For nLoop = 1 to 300 Next // ウィンドウのタイトル バーを使用可能に戻します。 FlashWindow (hWnd, FALSE) Windows メッセージの送信 PowerBuilder で作成したウィンドウまたは外部ウィンドウ(たとえば、 外部関数で作成したウィンドウ)にメッセージを送るときは、Post 関 数または Send 関数を使用します。PowerBuilder イベントを発生させる には、EVENT 構文、TriggerEvent 関数、または PostEvent 関数を使用し ます。 Post 関数と Send 関 数の使い方 通常、Post 関数と Send 関数は、PowerBuilder イベントにはない Windows イベントを発生させるときに使用します。これらの関数は、イベント が発生するウィンドウのスクリプト、またはアプリケーションの任意 のスクリプトで使用できます。 Post 関数は非同期関数です。つまり、メッセージはウィンドウまたは コントロールのメッセージ キューに送られます。Send 関数は同期関数 であり、ウィンドウやコントロールが直接メッセージを受け取ります。 PowerBuilder 6.0 の時点では、PowerBuilder によってポストされたすべ てのイベントは、Windows のシステム キューとは別のキューによって 処理されていました。PowerBuilder がポストしたメッセージは、Windows がポストしたメッセージの前に処理されていました。 ウィンドウのハンドルの入手方法 ウィンドウのハンドルを入手するには、Handle 関数を使用します。2 つ の Integer 型の数値を結合してメッセージの Long 値を形成するときは、 Long 関数を使用します。 Handle 関数と Long 関数はユーティリティ関数 で、この章で前述しています。 PowerBuilder イベン トの発生方法 476 PowerBuilder イベントを発生させるには、表 22-2 に示した方法を使用 できます。 PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 表 22-2: PowerBuilder イベントを発生させる方法 使用するもの TriggerEvent 関数 PostEvent 関数 イベント呼び出し構文 説明 ウィンドウやコントロールのスクリプトの実行 中、指定したオブジェクトのイベントをただちに 起動する同期関数 非同期関数。イベントはウィンドウやコントロー ルのイベント キューに追加される ドット(.)表記を使用して、コントロールのイ ベントを直接呼び出す方法 3 つの方法とも、メッセージ キューをバイパスするので、Send 関数と Post 関数よりスクリプトの記述が簡単です。 以下の 3 つのステートメントはすべて、コマンドボタン cb_OK の Clicked イベントを起動します。これらのステートメントは、cb_OK が 配置されているウィンドウのスクリプトに記述されているものとしま す。 例 Send 関数では、Handle ユーティリティ関数を使用して、コマンドボタ ン cb_OK があるウィンドウのハンドルを入手します。また、Long 関数 を使用して、コマンドボタン cb_OK のハンドルと 0(BN_CLICK)を連 結し、オブジェクトとイベントを識別する Long 型の数値に変換しま す。 Send(Handle(Parent),273,0,Long(Handle(cb_OK),0)) cb_OK.TriggerEvent(Clicked!) cb_OK.EVENT Clicked() TriggerEvent 関数は、イベントを起動するオブジェクトを識別します。 Clicked イベントを起動するには、カタログデータ型の値 Clicked! を指 定します。 イベント呼び出しは、EVENT キーワードを使用して Clicked イベント を起動します。イベントを呼び出すときは、TRIGGER キーワードがデ フォルトです。Clicked イベントをポストする場合は、POST キーワー ドを使用します。 Cb_OK.EVENT POST Clicked() アプリケーション テクニック 477 メッセージ オブジェクト メッセージ オブジェクト メッセージ(Message)オブジェクトは、あらかじめ定義された PowerBuilder のグローバル オブジェクトです(デフォルトのトランザクション オブ ジェクトの SQLCA やエラー オブジェクトと同類です)。メッセージ オ ブジェクトは、PowerBuilder で定義されたイベントにない Microsoft Windows イベントを処理するスクリプ トの中で使用されます。 PowerBuilder で定義されたイベントにない Windows イベントが発生す ると、PowerBuilder はそのイベントに関する情報をメッセージ オブ ジェクトに保持します。 メッセージ オブジェ クトのそのほかの用途 メッセージ オブジェクトは、以下のような場合にも用いられます。 • ウィンドウの開閉時に、ウィンドウ間でパラメータの受け渡しを するため 詳細については、『PowerScript リファレンス』マニュアルの OpenWithParm、OpenSheetWithParm、および CloseWithReturn の各関 数の説明を参照してください。 • TriggerEvent 関数や PostEvent 関数で、オプションのパラメータが使 用された場合でも、イベントに情報を渡すため 詳細については、 『PowerScript リファレンス』マニュアルを参照し てください。 メッセージ オブジェ クトのカスタマイズ アプリケーションで使用しているグローバル メッセージ オブジェク トは、組み込みの Message オブジェクトを継承した標準クラス ユーザ オブジェクトを定義することによってカスタマイズできます。その ユーザ オブジェクトでは、新たなプロパティ(インスタンス変数)や 関数の追加が可能です。アプリケーションの必要に応じて、ユーザ定 義プロパティの設定や関数の呼び出しが行えます。 標準クラス ユーザ オブジェクトの定義の詳細については、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください。 メッセージ オブジェクトのプロパティ メッセージ オブジェクトの最初の 4 つのプロパティは、Microsoft Windows のメッセージ構造体の最初の 4 つのプロパティに対応しま す。 478 PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 表 22-3: メッセージ オブジェクトのプロパティ プロパティ Handle データ型 用途 Integer Number Integer WordParm UnsignedInt LongParm Long DoubleParm StringParm PowerObjectParm Double Processed Boolean ウィンドウやコントロールのハンドル イ ベ ン ト を 識 別 す る 番 号。こ の 番 号 は Windows から送られる イベントの Word パラメータ。このパラ メータは Windows から送られる。パラメー タの値と意味はイベントによって異なる イベントの Long 型パラメータ。このパラ メータは Windows から送られる。パラメー タの値と意味はイベントによって異なる 数値または数値変数 文字列または String 型変数 構造体を含む PowerBuilder オブジェクト データ型 ユーザ定義イベントに対応するスクリプ トで設定された Boolean 型の値 String PowerObject • TRUE - スクリプトがイベントを処理し た。イベントの処理の後、デフォルト ウィンドウ プロシージャ (DefWindowProc 関数)を呼び出さない ReturnValue Long • FALSE -(デフォルト)イベントの処理 の後、DefWindowProc 関数を呼び出す Message.Processed プロパティが TRUE のと きに、開発者が Windows に戻す値 Message.Processed プロパティが FALSE の ときは、このプロパティは無視される メッセージ オブジェクトの値は、メッセージ オブジェクトに値が生成 されるイベント スクリプト内で使用します。たとえば、FileExists イベ ントに以下のスクリプトが記述されているとします。OpenWithParm で 応答ウィンドウを表示して、ファイルを上書きするかどうかを確認す るメッセージをユーザに表示します。ファイルを保存するかどうかは、 FileExists からの戻り値によって決まります。 OpenWithParm( w_question, & " 指定されたファイルはすでに存在します。" + & " このファイルを上書きしますか ?" ) IF Message.StringParm = "Yes" THEN RETURN 0 // ファイルを保存します ELSE RETURN -1 // 保存をキャンセルします END IF アプリケーション テクニック 479 コンテキスト情報 Microsoft Windows のメッセージ番号とパラメータの詳細については、 Microsoft Windows ソフトウェア開発キット(SDK)のマニュアルを参 照してください。 コンテキスト情報 PowerBuilder のコンテキスト機能を使用して、アプリケーションで一 定のホスト(PowerBuilder 以外)のサービスにアクセスできます。こ れは、COM QueryInterface に類似した PowerBuilder の実装機能です。 PowerBuilder では、以下のホスト サービスにアクセスできます。 • コンテキスト情報サービス • コンテキスト キーワード サービス • CORBACurrent サービス • エラー ロギング サービス • インターネット サービス • Secure Sockets Layer サービス • トランザクション サーバ サービス PowerBuilder は、現行の実行コンテキスト(ネイティブな PowerBuilder、 PowerBuilder のプラグイン、PowerBuilder ウィンドウの ActiveX、トラ ンザクション サーバ)に合わせて適切なサービス オブジェクトを作成 します。この機能により、アプリケーションで実行環境を最大限利用 できるようになります。たとえば、PowerBuilder ウィンドウのプラグ インでは、EMBED 構成要素に指定されたパラメータにアクセスでき ます。また、Internet Explorer で PowerBuilder ウィンドウの ActiveX を 実行しているときは、アプリケーションから ActiveX オートメーショ ン サーバにアクセスできるので、プログラムからブラウザにアクセス したり、その制御を行ったりすることができます。 コンテキスト機能では、ContextInformation、ContextKeyword、 CORBACurrent、ErrorLogging、Inet、SSLServiceProvider、 TransactionServer という 7 つの PowerBuilder サービス オブジェクトと InternetResult オブジェクトを使用します。コンテキスト機能はコンテ キスト オブジェクトと呼ばれることがありますが、PowerBuilder のシ ステム オブジェクトではありません。 480 PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 これらのオブジェクトの詳細については、 『オブジェクトとコントロー ル』マニュアルまたは PowerBuilder オブジェクト ブラウザを参照して ください。 サービスを使用可能に する方法 サービスを使用する前に、GetContextService 関数を呼び出して、そのサー ビスのインスタンスを作成します。この関数を呼び出すと、PowerBuilder はそのインスタンス化されたサービスへの参照を返します。サービス の関数を呼び出すときは、この参照をドット(.)表記で使用してくだ さい。 ❖ サービスを使用可能にするには 1 適切な型のインスタンス変数を設定します。 ContextInformation ContextKeyword CORBACurrent ErrorLogging Inet SSLServiceProvider TransactionServer 2 icxinfo_base icxk_base corbcurr_base erl_base iinet_base sslsp_base ts_base GetContextService 関数を呼び出して、インスタンス変数のインスタ ンスを作成します。 this.GetContextService("ContextInformation", & icxinfo_base) this.GetContextService("ContextKeyword", icxk_base) // EAServer で ContextKeyword のかわりに Keyword を使用 this.GetContextService("Keyword", icxk_base) this.GetContextService("CORBACurrent", & corbcurr_base) this.GetContextService("ErrorLogging", erl_base) this.GetContextService("Internet", iinet_base) this.GetContextService("SSLServiceProvider", & sslsp_base) this.GetContextService("TransactionServer",ts_base) CREATE 文の使い方 サービス オブジェクトは、PowerScript の CREATE 文でインスタンス化 できます。ただし、このステートメントでは、アプリケーションがど こで実行しているかに関係なく、常にデフォルト コンテキスト(ネイ ティブな PowerBuilder の実行環境)のオブジェクトが作成されます。 アプリケーション テクニック 481 コンテキスト情報 コンテキスト情報サービス コンテキスト情報サービスは、アプリケーションの実行コンテキスト に関する情報を入手するときに使用します。このサービスでは、アプ リケーションが PowerBuilder 実行環境で PowerBuilder ウィンドウのプ ラグインまたは PowerBuilder ウィンドウの ActiveX として実行してい るかどうかがわかるだけでなく、現行バージョンに関する情報も入手 できます。この情報を使えば、ディスプレイの特性やアプリケーショ ンの動作形態を修正できます。たとえば、プラグインや ActiveX とし て実行しているときに、コマンドボタン[閉じる]を非表示にできます。 さらに、Internet Explorer の PowerBuilder ウィンドウの ActiveX で実行 している場合、コンテキスト情報サービスは ActiveX のオートメー ション サーバ オブジェクトへの参照を返します。アプリケーションで この参照を使えば、Web ブラウザを制御する関数を呼び出せます。 コンテキスト情報への アクセス コンテキスト情報サービスを使用して、表 22-4 の情報にアクセスでき ます。 表 22-4: コンテキスト情報 項目 使用する関数 コンテキスト名 GetName 説明 戻り値はコンテキストによって異な る • デフォルト :PowerBuilder Runtime • ウィンドウのプラグイン : PowerBuilder Window Plug-in • ウィンドウの ActiveX:PowerBuilder Window ActiveX コンテキスト名 の略称 GetShortName 戻り値はコンテキストによって異なる • デフォルト :PBRUN • ウィンドウのプラグイン : PBWinPlugin • ウィンドウの ActiveX:PBRTX 482 会社名 GetCompanyName バージョン GetVersionName メジャー バー ジョン マイナー バー ジョン フィックス バージョン GetMajorVersion GetMinorVersion GetFixesVersion 会社名を返す(Sybase, Inc など) 完全なバージョン番号を返す (11.0.0.1 など) メジャー バージョン番号を返す (11.0 など) マイナー バージョン番号を返す(0 など) フィックス バージョン番号を返す(1 など) PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 ClassName 関数を使用して、オブジェクトのコンテキストを決定する こともできます。ClassName 関数の戻り値は、コンテキストによって 異なります。たとえば、ウィンドウのプラグインの戻り値は plugincontextinformation で、ウィンドウの ActiveX では rtxcontextinformation です。 ClassName 関数の使 い方 この情報は以下のようなさまざまな用途に使用できます。 • 実行コンテキストに基づいてアプリケーションの表示形態を修正する場合 たとえば、PowerBuilder ウィンドウ プラグインや PowerBuilder ウィ ンドウ ActiveX として実行しているときには[閉じる]ボタンを 非表示にできます。プラグインや ActiveX では、ウィンドウを閉 じると HTML ページに空のスペースが生成されます。 • コンテキストで現行バージョンをサポートしているかどうかを検証する 場合 たとえば、アプリケーションで管理バージョン 11.0.0.1 の機 能や修正部分が必要な場合は、コンテキスト情報サービスを使用 して、現行の実行コンテキストのバージョンを確認できます。 ❖ コンテキスト情報にアクセスするには 1 ContextInformation 型のインスタンスまたはグローバル変数を宣言 します。 ContextInformation 2 icxinfo_base GetContextService 関数を呼び出して、コンテキスト情報サービスを 作成します。 this.GetContextService("ContextInformation", icxinfo_base) 3 & 必要な場合は、コンテキスト情報サービス関数を呼び出します。 この例では、GetShortName 関数を呼び出して現行コンテキストを 確認し、さらに GetVersionName 関数を呼び出して現行バージョン を確認します。 String ls_name String ls_version Constant String ls_currver = "7.0.01" icxinfo_base.GetShortName(ls_name) IF ls_name <> "PBRun" THEN cb_close.visible = FALSE END IF icxinfo_base.GetVersionName(ls_version) IF ls_version <> ls_currver THEN MessageBox(" エラー ", & " 次のバージョンでなければなりません " + ls_currver) アプリケーション テクニック 483 コンテキスト情報 END IF Internet Explorer の バ ー ジ ョ ン 3.0 ま た は こ れ 以 降 の バ ー ジ ョ ン で PowerBuilder ウィンドウの ActiveX を実行している場合は、アプリケー ションでコンテキスト情報サービスの GetHostObject 関数を使用して、 ActiveX オートメーション サーバ オブジェクト(ホスト オブジェクト) への参照を入手できます。特に、インスタンス化されていない OLEObject 変数を GetHostObject に渡すと、IWebBrowserApp オートメーション サーバへの参照が返されます。 ActiveX オートメー ション サーバのアク セス アプリケーションでは、IWebBrowserApp のメソッドとプロパティを呼 び出し、アクセスできるので、以下のようなブラウザの動作にアクセ スし、その制御を行うことが可能です。 • [戻る] • [進む] • [ホーム] • [更新] • [お気に入り] • [終了] IWebBrowserApp インタフェース、メソッド、およびプロパティの詳細 については、Internet Explorer のマニュアルまたは Microsoft の Web サ イトを参照してください。 ❖ ActiveX オートメーション サーバにアクセスするには 1 ContextInformation 型および OLEObject 型のインスタンスまたはグ ローバル変数を宣言します。 ContextInformation icxinfo_base OLEObject iole_browser 2 GetContextService 関数を呼び出して、コンテキスト情報サービスを 作成します。 GetContextService("ContextInformation", icxinfo_base) 3 & GetHostObject 関数を呼び出して、 ActiveX オートメーション サーバ への参照を設定します。 Integer li_rtrn li_rtrn = icxinfo_base.GetHostObject(iole_browser) IF li_rtrn = 1 THEN sle_host.Text = "GetHostObject 成功 " 484 PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 ELSE sle_host.Text = "GetHostObject 失敗 " END IF 4 必要な IWebBrowserApp の関数を呼び出します。この例では、Navigate 関数を呼び出して、Sybase のホーム ページを表示するデフォルト の Web ブラウザを開きます。 IF IsValid(iole_browser) THEN iole_browser.Navigate & ("http://www.sybase.com", 0, 0, 0) END IF コンテキスト キーワード サービス 現行コンテキストの環境情報にアクセスするには、コンテキスト キー ワード サービスを使用します。デフォルト環境の場合、このサービス はホストのワークステーションの環境変数を返します。PowerBuilder ウィンドウ プラグインでは、このサービスを使用すると、プラグイン の Embed 構成要素に指定されているパラメータにアクセスできます。 EAServer 内で実行するときには、キーワード サービスを使用して、固 有のコンポーネントのプロパティ値を取得できます(AIX を除くすべ ての EAServer プラットフォームにおいて、GetContextService 関数内の 文字列パラメータとして Keyword を使用する必要があります)。 EAServer でコンテキスト キーワード サービスを使用する方法の詳細 については、546 ページの「コンポーネント プロパティへのアクセス」 を参照してください。 環境変数のアクセス PowerBuilder の実行環境(デフォルトのコンテキスト)で実行してい る場合、このサービスを使用して環境変数を戻します。 ❖ 環境変数にアクセスするには 1 ContextKeyword 型のインスタンスまたはグローバル変数を宣言し ます。戻り値を保持する String 型の可変長配列も宣言します。 ContextKeyword icxk_base String is_values[ ] 2 GetContextService 関数を呼び出して、コンテキスト情報サービスを 作成します。 this.GetContextService("Keyword", icxk_base) アプリケーション テクニック 485 コンテキスト情報 3 GetContextKeyword 関数を呼び出して、必要な環境変数にアクセス します。この例では、GetContextKeyword 関数を呼び出して現行ア プリケーションの Path を確認します。 icxk_base.GetContextKeywords("Path", is_values) 4 戻り値の配列から値を抽出します。環境変数にアクセスする場合、 配列の構成要素は常に 1 つだけにしなければなりません。 MessageBox("Path", "Path is:" + is_values[1]) Embed 構成要素には追加のユーザ指定パラメータを入れることが可能 です。また、Embed 構成要素では、各パラメータに 2 つ以上の値を持 たせることが可能です。 Embed 構成要素パラ メータのアクセス PowerBuilder ウィンドウ プラグインのコンテキストで実行している場 合、キーワード サービスは、Embed 構成要素に指定されたパラメータ へアクセスするときに使用します。指定されたパラメータが見つから ない場合、このサービスは指定されたパラメータと環境変数の照合を 試みます。 ❖ Embed 構成要素のパラメータにアクセスするには 1 ContextKeyword 型のインスタンスまたはグローバル変数を宣言し ます。戻り値を保持する String 型の可変長配列も宣言します。 ContextKeyword icxk_base String is_values[ ] 2 GetContextService 関数を呼び出して、コンテキスト情報サービスを 作成します。 GetContextService("Keyword", icxk_base) 3 GetContextKeyword 関数を呼び出します。この例では、 GetContextKeyword 関数を呼び出してユーザ指定パラメータ VALID の値にアクセスします。 icxk_base.GetContextKeywords("VALID", is_values) 4 戻り値の配列から値を抽出します。この例では、パラメータをリ ストボックスに表示します。 Integer li_count FOR li_count = 1 to UpperBound(is_values) lb_parms.AddItem(is_values[li_count]) NEXT 486 PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 CORBACurrent サービス クライアント アプリケーションおよび[OTS スタイル]としてマーク された EAServer コンポーネントは、CORBACurrent コンテキスト サー ビス オブジェクトの関数を使用して、EAServer トランザクションに関 する情報の作成、制御、および取得ができます。CORBACurrent オブ ジェクトは、CORBACurrent インタフェース用に定義された数多くの メソッドを備えています。 詳細については、588 ページの「クライアントとコンポーネントを区 別するトランザクション」を参照してください。 エラー ロギング サービス トランザクション サーバ内で動作している PowerBuilder オブジェクト によって生成されたエラーをログ ファイルに記録するには、ErrorLogging サービス オブジェクトのインスタンスを作成し、そのログ メソッドを 呼び出します。たとえば、次のようになります。 ErrorLogging erlinfo_base this.GetContextService("ErrorLogging", & erlinfo_base) erlinfo_base.log(" この文字列をログに書き込む ") コンポーネントが EAServer で動作している場合、エラーは EAServer ログに記録されます。コンポーネントが COM+ で動作している場合 は、エラーは Windows のシステム アプリケーション ログに記録され ます。 インターネット サービス インターネット サービスは、以下の用途に使用します。 • • デフォルトのブラウザで Web ページを表示する。HyperLinkToURL 関数は指定された URL を使ってデフォルトのブラウザを起動す る 指定されたページの HTML にアクセスする。GetURL 関数は HTTP Get を実行する • アプリケーション テクニック CGI、ISAPI、または NSAPI プログラムにデータを送信する。 PostURL 関数は HTTP Post を実行する 487 コンテキスト情報 インターネット サービスの HyperLinkToURL 関数を呼び出して、指定さ れた URL を使ってデフォルトのブラウザを起動します。 URL へのハイパーリ ンク接続 ❖ URL にハイパーリンクで接続するには 1 Inet 型のインスタンスまたはグローバル変数を宣言します。 Inet 2 iinet_base GetContextService 関数を呼び出して、インターネット サービスを作 成します。 THIS.GetContextService("Inet", iinet_base) 3 HyperLinkToURL 関数を呼び出して、 ブラウザの起動時に表示される ページの URL を渡します。 iinet_base.HyperlinkToURL & ("http://www.sybase.com") インターネット サービスの GetURL 関数を呼び出して HTTP Get を実 行し、指定された URL の生の HTML を入手します。この関数は、 InternetResult オブジェクトを介して生の HTML を返します。 URL の入手 ❖ HTTP Get を実行するには 1 Inet 型のインスタンスまたはグローバル変数を宣言します。子孫オ ブジェクト InternetResult(この例では、n_ir_msgbox)をデータ型と して使って、インスタンスまたはグローバル変数をもう 1 つ宣言 してください 。 Inet iinet_base n_ir_msgbox iir_msgbox 2 GetContextService 関数を呼び出して、インターネット サービスを作 成します。 THIS.GetContextService("Internet", iinet_base) 3 子孫オブジェクト InternetResult のインスタンスを作成します。 iir_msgbox = CREATE n_ir_msgbox 4 GetURL 関数を呼び出し、返されるページの URL と、子孫オブジェ クト InternetResult のインスタンスへの参照を渡します。 iinet_base.GetURL & ("http://www.sybase.com", iir_msgbox) GetURL 関数は実行を終了すると、子孫オブジェクト InternetResult で定義されている InternetData 関数を呼び出し、指定された URL の HTML を渡します。 488 PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 インターネット サービスの PostURL 関数を呼び出して HTTP Post を実 行し、データを CGI、ISAPI、または NSAPI プログラムに送信します。 この関数は、InternetResult オブジェクトを介して生の HTML を返しま す。 URL へのポスト ❖ HTTP Post を実行するには 1 Inet 型のインスタンスまたはグローバル変数を宣言します。子孫オ ブジェクト InternetResult(この例では、n_ir_msgbox)をデータ型と して使って、インスタンスまたはグローバル変数をもう 1 つ宣言 してください 。 Inet iinet_base n_ir_msgbox iir_msgbox 2 GetContextService 関数を呼び出して、インターネット サービスを作 成します。 THIS.GetContextService("Internet", iinet_base) 3 子孫オブジェクト InternetResult のインスタンスを作成します。 iir_msgbox = CREATE n_ir_msgbox 4 PostURL 関数への引数を設定します。 Blob lblb_args String ls_headers String ls_url Long ll_length ls_url = "http://coltrane.sybase.com/" ls_url += "cgi-bin/pbcgi80.exe/" ls_url += "myapp/n_cst_html/f_test?" lblb_args = Blob("") ll_length = Len(lblb_args) ls_headers = "Content-Length: " & + String(ll_length) + "~n~n" 5 PostURL 関数を呼び出し、実行するルーチンの URL、引数、ヘッ ダ、および子孫オブジェクト InternetResult のインスタンスへの参 照を渡します。 iinet_base.PostURL & (ls_url, lblb_args, ls_headers, 8080, iir_msgbox) PostURL 関数は実行を終了すると、子孫オブジェクト InternetResult で定義された InternetData 関数を呼び出し、指定されたルーチンか ら返された HTML を渡します。 アプリケーション テクニック 489 コンテキスト情報 GetURL 関数と PostURL 関数は、いずれも InternetResult オブジェクトの データを受け取ります。このオブジェクトは、インターネット経由で 返される非同期データを受け取り、キャッシュするバッファとして動 作します。データを全部受け取ると、この InternetResult オブジェクト はその InternetData 関数を呼び出すので、必要であれば、ここでデータ を上書きして処理できます。 InternetResult オブ ジェクトの使い方 InternetResult の子孫オブジェクトへの実装 この機能は、InternetResult 型の標準クラス ユーザ オブジェクトを作成 して実装します。この子孫ユーザ オブジェクトのそれぞれに、渡され た HTML を必要に応じて処理する InternetData 関数を定義してくださ い。 ❖ 子孫オブジェクト InternetResult を実装するには 1 InternetResult 型の標準クラス ユーザ オブジェクトを作成します。 2 以下のような新規ユーザ オブジェクト関数を宣言します。 3 • 名前 • アクセス レベル • 戻り値 Integer • 引数名 値渡しのデータ • 引数のデータ型 Blob InternetData パブリック 返された HTML を処理する InternetData 関数のコードを追加しま す。この例では、HTML を MessageBox に表示するだけです。 MessageBox(" 返された HTML", & String(data, EncodingANSI!)) Return 1 490 PowerBuilder 第 22 章 外部関数とそのほかの拡張処理機能の使い方 Secure Sockets Layer サービス PowerBuilder を使用すれば、EAServer への Secure Sockets Layer(SSL) 接続を設定できます。SSL プロトコルでは、デジタル認証に基づく公 開鍵の暗号化と認証のアルゴリズムを使用して、安全に接続すること ができます。SSL は「ラッパー」プロトコルであり、ほかのプロトコ ル用のパケットは、SSL パケットの内部に埋め込むことによって保護 されます。たとえば、HTTPS は、各 HTTP パケットを SSL パケット内 に埋め込むことによって保護される HTTP です。同様に、IIOPS は、 SSL 内に埋め込まれた IIOP です。 SSLServiceProvider オブジェクトのインスタンスを使用して、クライア ントからサーバへの接続を確立します。詳細については、 『PowerScript リファレンス』マニュアルおよび第 26 章「PowerBuilder クライアント での SSL の使い方」を参照してください。 トランザクション サーバ サービス EAServer、COM+ などのトランザクション サーバ内で動作するオブ ジェクトのコンテキストに関する情報にアクセスするには、トランザ クション サーバ サービスを使用します。TransactionServer オブジェク トを使用すれば、トランザクションの動作をプログラムで制御したり、 トランザクション サーバ上の別のコンポーネントのメソッドにアク セスしたりすることができます。 詳細については、第 24 章「EAServer コンポーネントの構築」および ëÊ 27 èÕÅuCOM/COM+ ÉRÉìÉ|Å[ÉlÉìÉgÇÃç\ízÅv を参照してください。 アプリケーション テクニック 491 コンテキスト情報 492 PowerBuilder 第 6 部 分散アプリケーションの開発 第 6 部では、PowerBuilder で分散アプリケーションを構 築するためのツールとテクニックについて説明します。 PowerBuilder Enterprise 版のみ PowerBuilder で使用可能な多層アプリケーションを構築するた めのツールは、Enterprise 版でのみサポートします。 第 2 3 章 PowerBuilder を使った分散アプリ ケーション開発 この章について この章では PowerBuilder を使った分散アプリケーション開発の概 要を示します。 PowerBuilder Enterprise 版のみ 分散アプリケーション開発は、Enterprise 版でのみサポートされて います。 内容 項目 分散アプリケーションのアーキテクチャ サーバのサポート ページ 495 496 分散アプリケーションのアーキテクチャ 分散アプリケーション開発は、多階層アプリケーション開発とも 呼ばれ、自然な方法でアプリケーションで必要なビジネス ロジッ クからアプリケーションのユーザ インタフェース コンポーネン トを分離できます。ビジネス ロジックを中間層のサーバに集中す ることで、クライアントの作業負荷を軽減し、機密情報へのアク セス制御を行えます。 分散アプリケーションでは、クライアントとサーバは、連携して ビジネス ユーザのためのタスクを実行します。クライアントは、 ユーザとの対話をすべて処理し、中間層のサーバはクライアント に対してバックグラウンドのサービスを提供します。通常、中間 層のサーバがほとんどの処理とデータベース アクセスを行いま す。サーバのサービスを呼び出すには、クライアントは、サーバ に置かれたコンポーネント(またはオブジェクト)に関連付けら れているメソッド(または関数)を呼び出します。 アプリケーション テクニック 495 サーバのサポート 分割されたアプリケー ション エンタープライズ アプリケーションのクライアントサイドのロジッ クは、ネットワークの帯域幅を節約できるようにできるだけ小さく効 率的にする必要があります。このためには、アプリケーションをプレ ゼンテーション、ビジネス ロジック、データベース アクセスの 3 つに 分割します。データベースは、エンタープライズ システムの最下層に あり、組織の資産を保持し、またセキュリティ保護します。ビジネス ロジックは、中間層またはサーバに置かれます。プレゼンテーション は、ユーザのデスクトップ、つまり最上位層に配置されるか、ユーザ のデスクトップに動的にダウンロードされます。 サーバは、企業のビジネス ロジックの大多数の実行とセキュリティ保 護を担当します。このため、サーバは、ネットワーク中心のアーキテ クチャの重要なコンポーネントとなります。クライアントは、ビジネ ス ロジックを実行する中間層コンポーネントを呼び出して、サーバと 通信を行います。 Web アプリケーショ ン アーキテクチャ Web アプリケーションは分散型アーキテクチャの一種で、クライアン トは Web ブラウザでホストされます。PowerBuilder には、シン クライ アント ソリューションを提供する .NET Web フォームの配布、JSP ター ゲット、および Web データウィンドウなど、Web アプリケーションの 構築のためのテクノロジが複数用意されています。アプリケーション のアーキテクチャは、使用するテクノロジによって異なります。 詳細については、第 30 章「PowerBuilder での Web アプリケーション開 発」を参照してください。 サーバのサポート PowerBuilder の開発者は、Sybase EAServer、COM+、および別のアプ リケーション サーバのサービスを呼び出すクライアントを作成し、さ らに各サーバの内部でビジネス ロジックを実行するコンポーネント (またはオブジェクト)を作成できます。 また、PowerBuilder は、 J2EE 準拠のサーバで動作する Enterprise JavaBeans コンポーネント(EJB)のクライアントの作成もサポートしています。 EAServer 496 PowerBuilder と EAServer は完全に統合されました。PowerBuilder アプ リケーションは、EAServer コンポーネントのクライアントの役割を果 たします。さらに、EAServer は、中間層コンポーネントとして動作す る PowerBuilder カスタム クラス ユーザ(非ビジュアル)オブジェクト を持つことができます。 PowerBuilder 第 23 章 PowerBuilder を使った分散アプリケーション開発 EAServer は、PowerBuilder 仮想マシンのネイティブのホストとして機 能します。つまり、EAServer と PowerBuilder 非ビジュアル ユーザ オ ブジェクトは互いに直接通信できます。PowerBuilder で開発された EAServer コンポーネントは、PowerScript の使いやすさと柔軟性、およ び PowerBuilder のシステム オブジェクトのパワーをフルに活用できま す。 PowerBuilder で開発されたコンポーネントは、トランザクション、相 互運用性、およびインスタンス プールなどの機能を活用できます。 図 23-1 に示すように、どのタイプのクライアントでも、コンポーネン トの開発に使用された言語に関係なく、EAServer で動作するすべての タイプのコンポーネントにアクセスできます。 図 23-1: クライアントと EAServer 上のコンポーネント 詳細については、第 24 章「EAServer コンポーネントの構築」および 第 25 章「EAServer クライアントの構築」を参照してください。 J2EE サーバ J2EE(Java 2 Platform, Enterprise Edition)は、エンタープライズ アプリ ケーション開発用の公認 Java フレームワークです。J2EE アプリケー ションは、多層システムのさまざまなコンピュータにインストールさ れた別々のコンポーネントで構成されます。図 23-2 に、このシステ ムの 3 つの階層、すなわち、クライアント層、中間層、エンタープラ イズ情報システム(EIS)層を示します。中間層は、Web 層とビジネ ス層の 2 つの層で構成されると見なす場合もあります。 アプリケーション テクニック 497 サーバのサポート 図 23-2: J2EE クライアント層、中間層、EIS 層 アプリケーション クライアントやアプレットなどのクライアント コ ンポーネントは、クライアント層のコンピュータ上で動作します。Java サーブレットおよび JavaServer Pages(JSP)コンポーネントなどの Web コンポーネントは、Web 層の J2EE サーバで動作します。Enterprise JavaBeans(EJB)コンポーネントはビジネス コンポーネントであり、 ビジネス層の J2EE サーバで動作します。EIS 層は、リレーショナル データベース管理システム、エンタープライズ リソース プランニング アプリケーション、メインフレーム トランザクション処理、そのほか のレガシ情報システムを実行するサーバで構成されます。 PowerBuilder では、任意の J2EE 準拠サーバで動作する EJB コンポーネ ントのサービスを使用するクライアント アプリケーションを構築で きます。詳細については、第 29 章「EJB クライアントの構築」を参照 してください。 498 PowerBuilder 第 23 章 J2EE サーバのプラグ イン PowerBuilder を使った分散アプリケーション開発 PowerBuilder Application Server Plug-in がインストールされているサー ドパーティのアプリケーション サーバに、カスタム クラス ユーザ オ ブジェクトを配布することも可能です。Plug-in は、複数の Web サーバ をサポートする Sybase 製品です。これらのサーバに配布可能なアプリ ケーション サーバ コンポーネントおよび、クライアント アプリケーション の構築に使用できるプロキシの生成に役立つウィザードは PowerBuilder に組み込まれていますが、Plug-in 製品は個別に購入する必要がありま す。ウィザードと手法は、EAServer コンポーネントとクライアントの 構築に使用するという点で、とてもよく似ています。詳細については、 Sybase 製品マニュアル Web のサイト http://www.sybase.com/support/manuals/ で、PowerBuilder Application Server Plug-in のマニュアルを参照してく ださい。 COM+ PowerBuilder アプリケーションは、COM サーバへのクライアントとし て機能できます。このサーバは、PowerBuilder またはそのほかの COM 準拠型アプリケーション開発ツールを使用して作成できます。また、 図 23-3 に示すように、インプロセス サーバとしてリモート コンピュー タ上で、または COM+ で、ローカルに実行できます。 アプリケーション テクニック 499 サーバのサポート 図 23-3: COM コンポーネントの PowerBuilder クライアント ビジネス ロジックを含むカスタム クラス ユーザ オブジェクトを PowerBuilder で開発してから、そのオブジェクトを COM オブジェクト としてパッケージすることができます。PowerBuilder COM サーバに は、1 つまたは複数の PowerBuilder カスタム クラス ユーザ オブジェク トを組み込むことができます。ユーザ オブジェクトをユーザ オブジェ クト ペインタで作成してから、プロジェクト ペインタでサーバを構築 します。COM サーバをローカルの COM+ サーバに直接配布したり、プ ロジェクト ペインタで COM+ パッケージを作成したりすることもで きます。 詳細については、第 27 章「COM/COM+ コンポーネントの構築」およ び第 28 章「COM/COM+ クライアントの構築」を参照してください。 500 PowerBuilder 第 2 4 章 EAServer コンポーネントの構築 この章について この章では、PowerBuilder を使用して EAServer コンポーネントを 構築する方法について説明します。 内容 項目 EAServer コンポーネントの構築について 共有コンポーネントおよびサービス コンポーネントの操作 インスタンス プーリングのサポート トランザクションのサポート EAServer コンポーネントからデータベースへのアクセス コンポーネント インタフェースの定義 既存インタフェースの実装 別のサーバ コンポーネントのメソッドの呼び出し コンポーネント プロパティへのアクセス Web サービスとしての NVO の公開 コンポーネントのテストとデバッグ データの印刷 EAServer へのコンポーネントの配布 ページ 501 505 512 516 523 537 542 544 546 551 553 558 564 EAServer コンポーネントの構築について PowerBuilder には、カスタム クラス(非ビジュアル)ユーザ オブ ジェクトを開発して、それらを EAServer コンポーネントとして配 布する ための ツール がありま す。これ らのコ ンポーネ ントを Windows、UNIX、および Linux オペレーティングシステムで稼動 している EAServer ホストに配布できます。564 ページの「EAServer へのコンポーネントの配布」を参照してください。 アプリケーション テクニック 501 EAServer コンポーネントの構築について UNIX の制限 コンポーネントを UNIX または Linux サーバに配布することを予定し ている場合、これらのプラットフォーム上では PowerBuilder ランタイ ム ライブラリがグラフィック処理や、Windows アプリケーション プロ グラミング インタフェースの呼び出しをサポートしていないことに注 意してください。 ウィザードの使い方について PowerBuilder には、EAServer コンポーネントの開発と配布を容易にす るウィザードがいくつか用意されています。すべてのウィザードで EAServer プロジェクトを作成できます。 • ターゲット ウィザード 新規のターゲット、新規のアプリケーショ ン オブジェクト、新規のカスタム クラス ユーザ オブジェクト、お よび新規の EAServer プロジェクトを作成します。 • 既存のターゲットと新規の EAServer プ ロジェクトの中に、カスタム クラス ユーザ オブジェクトを新規作 成します。 • 1 つまたは複数のカスタム クラス ユーザ オブジェクトを選択する、1 つの EAServer プロジェクトを作成し ます。 オブジェクト ウィザード プロジェクト ウィザード 開発プロセスについて EAServer コンポーネ ントの作成手順 502 カスタム クラス ユーザ オブジェクトから EAServer コンポーネントを 作成して配布するには、次の手順で操作を進めます。 1 EAServer コンポーネント ターゲット ウィザードを使用して、新規 ターゲットにユーザ オブジェクトを新規作成します。既存のター ゲットで作業している場合は、この操作を行うかわりに、EAServer コンポーネント オブジェクト ウィザードを使用してオブジェク トを作成できます。これらのウィザードでは、新規ユーザ オブジェ クトを Web サービスとして公開するための情報を入力することも できます。 2 ユーザ オブジェクト ペインタで、生成されたユーザ オブジェクト に関数、イベント、およびインスタンス変数を追加します。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 3 オブジェクトのテストとデバッグを行います。 4 オブジェクトを EAServer に配布します。 PowerBuilder で開発した EAServer コンポーネントのテストまたは配布 を行うには、プロジェクト オブジェクトとプロジェクトを作成しま す。プロジェクト オブジェクトは、ターゲット ウィザード、オブジェ クト ウィザード、またはプロジェクト ウィザードで作成できます。 コンポーネントを配布するには、プロジェクト ペインタでプロジェク トを開き、必要な場合はプロジェクトの設定を修正して、プロジェク トを作成します。その後、EAServer コンポーネント ジェネレータに よって、コンポーネント インタフェースと PowerBuilder に実装された そのインタフェースがターゲット サーバに配布されます。 テストのために、ライブ編集を利用してユーザ オブジェクト ペインタ から自動的にプロジェクトを作成できます。この操作では、プロジェ クト ペインタからプロジェクトを作成する必要はありません。ユーザ オブジェクト ペインタでライブ編集を有効にすると、ユーザ オブジェ クトを保存するたびに EAServer コンポーネントのプロジェクトが作 成されます。ライブ編集についての詳細は、553 ページの「コンポー ネントのテストとデバッグ」を参照してください。 To-Do リスト EAServer のターゲット ウィザードかオブジェクト ウィザードを使用 して新規のユーザ オブジェクトを作成すると、オプションで To-Do リ ストを作成できます。ウィザードの最終ページにある[To-Do リスト の作成]チェックボックスをオンにすると、ウィザードは To-Do リス トにタスクを追加して、開発の全フェーズが遂行されるように開発者 の注意を促します。 アプリケーション サーバ プロファイルの作成 アプリケーション サーバ プロファイルは、システム レジストリに保 存されている名前付きパラメータ セットで、特定の EAServer または サードパーティ製アプリケーション サーバ ホストへの接続を定義し ます。ウィザードを使用してコンポーネントを作成する前に、コンポー ネントが配布されるサーバのプロファイルを作成する必要がありま す。 アプリケーション テクニック 503 EAServer コンポーネントの構築について アプリケーションサーバ プロファイル ダイアログボックスには、定義 済みのプロファイルが一覧表示されます。このダイアログボックスか ら、EAServer プロファイルの作成、編集、削除、およびテストを実行 できます。 EAServer とアプリケーション サーバのコンポーネントとプロキシの 各ウィザードには、 [EAServer プロファイルの選択]ページまたは[ア プリケーションサーバ プロファイルの選択]ページに[プロファイル の編集]ボタンが表示されます。このボタンをクリックすると、アプ リケーションサーバ プロファイル ダイアログボックスが表示されま す。このダイアログボックスでは、ウィザードを終了しないで、新し いプロファイルを追加したり、既存のプロファイルを編集したりする ことができます。 アプリケーションサーバ プロファイルの編集 ダイアログボックスの [プロファイル名]は編集できません。これは、プロファイルのほかの プロパティだけでなく、名前もプロジェクト オブジェクトに格納され るためです。プロジェクトの配布時に、レジストリにプロファイル名 が見つからない場合は、プロジェクト オブジェクトに格納されている プロファイル名が使用されます。 ❖ アプリケーションサーバ プロファイルを作成するには 1 パワーバーの[アプリケーションサーバ プロファイル]ボタンを クリックします。 アプリケーションサーバ プロファイル ダイアログボックスが表 示され、定義済みのプロファイルが一覧表示されます。 2 [追加]を選択します。 アプリケーションサーバ プロファイルの編集 ダイアログボック スが表示されます。 3 504 プロファイル名、サーバ名、ポート番号、ログイン名、およびパ スワード(必要な場合)を入力します。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 4 (オプション)[テスト]を選択して、接続の検証を行います。 5 [OK]をクリックして変更内容を保存し、ダイアログボックスを 閉じます。 アプリケーションサーバ プロファイル ダイアログボックスに、 新規プロファイル名が表示されます。アプリケーション サーバ プロファイルの値は、 HKEY_CURRENT_USER\Software\Sybase\PowerBuilder\11.0\Jagu arServerProfiles のレジストリに保存されます。 共有コンポーネントおよびサービス コンポーネントの操作 PowerBuilder で EAServer コンポーネントを作成するときには、スタン ダード コンポーネント、共有コンポーネント、またはサービス コン ポーネントのどれを作成するかをウィザードで選択できます。 共有コンポーネントについて EAServer によるプロ グラム変数領域の管理 EAServer アーキテクチャはコンポーネント指向です。各コンポーネン トは、それぞれの状態を保持しています。1 つのクライアントがサー バ上でいくつかの PowerBuilder オブジェクトをインスタンス化する と、EAServer は、オブジェクトのプログラム変数領域を別々に管理し ます。EAServer で動作する各 PowerBuilder ユーザ オブジェクトは、グ ローバル変数と共有変数について独自のコピーを保持しています。 PowerBuilder オブジェクトはそれぞれ共通の状態にはありません。し たがって、PowerBuilder オブジェクトどうしは、メソッド、EAServer の共有コンポーネント、サーバ ファイル、およびデータベースを介し てのみ通信できます。 クライアントが状態情報を共有できるように、EAServer は共有コン ポーネントをサポートします。共有コンポーネントを使用すれば、複 数のクライアントが同じコンポーネント インスタンスを共有できま す。 EAServer Manager および Management Console EAServer 5.x では、EAServer Manager を使用して EAServer のプロパ ティを管理できます。EAServer 6.x では、Sybase Management Console の EAServer Manager プラグインを使用します。 アプリケーション テクニック 505 共有コンポーネントおよびサービス コンポーネントの操作 PowerBuilder ウィザードで共有コンポーネントとしてマークすると、 Management Console のコンポーネントのプロパティの[General]ペー ジ、または EAServer Manager の[Instance]ページでコンポーネントを 共有としてマークした場合と同じ結果になります。EAServer では、コ ンポーネントの 1 つのインスタンスだけをインスタンス化できます。 クライアント(とそのほかのサーバ コンポーネント)は、共有コン ポーネントに対して、それがあたかも別の種類のコンポーネントであ るかのようにアクセスします。 EAServer 共有コン ポーネントを使用する 利点 EAServer 共有コン ポーネントと PowerBuilder 共有オ ブジェクト 共有コンポーネントを使うと、以下のことが可能になります。 • クライアント接続ごとに別々に取り出す必要がある共通データに 容易にアクセスできるようにする • データベース アクセスの数を減らすことによって、データベース サーバをほかの処理に使用できるようにする EAServer 共有コンポーネントとして提供する利点の多くは、 PowerBuilder 共有オブジェクトの場合と同じです。EAServer に配布する PowerBuilder コンポーネントは、PowerBuilder 共有オブジェクトに加えて、EAServer 共有コンポーネントに対してもクライアントの役目を果たせます。 EAServer 共有コンポーネントに対しては、PowerBuilder で実装されて いないクライアントとコンポーネントからアクセスできます。 しかし、EAServer は、PowerBuilder 共有オブジェクトを EAServer 共 有コンポーネントのようには扱いません。したがって、PowerBuilder 共有オブジェクトの操作に使用する関数(SharedObjectRegister や SharedObjectGet など)は、EAServer 共有コンポーネントでは動作しま せん。EAServer で動作している PowerBuilder コンポーネント内でこれ らの関数を呼び出そうとしても、そのリクエストは失敗します。 サービス コンポーネントについて サービス コンポーネントは、EAServer クライアントとそのほかの EAServer コンポーネントのバックグラウンド処理を行います。EAServer は、サーバの起動時にサービス コンポーネントをロードします。 いずれかの PowerBuilder ウィザードで、コンポーネントをサービス コ ンポーネントとしてマークした場合には、そのコンポーネントは配布 時にサービスとして EAServer にインストールされます。 EAServer 5.x では、サーバの com.sybase.EAServer.server.services プロパ ティを修正して、サーバのサービス リストにコンポーネントを追加す るのと同じです。 506 PowerBuilder 第 24 章 EAServer コンポーネントの構築 EAServer 6.x では、プロパティは Ant 環境設定ファイルで指定されま す。たとえば、EAServer とともにインストールされたサービス コンポー ネントは、EAServer6\bin デ ィ レ ク ト リ の default-service-components ファイルに設定されます。 EAServer 6.x でのサービス コンポーネントの作成と設定の詳細につい ては、Sybase 製品マニュアル Web のサイト http://infocenter.sybase.com/help/index.jsp?topic=/com.sybase.dc00548_0600/ht ml/easautoconfig/X1201010.htm で『Automated Configuration Guide』マ ニュアルを参照してください。 共有か非共有か サービス コンポーネ ントの関数 サービス コンポーネントを作成する場合は、ウィザードでサービス コ ンポーネントにマークを付けます。サービス コンポーネントの複数の インスタンスを使用したい場合は、プロジェクト ペインタで設定を変 更できます。プロジェクト ペインタの EAServer コンポーネント ジェ ネレータのプロパティ シートにある[コンポーネント]ページで、 [サービス インスタンス]スピン コントロールから使用したいインス タンスの数を選択します。インスタンスの数を複数に変更すると[同 時実行]と[自動的なデマケーション / 不活性化]がオンになるので、 注意してください。これは、EAServer でコンポーネントがスレッド実 行の問題に遭わないようにするためです。詳細については、次の「ス レッド実行の問題とコンポーネントの種類」を参照してください。 PowerBuilder ウィザードは、サービス コンポーネント用に 3 つの補助 関数を組み込みます。これらの関数は CTSServices::GenericServices イ ンタフェースに定義されており、サービスに関連付けられているバッ クグラウンド処理の動作を制御できます。 サービス コンポーネントがロードされた後、EAServer は Start 関数を呼び出します。この関数にロジックを追加すれば、サービ ス起動の初期設定を実行できます。 • Start • Run 最初に呼び出された Start 関数が戻った後、EAServer は Run 関数を呼び出します。Run 関数を使うと、反復タスクをバックグラ ウンド プロセスとして実行できます。Run 関数は、その実行を定 期的に一時停止するために、JagSleep C 関数を呼び出さなければ なりません。JagSleep 関数は、ほかのタスクを実行できるように CPU を解放します。JagSleep 関数を使用するには、PowerBuilder で JagSleep の外部関数を宣言します。関数の宣言に使用する構文を 次に示します。 subroutine JagSleep (Long seconds) LIBRARY "libjdispatch.dll" アプリケーション テクニック 507 共有コンポーネントおよびサービス コンポーネントの操作 • Stop この関数を使うと、Run 関数でコーディングされたバックグ ラウンド プロセスの実行も停止できます。EAServer を再起動する ことなくサービスを再開できるように、Stop、Start、および Run を 呼び出すサービス マネージャ クライアントをサービスに実装で きます。Stop 関数のスクリプトは、Start 関数で割り当てられたリ ソースの後処理も実行できます。 スレッド実行の問題とコンポーネントの種類 PowerBuilder コンポーネントの各インスタンスは独自のセッションを 実行しているため、各セッションではスレッドを 1 つしか実行できま せん。したがって、PowerBuilder コンポーネントのインスタンスの 1 つが、クライアントのリクエストを同時に複数実行することは不可能 です。ただし、同じコンポーネントの複数のインスタンスは、それぞ れ別のクライアントのリクエストを実行できます。コンポーネントを 作成すると、EAServer でのスレッドの処理方法に影響するいくつかの プロパティにデフォルト値が設定されます。 Thread Manager の使い方 EAServer Thread Manager では、より堅固なサービスの開発も可能です。 511 ページの「EAServer Thread Manager の使い方」を参照してください。 Concurrency プロパ ティ コンポーネントの複数のインスタンスを作成して複数のクライアント のリクエストを処理できるかどうかは、Concurrency プロパティによっ て 決 ま り ま す。com.sybase.jaguar.component.thread.safe プ ロ パ テ ィ を TRUE に設定するには、ウィザードかプロジェクト ペインタで[同時 実行]チェックボックスをオンにします。 スタンダード コンポーネントでは、コン ポーネントの複数のインスタンスでクライアントのリクエストを処理 することによって、パフォーマンスを向上できます。デフォルト設定 で は、ス タ ン ダ ー ド コ ン ポ ー ネ ン ト の Concurrency プ ロ パ テ ィ が チェックされますが、そのコンポーネントのインスタンスを 1 つしか 使用しない場合は、設定を変更することも可能です。 スタンダード コンポーネント 共有コンポーネント 共有コンポーネントの場合、コンポーネントのイ ンスタンスは常に 1 つしかアクティブになりません。したがって、ス レッドは 1 つしか実行できません。共有コンポーネントの[同時実行] チェックボックスは選択不可能で、オンにはなりません。 508 PowerBuilder 第 24 章 EAServer コンポーネントの構築 サービス コンポーネント 通常は、サービス コンポーネントは共有コン ポーネントとして処理されますが、サービス コンポーネントのインス タンスを複数作成して、パフォーマンスとスケーラビリティを向上さ せることも可能です。サービス コンポーネントの[コンポーネント] ページには、[同時実行]、 [自動的なデマケーション / 不活性化]、お よび[サービス インスタンス]の 3 つのオプションがあり、[サービ ス インスタンス]オプションはサービス コンポーネントでのみ変更で きます。 [サービス インスタンス]オプションを 2 以上に変更すると、 [同時実 行]チェックボックスと[自動的なデマケーション / 不活性化]チェッ クボックスがオンになります。必要であれば、サービス コンポーネン トの複数のインスタンスを作成し、各メソッドの呼び出し後、それら のインスタンスを非アクティブにできます。開発者がコンポーネント のインスタンスを明示的に非アクティブにするために[自動的なデマ ケーション / 不活性化]チェックボックスをオフにすると、 [サービス インスタンス]スピン コントロールは 1 にリセットされ、 [同時実行] チェックボックスがオフになります。 bind.thread、sharing、 および tx_vote プロパ ティ EAServer のスレッドの処理に影響するコンポーネント プロパティには、 ほかに sharing、tx_vote、および bind.thread の 3 つがあります。 Bind Object プロパティ(未使用) 付加的なプロパティである bind.object を使うと、クライアント スレッ ドを 1 つのインスタンス内で実行できるだけでなく、複数インスタン スの作成もサポートされます。このプロパティは、PowerBuilder コン ポーネント用には使用できないため、常に FALSE に設定されます。 bind.thread プロパティが TRUE に設定されているときは、コンポーネン ト インスタンスのメソッドは、そのインスタンスを作成したスレッド と同じスレッドで実行されなければなりません。ライブ編集を使用し てコンポーネントを作成している場合は、このプロパティを TRUE に 設定しなければなりません。UNIX サーバに配布されるコンポーネン トでは、スケーラビリティを向上させるために、このプロパティを FALSE に設定する必要があります。 アプリケーション テクニック 509 共有コンポーネントおよびサービス コンポーネントの操作 sharing プロパティでは、コンポーネントを共有するかどうかを識別し ます。このプロパティは、ウィザードで[スタンダード]を選択した ときは FALSE、[共有]または[サービス]を選択したときには TRUE に設定されます。PowerBuilder でこのプロパティを変更するには、プ ロジェクト ペインタで、サービス コンポーネントの[コンポーネン ト]タブ ページにある[サービス インスタンス]設定を変更する以 外、方法はありません。sharing プロパティか thread.safe プロパティの 一方が TRUE に設定されている場合は、もう一方のプロパティを FALSE に設定しなければなりません。 連続するメソッド呼び出しの間、アクティブなまま保たれるコンポー ネントのことを、ステートフル(状態を持つ)コンポーネントと呼び ます。インスタンス プーリングをサポートしていてメソッド呼び出し 後に非アクティブになるコンポーネントのことを、ステートレス(状 態を持たない)コンポーネントと呼びます。一般に、ステートレス コ ンポーネントで作成されたアプリケーションの方が、高いスケーラビ リティを実現できます。コンポーネントがメソッド呼び出し後に非ア クティブになるかどうかは、tx_vote プロパティによって決まります。 このプロパティが FALSE(ステートレス)に設定されるのは、ウィザー ドの[自動的なデマケーション / 不活性化]チェックボックスをオン にした場合またはプロジェクト ペインタの[コンポーネント]ページ で複数のインスタンスを選択した場合です。それ以外の場合、このプ ロパティは TRUE(ステートフル)に設定されます。ステートフル サー ビス オブジェクトのインスタンスは、1 つしか所有できません。 表 24-1 に、コンポーネントの種類によるデフォルト設定と変更できる 設定を示します。 510 PowerBuilder 第 24 章 EAServer コンポーネントの構築 表 24-1: スレッド処理プロパティ コンポーネ ント スタンダー ド 共有 サービス (単一インス タンス) サービス (複数インス タンス) bind.thread sharing thread.safe tx_vote FALSE、変更 FALSE、変更 TRUE、変更 FALSE、変更可 可 不可 可 FALSE、変更 TRUE、変更 FALSE、変更 可 不可 不可 FALSE、変更 TRUE、変更 FALSE、変更 可 不可 可 FALSE、変更 FALSE、変更 TRUE、変更 FALSE、変更可 可 不可 可 TRUE に変更し た 場 合、イ ン ス タンス数は 1 に、 sharing は TRUE に、thread.safe は FALSE に設定さ れる FALSE、変更可 FALSE、変更可 bind.thread、thread.safe、および sharing が TRUE に設定されているサー ビス コンポーネントを配布する場合は、実行時に thread.safe プロパ ティが自動的に無効化されます。 EAServer Thread Manager の使い方 Thread Manager は組み込みの EAServer コンポーネントで、EAServer コ ンポーネントのインスタンスを、クライアントのメソッド呼び出しが 独立して行われるスレッド内で実行できます。Thread Manager によっ て生成されたスレッドを使用して、ユーザとの対話と非同期に発生す る処理を実行できます。 たとえば、ファイルのインデックス作成という長い操作を開始するコ ンポーネント メソッドがあるとします。この場合、メソッドを使えば、 Thread Manager を呼び出して新しいスレッドで処理を開始し、即座に 復帰できます。 アプリケーション テクニック 511 インスタンス プーリングのサポート PowerBuilder コンポーネントの各インスタンスは独自のセッションを 実行し、それぞれのセッションは実行のスレッドを 1 つしかサポート しないため、Thread Manager を使用せずに停止や更新ができるサービ スを開発するのは不可能です。サービスの start メソッドと run メソッ ドは、サービスの処理を行うスレッドを生成します。サービスの stop メソッドは、Thread Manager の stop メソッドを呼び出して、スレッド を停止します。 Thread Manager の詳細については、EAServer のマニュアルを参照して ください。 インスタンス プーリングのサポート インスタンス プーリ ングの利点 EAServer コンポーネントは、オプションでインスタンス プーリングを サポートできます。インスタンス プーリングを利用すると、EAServer クライアントはコンポーネント インスタンスを再利用できます。イン スタンス プーリングは、コンポーネント インスタンスを繰り返し割り 当てることにより生じるリソースの枯渇を解消し、EAServer の全体的 なパフォーマンスを改善します。 ウィザードでのプーリ ング オプションの指 定 いずれかの PowerBuilder ウィザードを使用して EAServer コンポーネ ントを作成した場合には、コンポーネントに対して表 24-2 に示すいず れかのインスタンス プーリング オプションを指定できます。 512 PowerBuilder 第 24 章 EAServer コンポーネントの構築 表 24-2: EAServer コンポーネント プーリング オプション プーリング オプ ション 説明 [サポートする] クライアント使用のたびに必ずコンポーネントのプーリ ングを実行します。このオプションが選択された場合に は、コンポーネントに対して CanBePooled イベントは発 生しません。 このオプションをオンにすると、コンポーネントのプー リング プロパティが TRUE に設定されます。コンポーネ ントの[自動的なデマケーション / 不活性化]設定が有効 である場合には、メソッド呼び出しのたびにインスタン スがプールされます。[自動的なデマケーション / 不活性 化]設 定 が 無 効 で あ る 場 合 に は、コ ン ポ ー ネ ン ト が TransactionServer コンテキスト オブジェクトの SetComplete メソッドか SetAbort メソッドを呼び出したときに、イン スタンスがプールされます。 [サポートなし] デフォルトでは、クライアント使用後にコンポーネント プーリングは実行されません。ただし、CanBePooled イベ ントのスクリプトを作成してデフォルト動作を無効にす ることも可能です。CanBePooled イベントでは、特定のコ ンポーネント インスタンスをプールするかどうかをプロ グラムで指定できます。CanBePooled イベントのスクリプ トを作成した場合には、このイベントはクライアント使 用のたびに発生します。 このオプションをオンにすると、コンポーネントのプー リング プロパティが FALSE に設定されます。 プールされたインスタ ンスの状態の制御 インスタンス プーリングをサポートする EAServer コンポーネントを 作成した場合には、各クライアントがプールされたインスタンスの使 用を終了した後で、そのコンポーネントの状態をリセットしなければ ならないことがあります。 コンポーネントの状態を制御できるように、コンポーネントの有効期 間中に、EAServer は 表 24-3 に示すイベントを 1 つまたは複数発生さ せます。 表 24-3: コンポーネントの状態イベント イベント Activate CanBePooled Deactivate アプリケーション テクニック PBM コード PBM_COMPONENT_ACTIVATE PBM_COMPONENT_CANBEPOOLED PBM_COMPONENT_DEACTIVATE 513 インスタンス プーリングのサポート コンポーネントのプーリング オプションを[サポートする]に設定 (プーリング プロパティを TRUE に設定)した場合には、Activate イベ ントと Deactivate イベントのスクリプトを作成して、プールされたコ ンポーネントの状態をリセットする必要があります。コンポーネント がインスタンス変数、共有変数、またはグローバル変数の状態を保持 する場合には、この操作が必要です。 コンポーネントのプーリング オプションを[サポートしない]に設定 (プーリング プロパティを FALSE に設定)した場合には、CanBePooled イベントのスクリプトを作成して、特定のコンポーネント インスタン スをプールするかどうかを指定できます。CanBePooled イベントのス クリプトを作成した場合には、Activate イベントと Deactivate イベント のスクリプトも作成して、プールされたコンポーネントの状態をリ セットする必要があります。CanBePooled イベントのスクリプトを作 成しない場合には、コンポーネント インスタンスはプールされませ ん。 EAServer コンポーネントのターゲット ウィザードとオブジェクト ウィザードは、EAServer コンポーネントとして配布されるカスタム ク ラス ユーザ オブジェクトに、Activate イベントと Deactivate イベント を自動的に組み込みます。CanBePooled イベントのスクリプトを作成 したい場合は、このイベントを自分で追加する必要があります。その 場合には、イベントを正しい PBM コードにマップしてください。 Constructor と Destructor は 1 回起動されます インスタンス プーリングが有効である場合には、Constructor イベント と Destructor イベントは、コンポーネントに対して 1 回だけ起動され ます。Constructor イベントと Destructor イベントは、新しいクライア ントがコンポーネント インスタンスを使用するたびに起動されるの ではありません。したがって、プールされるコンポーネント インスタ ンスの状態をリセットするには、Constructor イベントと Destructor イ ベントではなく、Activate イベントと Deactivate イベントにロジックを 追加します。 インスタンス プール のタイムアウト 514 インスタンス プーリングによってクライアント応答時間を短縮でき ますが、サーバのメモリ使用量が増加することもあります。プール内 でインスタンスが休止状態を持続できる時間を秒単位で指定できま す。デフォルトは 600(10 分)です。休止状態のコンポーネント イン スタンスが使用しているリソースを解放するために、サーバは、指定 した時間が過ぎると休止状態のインスタンスを削除することができま す。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 PowerBuilder と EAServer におけるメモリの管理方法は、環境変数で設 定できます。詳細については、51 ページの「メモリ管理の設定」およ び テ ク ニ カ ル ド キ ュ メ ン ト EAServer/PowerBuilder Memory Tuning and Troubleshooting のサイト http://www.sybase.com/detail?id=1027319 を参照し てください。 コンポーネントの有効 期間 インスタンス プーリングの仕組みを理解するには、コンポーネント イ ンスタンスの有効期間(ライフサイクル)を理解する必要があります。 コンポーネントの有効期間中の動作を以下に示します。 1 一般に、コンポーネントは最初のメソッド呼び出しでインスタン ス化されます。PowerBuilder で開発されたコンポーネントがこのイ ンスタンス化の対象となった場合、コンポーネントが動作するた めの新しい PowerBuilder セッションが EAServer により作成されま す。 2 PowerBuilder セッションでは、EAServer コンポーネントを表す、 PowerBuilder 非ビジュアル オブジェクトのインスタンスを作成し ます。オブジェクトを作成すると、Constructor イベントが発生 します。 3 オブジェクトがインスタンス化された後、EAServer は非ビジュア ル オブジェクト上で Activate イベントを発生させ、オブジェクト が新しいクライアントによって使用されることをオブジェクトに 通知します。この時点で、コンポーネントは、自分自身が実行可 能な状態であることを確認しなければなりません。 4 次に、EAServer はコンポーネント上のクライアントによって呼び 出されたメソッドを実行します。 5 コンポーネントがその作業の完了を知らせると、EAServer は Deactivate イベントを発生させて、コンポーネントがその後処理を行えるよう にします。コンポーネントの[自動的なデマケーション / 不活性化] 設定が有効である場合には、各メソッド呼び出しの後で、Deactivate イベントが自動的に発生します。設定が無効である場合には、コ ンポーネントが TransactionServer コンテキスト オブジェクトの SetComplete メソッドか SetAbort メソッドを呼び出したときに、 Deactivate イベントを発生させます。 アプリケーション テクニック 515 トランザクションのサポート 6 プーリング オプションで[サポートしない]を選択するか、コン ポーネントのインスタンス プーリング プロパティを FALSE に設 定し、CanBePooled イベントのスクリプトも作成した場合には、 EAServer は、このイベントを発生させることによって、この時点 でプーリングできるかどうかをコンポーネントにたずねます。 CanBePooled イベントを発生させると、コンポーネント インスタン スは、プーリングを選択的に実行するか拒否できます。CanBePooled イベントの戻り値は、コンポーネント インスタンスがプールされ るかどうかを決定します。 戻り値が 1 である場合には、プーリングが有効です。戻り値が 0 である場合には、プーリングが無効です。CanBePooled イベントの スクリプトが作成されていない場合、デフォルトでは、インスタ ンスはプールされません。 プーリング プロパティが有効である場合の動作 プーリング オプションで[サポートする]を選択した場合、または コンポーネントのプーリング プロパティを TRUE に設定した場合 は、コンポーネント インスタンスは常にプールされ、CanBePooled イベントは発生しません。 7 非アクティブ化の後でインスタンスがプールされない場合には、 EAServer は Destructor イベントを発生させます。次に、PowerBuilder オブジェクトを破棄し、実行時セッションを終了させます。 トランザクションのサポート EAServer のトランザ クション サポートの 利点 516 PowerBuilder で開発する EAServer コンポーネントは、EAServer トラン ザクションに関与できます。EAServer トランザクションは、その境界 と結果が EAServer によって決定されるトランザクションです。コン ポーネントにマークを付けることによって、トランザクション サポー トを提供するコンポーネントを判別できます。コンポーネントがトラ ンザクション サポートを提供する場合には、EAServer は、コンポーネ ントのデータベース操作がトランザクションの一部として実行される ことを保証します。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 1 つの EAServer トランザクションに複数の EAServer コンポーネント が関与できます。EAServer では、関与するコンポーネントによるデー タベース変更内容すべてのコミットまたはロールバックが確実に完了 します。EAServer トランザクションを使用するコンポーネントを定義 すれば、トランザクションに関与するコンポーネントによって実行さ れるすべての作業は意図したとおりに行われることを保証できます。 コンポーネントによる トランザクション サ ポートの指示 各 EAServer コンポーネントには、コンポーネントが EAServer トラン ザクションにどう関与するかを指示するトランザクション属性があり ます。PowerBuilder で EAServer コンポーネントを開発する場合には、 ウィザードでトランザクション属性を指定できます。表 24-4 に、オプ ションを示します。 表 24-4: トランザクション属性オプション トランザクションの 種類 [サポートなし] [トランザクション をサポート] [トランザクション が必要] アプリケーション テクニック 説明 コンポーネントはトランザクションの一部として実 行されない。コンポーネントが、トランザクション 内部で実行中の別のコンポーネントによってアク ティブにされた場合には、その新しいインスタンス の作業は既存のトランザクションの外部で行われる コンポーネントは EAServer トランザクションのコ ンテキスト内で実行できるが、コンポーネントのメ ソッドを実行するためにトランザクションは必要と しない。コンポーネントがクライアントによって直 接インスタンス化された場合、EAServer はトランザ クションを開始しない。コンポーネント A がコン ポーネント B によってインスタンス化されていて、 コンポーネント B はトランザクション内部で実行さ れている場合には、コンポーネント A は同じトラン ザクション内で実行される コンポーネントは常にトランザクションで実行され る。コンポーネントがクライアントによって直接イ ンスタンス化された場合には、新しいトランザク ションが始まる。コンポーネント A がコンポーネン ト B によってアクティブ化され、B はトランザク ション内で実行されている場合には、A は同じトラ ンザクション内で実行される。B がトランザクショ ン内で実行されていない場合には、A は新しいトラ ンザクション内で実行される 517 トランザクションのサポート トランザクションの 種類 [新規のトランザク ションが必要] [Mandatory] [OTS スタイル] [Never] トランザクション サービス コンテキス ト オブジェクトの使 い方 説明 コンポーネントがインスタンス化されるたびに、新 しいトランザクションが始まる。コンポーネント A がコンポーネント B によってアクティブにされ、B がトランザクション内部で実行されている場合に は、A は B のトランザクションの結果に影響されな い新しいトランザクションを開始する。B がトラン ザクション内で実行されていない場合には、A は新 しいトランザクション内で実行される メソッドは、実行中のトランザクションがあるクラ イアントによってのみ呼び出される。実行中のトラ ンザクションがないときにこのコンポーネントを呼 び出すと、実行時エラーになる コンポーネントはトランザクションを管理でき、ま たクライアントのトランザクションを継承できる。 トランザクションなしで呼び出された場合、コン ポーネントは、CORBACurrent コンテキスト サービ ス オブジェクトのインスタンスを使用して、トラン ザクションの開始、コミット、およびロールバック を行う 未処理のトランザクションがある場合、メソッドの 呼び出しは不可能。実行中のトランザクションがあ るときにこのコンポーネントを呼び出すと、実行時 エラーになる コンポーネント メソッドを使うと、EAServer のトランザクション状態 プリミティブを呼び出して、EAServer が現行のトランザクションをコ ミットするか中断するかを制御できます。EAServer のトランザクショ ン状態プリミティブにアクセスできるようにするため、PowerBuilder は TransactionServer というトランザクション サービス コンテキスト オブジェクトを提供します。 TransactionServer コンテキスト オブジェクトを使用する予定の場合 は、UseContextObject DBParm パラメータに Yes を設定する必要があり ます。 518 PowerBuilder 第 24 章 EAServer コンポーネントの構築 トランザクション コンポーネントに対して、UseContextObject に Yes を 設定すると、COMMIT と ROLLBACK のかわりに TransactionServer オブ ジェクトのメソッドを使用して、コンポーネントが現行のトランザク ションの作業を完了したかどうかを示すことを PowerBuilder に指示し ます。スクリプトに COMMIT および ROLLBACK 文を含めると、スクリ プトはランタイム エラーを起こします。UseContextObject に No を設定 すると、COMMIT および ROLLBACK 文は EAServer トランザクション サービスの CommitWork および AbortWork メソッドを呼び出します。古 いコードを残して、TransactionServer オブジェクトを使用したくない 場合にだけ、この設定を使用すべきです。 トランザクションで必要のないコンポーネントについては、 UseContextObject 設定は無視され、PowerBuilder ドライバは COMMIT および ROLLBACK 文を処理します。 トランザクション コンテキスト サービスを使用するには、TransactionServer 型の変数を宣言し、GetContextService 関数を呼び出してから、トランザ クション コンテキスト サービスのインスタンスを作成します。 コンポーネントの Activate イベントか Constructor イベント発生時 は、GetContextService を呼び出して TransactionServer サービスをインス タンス化できます。 例 // インスタンス変数: // TransactionServer ts Integer li_rc li_rc = this.GetContextService("TransactionServer", & ts) IF li_rc <> 1 THEN // エラー処理 END IF いずれかのコンポーネント メソッドでは、データベースを更新して、 更新に成功した場合には SetComplete を呼び出し、失敗した場合には SetAbort を呼び出せます。 // インスタンス変数: // DataStore ids_datastore long ll_rv ... ... ll_rv = ids_datastore.Update() IF ll_rv = 1 THEN ts.SetComplete() ELSE ts.SetAbort() アプリケーション テクニック 519 トランザクションのサポート END IF TransactionServer インタフェースが提供する 表 24-5 のメソッドを使用 すれば、EAServer のトランザクション プリミティブにアクセスできま す。 表 24-5: TransactionServer メソッド メソッド DisableCommit EnableCommit IsInTransaction IsTransactionAborted SetAbort SetComplete 自動的なデマケーショ ン / 不活性化 520 説明 コンポーネントの作業が完了していないため、現行の トランザクションをコミットできないことを示す。イ ンスタンスは、現行のメソッドが復帰した後もアク ティブなままである 現行のメソッドを呼び出した後で、コンポーネントを 非アクティブにしないことを示す。コンポーネント インスタンスが非アクティブにされた場合には、現行 のトランザクションをコミットできる 現行のメソッドがトランザクション内で実行されて いるかどうかを判定する 現行のトランザクションが中断されたかどうかを判定 する コンポーネントは現行のトランザクションに対する 作業を完了できず、トランザクションをロールバック することを示す。メソッドが復帰したとき、コンポー ネント インスタンスは非アクティブにされる コンポーネントが現行のトランザクションで作業を 完了し、そのコンポーネントに関する限り、トランザ クションをコミットでき、コンポーネント インスタ ンスを非アクティブにできることを示す 各メソッド呼び出しの後でコンポーネントを自動的に非アクティブに したい場合には、コンポーネントの[自動的なデマケーション / 不活 性化]を有効にしてください。これによって、コンポーネントの tx_vote プロパティに FALSE が設定されます。 [自動的なデマケーション / 不活 性化]が有効にされた場合には、デフォルトで SetComplete が想定され るため、SetComplete を明示的に呼び出して非アクティブにする必要は ありません。トランザクションをロールバックするには、SetAbort を呼 び出します。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 各メソッド呼び出しの後でコンポーネントを自動的に非アクティブに したくない場合には、コンポーネントの[自動的なデマケーション / 不 活性化]設定を無効にします。これによって、コンポーネントの tx_vote プロパティに TRUE が設定されます。[自動的なデマケーション / 不活 性化]を無効にすると、EAServer は、通知を待ってからトランザク ションを完了します。したがって、プログラムで SetComplete か SetAbort を明示的に呼び出すことによって、必ず非アクティブにしてください。 COMMIT 文と ROLLBACK 文 TransactionServer コンテキスト オブジェクトを無効にし、かわりに COMMIT 文 と ROLLBACK 文 を 使 用 し て、コ ン ポ ー ネ ン ト に 対 す る EAServer トランザクション状態を指定することも可能です。この機能 を使うと、コードを修正せずに、PowerBuilder 6 のオブジェクトを EAServer に移行できます。TransactionServer コンテキスト オブジェク トを無効にするには、UseContextObject DBParm パラメータを No に設 定します。これを行った場合、COMMIT は SetComplete と同じになり、 ROLLBACK は SetAbort と同じになります。 非トランザクション コンポーネントにおける COMMIT と ROLLBACK TransactionServer コンテキスト オブジェクトを無効にする非トランザ クション コンポーネントでは、COMMIT は SetComplete を呼び出さず、 ROLLBACK は SetAbort を呼び出しません。たとえば、トランザクションの 種類として[サポートされていません]を指定し、 [自動的なデマケーショ ン / 不活性化]を無効にし(tx_vote を TRUE に設定) 、UseContextObject パラメータを No に設定した場合には、COMMIT を実行しても PowerBuilder 仮想マシンは SetComplete を発行しません(ROLLBACK を実行した場合 には SetAbort を発行しません)。この場合には、EAServer は、SetComplete か SetAbort への呼び出しを待機しているため、コンポーネントが解放 されません。 データベース アクセスをまったく行わないコンポーネントの[自動的 なデマケーション / 不活性化]を無効にした場合には、TransactionServer オブジェクトを使用して SetComplete か SetAbort を呼び出し、コンポー ネントを非アクティブにする必要があります。それ以外の場合は、コ ンポーネントは非アクティブにされません。 トランザクション処理 と実行時エラー PBVM で内部例外が発生したとき、または PowerBuilder コンポーネン トが実行時例外を生成したときの EAServer の動作を制御できます。そ のためには、コンポーネントが実行されているサーバ上で、環境変数 PBOnFatalError または PBRollbackOnRTError をバッチ ファイル内で設 定するか、システム環境変数として設定します。 アプリケーション テクニック 521 トランザクションのサポート 表 24-6: 例外処理用の環境変数 変数 PBOnFatalError 説明 PBVM で内部例外が発生したときに、EAServer を継続動作させるか、シャッ トダウンするか、または再起動するかを指定する。デフォルトはシャットダ ウン。EAServer で実行されている PowerBuilder コンポーネントによって未 処理の内部例外が生成されると、PBVM が不安定になり、予期しない動作を 起こす可能性がある 値は以下のとおり • continue - 動作を継続させて CORBA_TRANSACTION_ROLLEDBACK 例 外を送出する • restart - 自動的に再起動する PBRollbackOnRTError • shutdown - 自動的にシャットダウンする(デフォルト) EAServer で実行されている PowerBuilder コンポーネントによって実行時例 外が生成されたときに、トランザクションをどのように処理するかを指定す る。デフォルトでは、トランザクションをロールバックしてクライアントに 例外を送出する 値は以下のとおり • n、no、または false - トランザクションをコミットしてからクライアント に例外を送出する • y、yes、または true - トランザクションをロールバックしてからクライア ントに例外を送出する(デフォルト) トランザクションとコ ンポーネント有効期間 EAServer のトランザクション モデルとコンポーネント有効期間は密 に統合されています。トランザクションに関与するコンポーネント イ ンスタンスは、トランザクションが終了するか、トランザクションに 対するコンポーネントの関与が終了したことが示される(その作業が 終了してコミットの用意ができるか、その作業をロールバックする必 要がある)までは、非アクティブになりません。インスタンスがアク ティブになるタイミングは、トランザクションへのインスタンスの関 与開始と終了に正確に一致します。 詳細については、EAServer のマニュアルを参照してください。 522 PowerBuilder 第 24 章 EAServer コンポーネントの構築 EAServer コンポーネントからデータベースへのアクセス データベースの接続性 EAServer コ ン ポ ー ネ ン ト か ら デ ー タ ベ ー ス に ア ク セ ス で き ま す。 EAServer による接続プーリングとトランザクション管理のサポートを 活用したい場合には、EAServer によってサポートされているデータ ベース インタフェースのいずれかを使用して、データベースに接続す る必要があります。データベース インタフェースについての詳細は、 『データベースとの接続』マニュアルを参照してください。 データストアの使い方 PowerBuilder で開発された EAServer コンポーネントは、データストア を使用してデータベースと対話できます。データストアは、非ビジュ アルなデータウィンドウのコントロールです。データストアは、デー タウィンドウのコントロールと同じように機能しますが、ビジュアル 属性を持っていません。 データストアは、分散アプリケーションで使用すると便利です。デー タストアを使用すると、各クライアント マシンのかわりに、リモート サーバ上でデータベース処理を実行できます。 リッチテキスト提示様式はサポートされていません サーバ コンポーネントは、リッチテキスト提示様式を使用するデータ ウィンドウ オブジェクトを備えたデータストアを格納できません。 リッチテキスト処理は、分散アプリケーションではサポートされてい ません。 サーバとクライアント 間でのデータ共有 サーバ上で検索されるデータに視覚的なインタフェースを提供したい 場合、データウィンドウ コントロールを持つウィンドウをクライアン トに追加します。サーバ上でデータが検索されるたびに、データウィ ンドウ コントロールを更新してサーバ上のデータストアの結果集合 を表示します。同様に、ユーザがクライアント上でデータを変更する たびに、サーバ上のデータストアの内容を更新して、クライアント上 のデータウィンドウ コントロールの最新のステータスを反映させま す。 クライアントとサーバ間でデータを共有するには、サーバのデータス トアとクライアントのデータウィンドウ コントロールをプログラム によって同期させます。アプリケーションにデータベース更新の処理 を行わせたい場合は、加えてデータウィンドウのデータ バッファとス テータス フラグを、クライアントとサーバの間で互いにやりとりする 必要もあります。 サーバのデータストアとクライアントのデータウィンドウとの同期に ついての詳細は、529 ページの「更新の実行」を参照してください。 アプリケーション テクニック 523 EAServer コンポーネントからデータベースへのアクセス 分散アプリケーションは ShareData 関数をサポートしません クライアント上のデータウィンドウ コントロールとサーバ上のデー タストアとの間では、ShareData 関数を使用してのデータ共有はできま せん。 接続キャッシュの使い方 接続キャッシュの利点 データベース処理を最適化するため、EAServer は接続キャッシュをサ ポートします。接続キャッシュを使用すれば、EAServer コンポーネン トは、リモート データベース サーバに対してあらかじめ割り当てられ た接続のプールを共有できるため、コンポーネントの各インスタンス が別々の接続を確立することによるオーバーヘッドを避けることが可 能です。接続キャッシュを設定することによって、サーバは同じデー タ ソースに対する接続を再利用できます。接続キャッシュは、EAServer 6.x ではデータ ソースと呼ばれます。 動作 通常、PowerBuilder アプリケーションがデータベースに接続されると、 PowerBuilder は、DISCONNECT 文が実行された各データベース接続を 物理的に終了させます。一方、PowerBuilder コンポーネントが EAServer 接続キャッシュを使用した場合には、EAServer はデータベース接続を 論理的に終了させますが、接続を物理的に解除するわけではありませ ん。接続キャッシュ内ではデータベース接続が開いたままであり、ほ かのデータベース操作で再利用できます。 destructor イベントで接続を解除しない EAServer は、トランザクションが完了する時やコンポーネントが非ア クティブになる時に、キャッシュへのすべての接続ハンドルを解放し ま す。destructor イベント(deactivate イ ベントの後 に発生する)に DISCONNECT 文を配置すると、 接続はすでに論理的に終了しているので、 DISCONNECT で物理的に終了されます。DISCONNECT 文は、deactivate イベントに配置できます。 キャッシュ内のすべての接続は、共通のユーザ名、パスワード、サー バ名、および接続ライブラリを共有しなければなりません。 524 PowerBuilder 第 24 章 EAServer コンポーネントの構築 ユーザによるキャッ シュへのアクセス 指定された一連のユーザ名、パスワード、サーバ、および接続ライブ ラ リ の 値 を 使 用 す る キ ャ ッ シ ュ か ら 接 続 を 検 索 し た い 場 合 に は、 キャッシュを使えるようにデータベース アクセス コードを修正する 必要はありません。EAServer Manager で、コンポーネントが必要とする データベース接続プロパティ(ユーザ名、パスワード、サーバ名、およ び接続ライブラリ)を備えた新しいキャッシュを作成します。EAServer 6.x では、データ ソース(キャッシュ)を作成するには、Management Console で[Resources | Data Sources | Add]を選択します。実行時に、コン ポーネントがデータベースへの接続を試みると、EAServer は、コン ポーネントが要求する接続値に一致する接続をキャッシュから自動的 に返します。 名前によるキャッシュ へのアクセス キャッシュ名を指定することによって、キャッシュから接続を検索し たい場合には、CacheName DBParm を設定して、使用したいキャッシュ を識別します。名前によってキャッシュにアクセスすれば、コンポー ネントの対応するソース コードを変更せずに、Management Console で ユーザ名、パスワード、またはサーバを変更できます。 次の PowerBuilder コンポーネントのコード例に、名前によるキャッシュ へのアクセス方法を示します。 SQLCA.DBMS = "ODBC" SQLCA.Database = "EAS Demo DB" SQLCA.AutoCommit = FALSE SQLCA.DBParm = "ConnectString='DSN=EAS Demo DB; UID=dba;PWD=sql',CacheName='mycache'" キャッシュ名では大文字と小文字が区別される キャッシュ名では大文字と小文字が区別されます。したがって、スク リプトに指定するキャッシュ名が EAServer での名前と完全に一致す ることを確認してください。 プロキシによる接続 キャッシュにユーザによってアクセスするか名前によってアクセスす るかに関係なく、プロキシで接続できます。プロキシで接続した場合 は、代替ログイン名を入力することで、別のユーザの識別情報と権限 を使用できます。 アプリケーション テクニック 525 EAServer コンポーネントからデータベースへのアクセス この機能は、SQL コマンド set session authorization を認識する任意の データベースで使用できます。ユーザ A が ProxyUserName DBParm を 使用して別のユーザ B の識別情報を使用するには、ユーザ A はこのス テートメントを実行する権限を所有していなければなりません。たと えば、SQL Anywhere の場合、ユーザ A は DBA 権限を所有している必 要があり、また ASE の場合、ユーザ A はシステムのセキュリティ担当 者から set session authorization を実行する権限を与えられている必要が あります。 プロキシ接続をサポートする PowerBuilder データベース インタフェー スについての詳細は、 『データベースとの接続』マニュアルを参照して ください。 プロキシ接続を使用するには、代替ログイン名を識別するための ProxyUserName DBParm を設定します。次の例に、プロキシによる接 続方法を示します。 SQLCA.DBMS = "ODBC" SQLCA.DBParm = "CacheName='MyEAServerCache', UseContextObject='Yes',ProxyUserName='pikachu'" プロキシ接続を利用す る前に コンポーネントがプロキシ接続を利用するには、事前にキャッシュ プ ロパティ ファイルでプロキシ設定の Set-proxy サポートを有効にして おく必要があります。EAServer 5.x では、EAServer Manager は、キャッ シュ作成時に個々のキャッシュのプロパティを自動作成しません。し たがって、このファイルは手動で作成する必要があります。ファイルに cachename.props という名前を付けて、EAServer\Repository\ConnCache ディレクトリに格納します。キャッシュのプロパティ ファイルを作成 したら、次の行を追加します。 com.sybase.jaguar.conncache.ssa=true この設定を有効にするには、EAServer を更新しなければなりません。 EAServer 6.x では、データ ソースを作成するには、Management Console で[Resources | Data Sources | Add]を選択します。[Set Session Authorization]を選択して、[Set Session Authorization System ID]ボックスに名前を指定します。データ ソースのプロパティ ファ イルが Instance\com\sybase\djc\sql\DataSource ディレクトリの Repository に保存されます。 接続キャッシュ(またはデータ ソース)の管理についての詳細は、 EAServer のマニュアルを参照してください。 また、データベース サーバが ProxyUserName DBParm で定義した代替 ログイン名を認識して権限を与えるように設定しなければなりませ ん。 526 PowerBuilder 第 24 章 すべての接続が使用中 である場合の動作 EAServer コンポーネントの構築 キャッシュ内のすべての接続が使用中である場合の動作を制御できま す。そのためには、GetConnectionOption DBParm に次のいずれかの値 を設定します。 値 JAG_CM_NOWAIT JAG_CM_WAIT JAG_CM_FORCE 説明 接続を返せなかった場合に、接続を試みるとエラー で停止する 接続が利用可能になるまで、コンポーネントが待機 する 新しい接続を割り当てて開く。この新しい接続は キャッシュされないため、不要になったら破棄される デフォルトでは、PowerBuilder は JAG_CM_FORCE を使用します。 接続が解放されたとき の動作 接続が解放されたときの動作も制御できます。そのためには、 ReleaseConnectionOption DBParm に以下のいずれかの値を設定します。 値 JAG_CM_DROP JAG_CM_UNUSED 説明 接続を閉じて割り当て解除する。キャッシュからの 接続である場合には、その位置に新しい接続が作成 される。エラーによって使用できなくなった場合に は、JAG_CM_DROP を使用して接続を破棄する キ ャ ッ シ ュ か ら の 接 続 で あ る 場 合 に は、接 続 が キャッシュに戻される。キャッシュの外部で作成さ れた接続は、閉じて破棄される デフォルトでは、PowerBuilder は JAG_CM_UNUSED を使用します。 Unicode 用の EAServer 接続キャッ シュをサポート 以下の EAServer ネイティブ接続キャッシュは、PowerBuilder コンポー ネント用の Unicode 接続をサポートします。 EAServer 5.x 用 • OCI_9U – Oracle9i Unicode キャッシュ • OCI_10U – Oracle 10g Unicode キャッシュ • ODBCU – ODBC Unicode キャッシュ EAServer 6.x 用 • JCM_Oracle_Unicode – Oracle9i または 10g Unicode キャッシュ • JCM_Odbc_Unicode – ODBC Unicode キャッシュ アプリケーション テクニック 527 EAServer コンポーネントからデータベースへのアクセス これらの接続キャッシュ タイプは、Unicode 接続パラメータを受け 取ってから、データベース ドライバにリクエストを送信してデータ ベースへの Unicode 接続を開きます。Unicode 接続では、PowerBuilder コンポーネントは Unicode を使用してデータベースと通信できます。 EAServer 5.x 内の PowerBuilder コンポーネントで、Oracle9i データベー スにアクセスするために Oracle9i ネイティブ インタフェース(O90) を使用している場合は、接続キャッシュ用にデータベース ドライバ タ イプ OCI_9U を使用します。 EAServer 5.x 内の ODBC 接続キャッシュに関しては、データベース ド ライバ タイプ ODBCU を使用して、SQL Anywhere Unicode データベー スの複数言語データや SQL Anywhere DBCS データベースの DBCS データにアクセスして、データベース パラメータ ODBCU_CONLIB を 1 に設定します。以下に例を示します。 SQLCA.DBParm = "CacheName='EASDemo_u', UseContextObject='Yes',ODBCU_CONLIB=1" 検索操作の実行 データストアを使用して検索操作を行うには、まずスクリプトでデー タストア オブジェクトのインスタンスを作成し、データウィンドウ オ ブジェクトをデータストアに割り当てる必要があります。次に、デー タストアのトランザクション オブジェクトを設定します。これらの設 定が完了したら、データストア内でのデータの検索や、データストア の内容の印刷などの処理を、検索した結果集合に対して実行できます。 例 : 参照による配列渡し 説明 次の例に、データストアを使用してサーバ コンポーネント内のデータ を取り出す方法を示します。サーバ コンポーネント uo_customers には、 retrieve_custlist という関数があります。retrieve_custlist は、データストア ds_datastore のインスタンスを生成し、このデータストアを使用して Customer テーブル内のすべての行を取り出します。データが取り出さ れたら、retrieve_custlist はデータをクライアント アプリケーションに戻 します。 関数の宣言 retrieve_custlist 関数は、構造体 st_custlist の配列として定義される引数 customers を受け取ります。構造体 st_custlist は、データウィンドウ オ ブジェクトがデータベースへのアクセスに使用した d_custlist と同じレ イアウトを備えています。取り出された行数を返すために使用する retrieve_custlist の戻り値は Long 型です。 528 PowerBuilder 第 24 章 EAServer コンポーネントの構築 retrieve_custlist 関数のシグネチャを次に示します。 retrieve_custlist( REF st_custlist customers [] ) returns long スクリプト retrieve_custlist 関数のスクリプトを次に示します。 datastore ds_datastore long ll_rowcount ds_datastore = create datastore ds_datastore.dataobject = "d_custlist" ds_datastore.SetTransObject (SQLCA) IF ds_datastore.Retrieve() <> -1 THEN ll_rowcount = ds_datastore.RowCount() END IF customers = ds_datastore.object.data destroy ds_datastore return ll_rowcount retrieve_custlist 関数は、処理の最後にデータストアを破棄して、取り出 された行数をクライアントに返します。 更新の実行 データウィンドウの同 期 従来のクライアント / サーバ アプリケーションでは、データベースの 更新は、クライアント マシン上で動作している 1 つのアプリケーショ ンによって開始され、PowerBuilder はデータウィンドウの状態情報を 自動的に管理できます。分散アプリケーションの場合、状況は多少異 なります。アプリケーション コンポーネントはクライアントとサーバ の間で分割されるため、ロジックを記述することによって、クライア ント上のデータウィンドウ コントロールのデータ バッファとステー タス フラグを、サーバ上のデータストアのそれらと同期させることが 必要になります。 PowerBuilder は、分散アプリケーションにおいてデータウィンドウと データストアを同期させるために 4 つの関数を提供しています。 • GetFullState • SetFullState • GetChanges • SetChanges アプリケーション テクニック 529 EAServer コンポーネントからデータベースへのアクセス これらの関数は分散アプリケーション上では非常に役立ちますが、複 数のデータウィンドウ(データストア)を同期させなければならない、 分散モデル以外のアプリケーションでも使用できます。 データウィンドウの バッファとステータス フラグの移動 クライアント上のデータウィンドウ コントロールとサーバ上のデー タストアを同期させるには、データウィンドウのデータ バッファとス テータス フラグを、データの変化が起こるたびにクライアントとサー バの間でやりとりします。これを行うための手順は、変更の原因がク ライアントにあってもサーバにあっても、本質的に同じです。 完全な状態情報を 1 つのデータウィンドウ(またはデータストア)か ら別のデータウィンドウ(またはデータストア)に適用するには、次 の手順を実行する必要があります。 1 GetFullState 関数を呼び出して、ソース データウィンドウの現行状 態を取り込みます。 2 SetFullState 関数を呼び出して、ソース データウィンドウの状態を ターゲットに適用します。 変更を 1 つのデータウィンドウ(またはデータストア)から別のデー タウィンドウ(またはデータストア)に適用するには、次の手順を実 行する必要があります。 1 GetChanges 関数を呼び出して、ソース データウィンドウから変更 を取り込みます。 2 SetChanges 関数を呼び出して、ソース データウィンドウの変更を ターゲットに適用します。 SetChanges は空のデータウィンドウに適用できます SetChanges を呼び出して、変更を空のデータウィンドウ(またはデー タストア)に適用できます。ターゲット データウィンドウは、前の取 り出し操作の結果集合を格納する必要はありません。しかし、データ ウィンドウはデータウィンドウ定義にアクセスできなければなりませ ん。つまり、SetChanges を呼び出す前に、データウィンドウ オブジェ クトをターゲット データウィンドウに割り当てる必要があります。 データウィンドウの状 態は Blob に格納され ます 530 GetFullState 関数または GetChanges 関数を呼び出したとき、PowerBuilder はデータウィンドウのステータス情報を Blob 型の値で返します。 GetFullState 関数から返される Blob 値は、データ バッファ、ステータ ス フラグ、データウィンドウの詳細な仕様など、データウィンドウ の再構築に必要なすべての情報を提供します。GetChanges 関数から返 される Blob 値は、変更あるいは削除が行われた行についてのみ、デー タ バッファやステータス フラグの情報を提供します。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 更新後の同期 デフォルトでは、Update 関数は、更新に成功した後で更新フラグをリ セットします。したがって、サーバ上で Update 関数を呼び出した場合 には、サーバ データストアのステータス フラグは自動的にリセットさ れます。しかし、対応するクライアント データウィンドウ コントロー ルの更新フラグはリセットされません。したがって、サーバ データス トアの Update 関数が成功した場合には、クライアント データウィンド ウの ResetUpdate を呼び出して、フラグをリセットします。 1 つのソース、1 つの ターゲット 1 つのソース データウィンドウ(データストア)と 1 つのターゲット データウィンドウ(データストア)との同期化が可能です。1 つのソー スを複数のターゲットに同期させたり、逆に複数のソースを 1 つの ターゲットに同期させたりしないでください。 一般的な使用シナリオ サーバに、DS_1 というデータストアを使用するコンポーネントがある とします。このデータストアは、クライアント上の DW_1 というター ゲット データウィンドウのデータのソースです。Activate イベントで は、コンポーネントはデータベースに接続し、データストアを作成し、 データストアにデータウィンドウ オブジェクトを割り当てます。 そのメソッドの 1 つで、サーバ コンポーネントは DS_1 に対する Retrieve 関数を発行し、DS_1 の GetFullState 関数を呼び出して、取得した Blob をクライアントに渡します。コンポーネントの[自動的なデマケーショ ン / 不活性化]設定が無効(コンポーネントがステートフル)にされ ているため、メソッドが復帰する前に SetComplete 関数も呼び出して、 コンポーネント インスタンスを非アクティブにします。 [自動的なデマケーション / 不活性化]が有効である場合 コンポーネントに対する[自動的なデマケーション / 不活性化]設定 が有効の場合には、メソッドが実行を終了した時点で、コンポーネン ト インスタンスは自動的に非アクティブにされます。したがって、取 り出しの後に SetComplete 関数を呼び出す必要はありません。 アプリケーション テクニック 531 EAServer コンポーネントからデータベースへのアクセス クライアントがデータウィンドウ Blob を取得すると、SetFullState 関数 を呼び出して、Blob の状態情報を DW_1 に適用します。この時点で、 ユーザは DW_1 に新しい行を挿入したり、既存の行を変更または削除 したりできます。ユーザが更新リクエストを行うと、クライアントは GetChanges 関数を呼び出し、別のコンポーネント メソッドを呼び出し て取得した Blob をサーバに戻します。次に、コンポーネント メソッド は SetChanges 関数を呼び出して、DW_1 の変更を DS_1 に適用します。 サーバ コンポーネントは、DS_1 を DW_1 に同期させてから、データ ベースを更新し、SetComplete 関数または SetAbort 関数を呼び出して、 更新に成功したかどうかを示します。 更新が成功した場合には、クライアントは ResetUpdate 関数を呼び出し て、クライアント データウィンドウのステータス フラグをリセットし ます。 最初の更新操作が完了した後、クライアントとサーバは、完全な状態 情報ではなく Blob の変更結果を互いにやりとりして、それ以降の更新 を処理できます。それ以降の更新プロセスは繰り返しとなります。 例 次の例に、PowerBuilder クライアントと EAServer コンポーネントの間 で、データウィンドウの同期をとる方法を示します。この例ではステー トレス コンポーネントを使用します。 クライアント ウィン ドウの定義 クライアントには w_employee というウィンドウがあり、そのウィンド ウのボタンを使用して、ユーザはデータの検索と更新を行えるものと します。クライアント ウィンドウの[検索]ボタンには、次のスクリ プトがあります。 // // // // グローバル変数 : connection myconnect インスタンス変数 : uo_employee iuo_employee blob lblb_data long ll_rv myconnect.CreateInstance(iuo_employee) iuo_employee.RetrieveData(lblb_data) ll_rv = dw_employee.SetFullState(lblb_data) if ll_rv = -1 then MessageBox(" エラー ", "SetFullState 呼び出しに失敗 !") end if 532 PowerBuilder 第 24 章 EAServer コンポーネントの構築 クライアント ウィンドウの[更新]ボタンには、次のスクリプトがあ ります。 blob lblb_data long ll_rv ll_rv = dw_employee.GetChanges(lblb_data) if ll_rv = -1 then MessageBox(" エラー ", "GetChanges 呼び出しに失敗 !") else if iuo_employee.UpdateData(lblb_data) = 1 then & dw_employee.ResetUpdate() end if サーバ オブジェクト の定義 インスタンス変数 サーバのオブジェクト uo_employee には、以下の関数があります。 • RetrieveData • UpdateData uo_employee オブジェクトには、以下のインスタンス変数があります。 protected TransactionServer ts protected DataStore ids_datastore Activate uo_employee オブジェクトの Activate イベントは、 TransactionServer サー ビスをインスタンス化します。さらに、データベースに接続してデー タストアを作成します。このデータストアは、データベースへのアク セスに使用されます。 this.GetContextService("TransactionServer", ts) SQLCA.DBMS="ODBC" SQLCA.DBParm="ConnectString= 'DSN=EAS Demo DB;UID=dba;PWD=sql', UseContextObject='Yes'" CONNECT USING SQLCA; IF SQLCA.SQLCode < 0 THEN // エラー処理 END IF ids_datastore = CREATE datastore ids_datastore.dataobject = "d_emplist" ids_datastore.SetTransObject (SQLCA) RetrieveData 関数の スクリプト RetrieveData 関数は ablb_data という引数を受け取ります。この引数は、 参照渡しされる Blob です。この関数は Long 値を返します。 RetrieveData 関数のスクリプトを次に示します。 long ll_rv アプリケーション テクニック 533 EAServer コンポーネントからデータベースへのアクセス ids_datastore.Retrieve() ll_rv = ids_datastore.GetFullState(ablb_data) ts.SetComplete() return ll_rv UpdateData 関数のス クリプト UpdateData 関数は ablb_data という引数を受け取ります。この引数は、 参照渡しされる Blob です。この関数は Long 値を返します。 UpdateData 関数のスクリプトを次に示します。 long ll_rv if ids_datastore.SetChanges(ablb_data) = 1 then ll_rv = ids_datastore.Update() end if if ll_rv = 1 then ts.SetComplete() else ts.SetAbort() end if return ll_rv Deactivate uo_employee オブジェクトの Deactivate イベントは、データストアを破 棄し、データベースから接続を解除します。 DESTROY ids_datastore DISCONNECT USING SQLCA; 結果集合の受け渡し PowerBuilder は、2 つのシステム オブジェクトを提供することによっ て、EAServer で動作しているコンポーネントから結果集合を取得し、 EAServer コンポーネントとして動作している PowerBuilder ユーザ オ ブジェクトから結果集合を返します。これらのシステム オブジェクト (ResultSet と ResultSets)は、データストア オブジェクトとの間でトラ ンザクション サーバの結果集合の相互変換を簡単にするよう設計さ れており、状態情報は含まれていません。また、データベースの更新 に使用するようには設計されていません。データストア オブジェクト との間でこれらのオブジェクトに格納された結果集合を変換するに は、データストア オブジェクトの CreateFrom 関数と GenerateResultSet 関数を使用します。 534 PowerBuilder 第 24 章 EAServer コンポーネントの構築 GenerateResultSet について GenerateResultSet にはもう 1 つの構文があり、 EAServer とともに MASP (Method as Stored Procedure)を 使 用 す る と き に、TDS(Tabular Data Stream)の結果集合を返すために使用されます。詳細については、 『デー タウィンドウ リファレンス』マニュアルを参照してください。 結果集合を返すコンポーネント メソッドは、TabularResults モジュール を使用します。1 つの結果集合は TabularResults::ResultSet 構造体として 返されます。複数の結果集合は、TabularResults::ResultSets データ型を 使用して、一連の ResultSet 構造体として返されます。 PowerBuilder クライ アントから EAServer コンポーネント内の結 果集合にアクセス TabularResults::ResultSet を返す EAServer コンポーネント メソッドに対 して、PowerBuilder で EAServer プロキシ オブジェクトを生成した場合 には、プロキシ オブジェクトのメソッドは、PowerBuilder ResultSet オブ ジェクトを返します。複数の結果集合を返すメソッドは、PowerBuilder ResultSets オブジェクトを返します。 オブジェクト ブラウザでプロキシを表示 PowerBuilder オブジェクト ブラウザの[プロキシ]タブでは、EAServer プロキシ オブジェクトのプロパティとメソッドを表示できます。 PowerBuilder クライアントから結果集合にアクセスするには、コン ポーネントのインスタンスを作成し、メソッドを呼び出し、結果集合 を使用してデータストア オブジェクトに CreateFrom 関数を追加しま す。 次の例では、SVUBookstore コンポーネントのインスタンスを作成し、 GetMajors メソッドを呼び出します。 SVUBookstore lcst_mybookstore resultset lrs_resultset datastore ds_local integer li_rc // myconnect は接続オブジェクトです li_rc = myconnect.CreateInstance(lcst_mybookstore) IF li_rc <> 0 THEN MessageBox(" インスタンスの作成 ", string(li_rc) ) myconnect.DisconnectServer() RETURN END IF lrs_resultset = lcst_mybookstore.GetMajors() アプリケーション テクニック 535 EAServer コンポーネントからデータベースへのアクセス ds_local = CREATE datastore ds_local.CreateFrom(lrs_resultset) EAServer コンポーネ ントから結果集合を返 す EAServer に配布される PowerBuilder ユーザ オブジェクトから結果集 合を渡したり返したりするには、関数の引数または戻り値のデータ型 に ResultSet(1 つの結果集合の場合)または ResultSets(複数の結果集 合の場合)を設定します。ユーザ オブジェクトが EAServer コンポー ネントとして配布された場合には、ResultSet と ResultSets の戻り値は、 コンポーネントの IDL インタフェースでは、TabularResults::ResultSet と TabularResults::ResultSets のデータ型として表されます。 次の例では、データストア オブジェクトを作成し、その中にあるデー タを取り出し、続いて GenerateResultSet 関数を使用して、クライアン トに返す結果集合を作成しています。 datastore ds_datastore resultset lrs_resultset integer li_rc ds_datastore = create datastore ds_datastore.dataobject = "d_empdata" ds_datastore.SetTransObject (SQLCA) IF ds_datastore.Retrieve() = -1 THEN // エラーをレポートして復帰 END IF li_rc = ds_datastore.generateresultset(lrs_resultset) IF li_rc <> 1 THEN // エラーをレポートして復帰 END IF return lrs_resultset 536 PowerBuilder 第 24 章 EAServer コンポーネントの構築 コンポーネント インタフェースの定義 インタフェースの指定 方法 EAServer は、すべてのコンポーネント インタフェースを CORBA 2.0 インタフェース定義言語(IDL: Interface Definition Language)モジュー ルに格納します。IDL は、オブジェクト マネジメント グループによっ て、コンポーネント インタフェースを定義するための標準言語として 定義されています。PowerBuilder カスタム クラス ユーザ オブジェクト を EAServer コンポーネントとして配布すると、そのオブジェクトに定 義されたメソッド(関数とイベント)とインスタンス変数がコンポー ネント インタフェースに追加されます。EAServer コンポーネント ジェ ネレータがユーザにかわって IDL を記述するため、インタフェースの ために IDL を記述する必要はありません。 EAServer 6.0 以降では、PowerBuilder コンポーネントは EJB に組み込ま れます。詳細については、Sybase の製品マニュアルの Web サイトで、 EAServer のマニュアル一覧から『CORBA Components Guide』マニュア ルを参照してください。 インタフェースに組み 込まれるもの EAServer コンポーネント ジェネレータは、ユーザ オブジェクトに宣 言されたすべてのパブリック関数をコンポーネント インタフェース に組み込みます。さらに、コンポーネントに指定した構築オプション に応じて、ジェネレータはパブリック インスタンス変数のアクセサ メ ソッドを組み込み、ユーザ イベントをメソッドとして公開できます。 メソッド名とメソッド の多重定義 IDL はメソッドの多重定義をサポートしていません。それでも、多重 定義されたメソッドを持つ EAServer に対して、PowerBuilder カスタム クラス ユーザ オブジェクトを配布できます。IDL の制約を回避するた め、多重定義されるメソッド名に対して、コンポーネント ジェネレー タは 2 つのアンダースコア(__)と一意の接尾辞を付加します。した がって、PowerBuilder オブジェクト用に生成された IDL を調べてみる と、PowerBuilder で多重定義されたメソッドに接尾辞が付加されてい ることがわかります。 多重定義されたメソッドを持つコンポーネントにスタブまたはプロキ シ オブジェクトを生成すると、クライアントが正しい名前を使用して メソッドにアクセスできるように、EAServer は IDL の接尾辞を取り除 きます。 IDL についての詳細は、EAServer のマニュアルを参照してください。 アプリケーション テクニック 537 コンポーネント インタフェースの定義 メソッド名には 2 つの連続したアンダースコアを使用しないでください EAServer は 2 つのアンダースコア(__)を予約区切り記号として扱う ため、EAServer コンポーネントとして配布する予定のカスタム クラス ユーザ オブジェクトの関数名には、2 つの連続したアンダースコアを 使用しないでください。 データ型 EAServer コンポーネントとして配布するユーザ オブジェクトのイン タフェースでは、以下のデータ型を使用できます。 • 標準のデータ型(Any データ型を除く) • 構造体 • EAServer コンポーネントとして配布されたカスタム クラス(非ビ ジュアル)ユーザ オブジェクト これらのデータ型は、パブリック インスタンス変数に限らず、パブ リック メソッドの戻り値と引数にも使用できます。プライベート型と プロテクト型のインスタンス変数とメソッドでは、PowerBuilder がサ ポートするすべてのデータ型を使用できます。 コンポーネントのパブリック インタフェースでは、Any 型はサポート されていません。さらに、ResultSet と ResultSets のオブジェクトを除 いて、コンポーネント インタフェースは、組み込みの PowerBuilder シ ステム オブジェクト(たとえば、トランザクション オブジェクトや データストア オブジェクト)を実装できません。コンポーネント イン タフェースに実装できないものとしては、それ以外にビジュアル オブ ジェクト(ウィンドウやメニューなど)もあります。 コンポーネント メソッドは、標準データ型の配列と構造体の配列を渡 し、カスタム クラス ユーザ オブジェクトを使用して配列を渡せます。 int と uint の short へのマップ EAServer 6.x では、int と uint のどちらの PowerBuilder のデータ型も short にマップします。そのため、1 つの int 引数を持つ int を返す関数を 定義した場合、同じコンポーネント上に、1 つの uint 引数を持つ uint を 返す同じ名前の関数を定義すると、配布は失敗します。 538 PowerBuilder 第 24 章 EAServer コンポーネントの構築 EAServer で使用されるデータ型、各データ型の対応する CORBA IDL、 および各データ型がマッピングされる PowerBuilder のデータ型のリス トについては、 『PowerScript リファレンス』マニュアルまたはオンラ イン ヘルプを参照してください。PowerBuilder から EJB データ型への マッピングの詳細については、Sybase の製品マニュアルの Web サイト で、EAServer マニュアルの一覧から『CORBA Components Guide』マ ニュアルを参照してください。 参照渡し 引数を参照によってコンポーネント メソッドに渡せます。しかし、分 散アプリケーションと分散モデル以外のアプリケーションでは、動作 がいくぶん異なります。 参照で渡す場合には、メソッドが実行される前に変数が実際にサーバ にコピーされ、その後、メソッドが実行を完了したときにコピーして 戻されます。通常、この動作はアプリケーションからは透過的ですが、 場合によっては処理結果に影響を与えることもあります。 たとえば、x と y の 2 つの引数(いずれも参照渡し)を受け取る、 increment_values というメソッドを定義するとします。次に示すように、 メソッドのスクリプトは x と y をインクリメントします。 x = x + 1 y = y + 1 クライアントは、次のコードを使用してメソッドを呼び出します。 int z z = 1 increment_values(z,z) 分散モデル以外のアプリケーションでは、メソッドが実行を完了した 後の z の値は 3 となります(これは、ローカル呼び出しで z へのポイ ンタを渡して z を 2 回インクリメントするためです)。分散アプリケー ションでは、z の値は 2 となります(リモート呼び出しで z の 2 つのコ ピーを渡して、別々にインクリメントするためです)。 読み込み専用値を渡す 読み込み専用の値を渡すときの動作は、データを変更できないことを 除けば、値渡しに似ています。データのコピーが、ネットワークを介 してサーバに渡されます。 アプリケーション テクニック 539 コンポーネント インタフェースの定義 オブジェクトを渡す EAServer コンポーネント内で作成されたオブジェクトをクライアント に戻すことは可能ですが、この場合はこれらのオブジェクトがインス トール済みの EAServer コンポーネントでなければなりません。EAServer コンポーネントではない PowerBuilder オブジェクトを戻そうとした場 合は、実行時エラーが出力されます。サーバから戻されたコンポーネ ントを使用するには、クライアントには、対応する EAServer プロキシ (PowerBuilder クライアントの場合)またはスタブ(非 PowerBuilder ク ライアントの場合)が必要です。 クライアント アプリケーションは、PowerBuilder オブジェクト参照を EAServer に渡せません。したがって、PowerBuilder オブジェクト参照 を使用しても、サーバから PowerBuilder クライアントへのメッセージ のプッシュは実行できません。しかし、クライアント上の共有オブジェ クトを使用して EAServer と通信することによって、この動作をシミュ レートすることは可能です。 サーバ プッシュをシミュレートするには、クライアントは、 SharedObjectRegister 関数と SharedObjectGet 関数を使用して、共有オブ ジェクトを作成します。オブジェクトが作成されると、クライアント から共有オブジェクトにメソッドをポストして、サーバ上で処理終了 時に通知しなければならないコールバック オブジェクトを渡せます。 共有オブジェクトのメソッドは、処理を行う EAServer コンポーネン ト メソッドの同期呼び出しを行います。共有オブジェクトはクライ アント上の独立したスレッドで動作しているため、サーバ上でプロセ スを実行しながら、クライアント アプリケーションがほかの作業を 続行できます。 NULL 値のサポート 540 PowerBuilder では、EAServer コンポーネントのメソッドが NULL 値を 関数引数として受け取るか、戻り値の型として受け取るかを指定でき ます。コンポーネント インタフェースで NULL 値をサポートするには、 EAServer コンポーネントの生成に使用されたプロジェクトのプロパ ティ シートで、 [NULL 値をサポート]チェックボックスをオンにしま す。このボックスがオフである場合には、クライアントはどの引数に も NULL 値を渡せないため、サーバは、引数に NULL を設定したり NULL 値を返したりすることはできません。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 コンポーネント メソッドのプロトタイプで NULL 値を許可する場合、 PowerBuilder はプロジェクト ペインタから生成する EAServer プロキ シのメソッド名に「_N」接尾辞を追加します。このメソッドを呼び出 すには、NVO のインスタンスではなく、プロキシのインスタンスを作 成する必要があります。そして、「_N」接尾辞を持つメソッドを参照 する必要があります。たとえば、of_gen が NVO のメソッド名で、NULL 戻り値を許可する EAServer プロキシを作成する場合は、プロキシのイ ンスタンスを作成し、of_gen_N を呼び出してこのメソッドを使用する 必要があります。 EAServer 検証 EAServer コンポーネントとして配布する予定のカスタム クラス ユー ザ オブジェクトを設計している場合には、EAServer で無効なコード要 素が使用されたときに、PowerBuilder で警告を出すようにできます。 EAServer 検証では、パブリック インスタンス変数とパブリック関数の システム タイプ、ビジュアル タイプ、構造体、および変数をチェック します。 EAServer 検証は、EAServer ウィザードを使用してユーザ オブジェクト を作成した場合には、デフォルトでオンになっています。チェックす るには、ユーザ オブジェクト ペインタの[デザイン]メニューを選択 し、 [EAServer 検証]がオンになっていることを確認します。オブジェ クトを保存すると、出力ウィンドウに以下のような警告が一覧表示さ れます。 ---------- コンパイラ : 情報メッセージ 情報 C0197: コンポーネント検証 警告 C0198: 適切でない Jaguar タイプ : 'window' arg type for function: 'of_badfunc' 警告 C0198: 適切でない Jaguar タイプ : 'any' return type for function: 'of_badfunc' 検証は、ユーザ オブジェクト ペインタではなく、編集中のオブジェク トに関連付けられます。オブジェクトを再び開くと、オブジェクトの 検証状態は閉じたときと同じになります。 例外の送出 EAServer に配布するユーザ オブジェクトの関数で例外を宣言すると、 その例外はメソッドのプロトタイプの一部として、CORBA IDL に変換 されます。例外は、任意の種類の EAServer クライアント アプリケー ションまたは呼び出したコンポーネントで処理できます。詳細につい ては、39 ページの「PowerBuilder での例外処理」を参照してください。 アプリケーション テクニック 541 既存インタフェースの実装 既存インタフェースの実装 新規作成 ダイアログボックスの[ターゲット]タブまたは[PB オブ ジェクト]タブの EAServer コンポーネント ウィザードを使用して、既 存インタフェースの PowerBuilder の実装を作成できます。この機能は 一般的には、オンライン バンキングや証券取引のプロトコルなどの標 準 API の実装を作成するのに使用されます。 インタフェースの選択 ウィザードの[インタフェース実装の指定]ページで[既存の EAServer リモート インタフェースを実装する]を選択し、次に、実装したい IDL インタフェースが保存されているサーバの EAServer プロファイ ルを選択します。ウィザードでパッケージのリストを展開したときに 表示されるリストから、インタフェースを 1 つだけ選択できます。 PowerBuilder コンポーネントの場合、普通、インタフェース名はコン ポーネント名と同じですが、インタフェースのリストがそのままサー バ上のコンポーネントのリストにマッピングされるわけではありませ ん。リストには、タイプ インタフェースのすべての IDL モジュールが 含まれます。 ウィザードのオプショ ンの設定 実装するインタフェースを選択したら、コンポーネントの EAServer 名 を入力します。PowerBuilder カスタム クラス ユーザ オブジェクトの名 前は変更できません。この名前は常に、リモート インタフェースの名 前と同じになります。新規インタフェース作成時のように、パッケー ジ名、インスタンス プーリングなど、そのほか多くのオプションを設 定できます。 標準 API の PowerBuilder の実装を作成している場合、普通はリモート コンポーネントのコンポーネント名を使用しますが、同じパッケージ 名を使用してはいけません。 リモート コンポーネントのインタフェースは変更できないため、引数 に NULL 値をサポートするなど、メソッドのシグネチャが変更されて しまうようなオプションは、ウィザードでは設定できません。 ペインタでのユーザ オブジェクトの編集 542 ウィザードで作成したカスタム クラス ユーザ オブジェクトでは、リ モート インタフェースのパブリック属性はパブリック インスタンス 変数として表され、パブリック メソッドはパブリック関数として表さ れます。関数のスクリプトには、コンパイル エラーが発生しないよう に return ステートメントが格納されていますが、それぞれの関数を実 装するスクリプトを提供する必要があります。リモート インタフェー スにほかにも依存する要素(構造体など)が含まれている場合、ウィ ザードはユーザ オブジェクトと同じ PBL でそれらを作成します。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 EAServer 6.0 以降を使用している場合、PowerBuilder コンポーネント は、EJB コンポーネントとして組み込まれ、Remove メソッドは、EAServer によってコンポーネント インタフェースの一部として生成されます。 ただし、ユーザーがこのメソッドを使用する必要はありません。 ユーザ オブジェクトは、ほかのカスタム クラス ユーザ オブジェクト と同様に編集できます。ユーザ オブジェクト ペインタで制約を適用さ れることはありません。ただし、インタフェースに影響するような変 更を行ってはいけません。既存インタフェースの属性とメソッドに対 応するインスタンス変数や関数を削除したり、そのモードをパブリッ クからプライベートやプロテクトに変更したりしないでください。関 数は多重定義できません。また、戻り値か引数には NULL 値を使用で きません。 EAServer へのコン ポーネントの配布 ウィザードによって作成されたプロジェクトには、ウィザードがコン ポーネントを構築したインタフェースに関する情報が格納されていま す。プロジェクトを実行すると、PowerBuilder は次のことをチェック します。 • 既存 IDL インタフェースのすべてのパブリック属性とメソッド が、ユーザ オブジェクトのパブリック インスタンス変数や関数と して定義されている • IDL インタフェースで定義されたメソッドが、ユーザ オブジェク トで多重定義されていない これらのチェックのいずれかが失敗した場合、コンポーネントは配布 されますが、プロジェクト ペインタと出力ウィンドウに警告が表示さ れます。 異なるプロジェクトの 使い方 これらのチェックは、コンポーネント作成時に作成されたプロジェク トを使用してコンポーネントが配布された場合のみ実行されます。新 しいプロジェクトを作成したり、別のプロジェクトにコンポーネント を追加したりした場合は、プロジェクト実行時にはチェックは実行さ れません。 コンポーネントと一緒に作成されたプロジェクトを使用して配布する と、新規の実装は常にサーバ上の既存の IDL を使用します。別のプロ ジェクトを使用する場合は、コンポーネントをオリジナル パッケージ に配布して、インタフェースの変更に関する警告なしに既存 IDL を上 書きすることがあるため、注意が必要です。 アプリケーション テクニック 543 別のサーバ コンポーネントのメソッドの呼び出し プロキシの生成 既存インタフェースを実装するオブジェクトのプロキシを生成し、 サーバの既存 IDL を使用するときは、プロキシは既存 IDL に基づきま す。結果として、[EAServer パッケージ名をオブジェクト名の前に追 加]オプションを選択すると、オブジェクト名に付く名前は、新しい パッケージの名前ではなく IDL モジュールの名前になります。 別のサーバ コンポーネントのメソッドの呼び出し EAServer では、サーバ コンポーネントのメソッドを使って、ほかの サーバ コンポーネントのメソッドを呼び出せます。呼び出される側の サーバ コンポーネントは、PowerBuilder コンポーネントである必要は なく、EAServer によってサポートされる言語で実装されているコン ポーネントでもかまいません。 現行のサーバのコン ポーネントにアクセス 現行のサーバにある別の EAServer コンポーネントのメソッドにアク セスするには、PowerBuilder クライアントの場合と同じように、接続 オブジェクトを使用してコンポーネントと通信します。あるいは、 PowerBuilder が提供する、TransactionServer というトランザクション サービス コンテキスト オブジェクトを使用します。TransactionServer インタフェースが提供する CreateInstance というメソッドを使用すれ ば、ローカルで使用するほかのコンポーネントにアクセスできます。 CreateInstance は、呼び出し元のコンポーネントに適用されるものと同 じユーザ情報とパスワード情報を使用します。 トランザクション コンテキスト サービスを使用するには、 TransactionServer 型の変数を宣言し、GetContextService 関数を呼び出し てから、トランザクション コンテキスト サービスのインスタンスを作 成します。コンポーネント間呼び出しのプロキシ オブジェクトを使 用する必要があります。プロキシ オブジェクトがなければ、 TransactionServer オブジェクトは、呼び出しているコンポーネントの 正しいメソッド名を取得することはできません。 EAServer コンポーネント用のプロキシ オブジェクトの作成について は、574 ページの「EAServer プロキシ オブジェクトの生成」を参照し てください。 例 コンポーネントの Activate イベントで GetContextService を呼び出 して、TransactionServer サービスをインスタンス化できます。 544 PowerBuilder 第 24 章 EAServer コンポーネントの構築 // インスタンス変数: // TransactionServer ts Integer rc rc = this.GetContextService("TransactionServer", ts) IF rc <> 1 THEN // エラー処理 END IF いずれかのコンポーネント メソッドから、CreateInstance を呼び出して 2 番目のコンポーネントをインスタンス化し、そのメソッドの 1 つを 呼び出せます。アプリケーションには、以下のように 2 番目のコンポー ネントのプロキシを含めます。 // 2 番目のコンポーネントのインスタンス変数 : // nvo_comp2 mycomp2 Integer rc rc = ts.CreateInstance(mycomp2, "mypackage/nvo_comp2") IF rc <> 0 THEN // エラー処理 ELSE mycomp2.method1() END IF ほかのサーバ内にある コンポーネントへのア クセス ほかのサーバのサーバ コンポーネントにアクセスする手順は、PowerBuilder クライアントからサーバ コンポーネントにアクセスする手順と基本 的に同じです。ほかのサーバの EAServer コンポーネントにアクセスす るには、接続オブジェクトを作成し、接続オブジェクトのプロパティ を設定し、ConnectToServer を呼び出します。 EJB コンポーネント へのアクセス PowerBuilder コンポーネントは、接続オブジェクトまたは TransactionServer オブジェクトのいずれかの Lookup メソッドを使用し て、EJB コンポーネントにアクセスできます。TransactionServer オブ ジェクトの Lookup メソッドには、オプションとして、ホーム インタ フェースの名前を指定するための第 3 引数があります。この引数は、 ホーム インタフェース名が一般的な命名規約に従わない場合のみ使 用します。 このスクリプトは、Cart コンポーネントをインスタンス化し、い くつかのコンポーネント メソッドを呼び出します。次の例では、Lookup メソッドの第 2 引数に、コンポーネント名と EAServer パッケージ名を 指定しています。 例 // インスタンス変数 : //Connection myconnect CartHome MyCartHome // EJB のホーム インタフェース アプリケーション テクニック 545 コンポーネント プロパティへのアクセス Cart MyShoppingCart // EJB のリモート インタフェース TransactionServer ts long ll_result This.GetContextService("TransactionServer", ts) // ホーム インタフェースを取得 ll_result = & ts.Lookup(MyCartHome, "Shopping/Cart") //Cart コンポーネントのビジネス ロジックへの参照を取得 MyShoppingCart = MyCartHome.Create() // ショッピング カートを使用 MyShoppingCart.AddItem(66) MyShoppingCart.Purchase() PowerBuilder クライアントから EJB コンポーネントへのアクセスにつ いては、578 ページの「EJB コンポーネント メソッドの呼び出し」を 参照してください。 コンポーネントを区別 するトランザクション [OTS スタイル]としてマークされた EAServer コンポーネントは、 CORBACurrent コンテキスト サービス オブジェクトの関数を使用し て、EAServer トランザクションに関する情報の作成、制御、および取 得が行えます。CORBACurrent オブジェクトは、CORBACurrent インタ フェース用に定義された数多くのメソッドを備えています。 詳細については、588 ページの「クライアントとコンポーネントを区 別するトランザクション」を参照してください。 コンポーネント プロパティへのアクセス ContextKeyword サー ビス オブジェクト ContextKeyword サービス オブジェクトを使用して、コンポーネントの .properties ファイルから固有のコンポーネントのプロパティ値を取得 できます。プロパティ値を取り出すには、GetContextKeywords 関数を呼 び出します(EAServer コンポーネントのすべてのプロパティを列挙す るには、Jaguar::Repository API を使用します)。 ContextKeyword サービス オブジェクトを使用するには、 GetContextService 関数を呼び出し、サービス名として Keyword を使用 してから、オブジェクトへの参照を作成します。 546 PowerBuilder 第 24 章 PowerBuilder の EAServer プロパティ EAServer コンポーネントの構築 表 24-7 に、EAServer コンポーネントとして動作する PowerBuilder カ スタム クラス ユーザ オブジェクトに関係するコンポーネント プロパ ティを示します。コンポーネント プロパティの前には、文字列 com.sybase.jaguar.component が付けられます。EAServer 5.x では、 EAServer Manager の コンポーネントのプロパティ ダイアログボック スの[Advanced]タブには、すべてのコンポーネント プロパティの 値が表示されます。表 24-7 に示すように、いくつかのプロパティは、 このダイアログボックスのほかのタブの項目にもマップされます。 EAServer 6.x でのプロパティの詳細については、Sybase 製品マニュアル Web のサイト http://infocenter.sybase.com/help/index.jsp?topic=/com.sybase.dc00547_0600/ht ml/eascorba/BABCDICB.htm で『CORBA Components Guide』マニュアル を参照してください。 表 24-7: EAServer 5.x における PowerBuilder コンポーネントの EAServer コンポーネント プロパティ プロパティ auto.failover 説明 表示位置 Transactions サーバが使用できなくなったときにコンポーネントを代替サーバ に転送するためのクライアント プロキシを有効にする (Automatic このプロパティは、自動的なデマケーション / 不活性化が有効でな failover) ければ有効にできない bind.thread code.set interfaces 自動フェイルオーバでは、冗長サーバでアプリケーションのコン ポーネントを実行できるように、アプリケーションがサーバのク ラスタを使用する必要がある。クラスタは最低 1 つのネーム サー バを含み、クライアントはネーミング サービスを使用してプロキ シ参照を解決しなければならない。詳細については、『EAServer System Administration Guide』マニュアルの「Load Balancing, Failover, and Component Availability」を参照 作成するスレッド上でコンポーネント インスタンスを常に起動さ Instances(Bind せるかどうかを指示する Thread) 有効な値は TRUE と FALSE である。ライブ編集の場合には、この プロパティを TRUE に設定しなければならないが、それ以外の場合 は、スケーラビリティを向上させるために FALSE に設定する必要 がある コンポーネントが使用するコード化文字セットの名前を指定する Advanced デフォルトでは、コンポーネントはサーバのコード化文字セット (サーバの Properties ウィンドウの[General]タブで指定)を使用 する。ヨーロッパ言語またはアジア言語では、このプロパティを iso_1 または big5 などの値に設定しなければならない場合がある Advanced コンポーネントが実装するインタフェースを識別する これは、IDL インタフェース名をカンマで区切ったリストであり、 それぞれのインタフェース名は module::interface という書式と なる アプリケーション テクニック 547 コンポーネント プロパティへのアクセス プロパティ minpool maxpool name 説明 表示位置 Resources インスタンス プーリングが有効のときは、プールできるインスタ ンスの最少数を指定する プールから休止中のインスタンスを解放するため、EAServer には 定期的に実行されるガベージ コレクタ スレッドがある。このス レッドが実行されるたびに、ガベージ コレクタは、休止中のイン スタンスを 1 つプールから削除する。ただし、プールが最小サイ ズに到達したときは削除されない。デフォルトは 0 インスタンス プーリングが有効のときに、プールできるインスタ Resources ンスの最大数を指定する プール サイズの最大値に到達した場合、EAServer は非アクティブ 化後に過剰インスタンスを破棄する。デフォルトは 0 で、最大プー ル サイズが有効でないことを意味する コンポーネントの名前を指定する この値の書式は package/component でなければならない pb.appname pb.class pb.cookie General(コン ポーネント部の み) General PowerBuilder アプリケーションの名前を指定する PowerBuilder カスタム クラス ユーザ オブジェクトの名前を指定す General る Advanced ライブラリ リストのパスの作成に使用する数を提供する パスの書式は次のとおり Repository\Component\package\component\Ccookie debug pb.librarylist pb.live_edit pb.trace pb.version 548 PowerBuilder デバッガでコンポーネントをデバッグできるかどう Advanced かを示す General PowerBuilder ライブラリ リストを指定する ライブラリ名の前に円記号(\)が付いている場合は、その位置は EAServer Repository ディレクトリからの相対指定であるとみなさ れる。ライブラリ名の前に円記号が付いていない場合は、その名 前は絶対パスを指定するとみなされる プロジェクト ペインタではなく、ユーザ オブジェクト ペインタで Advanced プロジェクトを構築できるかどうかを指定する 553 ページの「ライブ編集」を参照 コンポーネントに対するログ収集動作のトレース オプションを指 Advanced 定する(現在無効) コンポーネントが作成された PowerBuilder のバージョンを指定す Advanced る PowerBuilder 第 24 章 プロパティ pooling EAServer コンポーネントの構築 説明 コンポーネントがプールされているかどうかを示す 表示位置 Instances pooling プロパティに TRUE が設定された場合は、コンポーネント は常にプールされ、CanBePooled イベントは発生しない。pooling プ ロパティに FALSE が設定された場合は、CanBePooled イベントが 発生するため、プーリングの拒否を選択できる sharing tx_vote プロパティに FALSE が設定された場合は、各メソッドの後 でコンポーネントがプールされる。それ以外の場合は、トランザ クションの最後にプールされる Instances 共有コンポーネントであるかどうかを示す sharing プロパティに TRUE が設定された場合は、すべてのクライ アントが 1 つのコンポーネント インスタンスを共有する。共有コ ンポーネントにプーリング オプションは適用されない 共有コンポーネントをサービスにするには、 com.EAServer.server.services プロパティ用に指定したサービスのリ ストに共有コンポーネントを追加する state state.gs stateless 自動的な永続格納を使用するときに、IDL 型の名前を指定する Persistence PowerBuilder では、名前の付いている型はユーザ定義の構造体で、 永 続 す る す べ て の デ ー タ を カ プ セ ル 化 し な け れ ば な ら な い。 [Persistence]タブ ページで[Automatic Persistent State]を選択し、 [State]テキストボックスに構造体の名前を入力して[OK]をク リックすると、ページ上にあるほかのプロパティがデフォルト値 に設定される。自動的な永続格納を使用する場合、PowerBuilder コ ンポーネントのステートフル フェイルオーバがサポートされる。 詳 細 に つ い て は、 『EAServer Programmer’s Guide』マニュアルの 「managing persistent component state」の章を参照 state データ型を取得し設定する state 構造体のメソッド名で、2 項 Persistence (State メソッド) 目のカンマ区切りのリストとして指定される デフォルトは getState、setState EJB セッション Beans と、コントロール インタフェース CtsComponents::ObjectControl を使用する非 EJB コンポーネントの みに適用される Instances このプロパティを設定すると、tx_vote プロパティを FALSE に設定 するのと同じ結果になるが、activate イベントと deactivate イベント も無効になる。コンポーネントをステートレスに指定する場合は、 このプロパティを設定しないこと。かわりに、pooling を TRUE に、 tx_vote を FALSE に設定する アプリケーション テクニック 549 コンポーネント プロパティへのアクセス プロパティ storage 説明 表示位置 リモート データベース サーバからコンポーネントの状態情報を読 Persistence(ス み書きするコンポーネントの名前を指定する トレージ・コン 自動的な永続格納を使用するとき、または EAServer の組み込み格 ポーネント、接 納コンポーネントに実装を任せてコンポーネント管理による永続 続キャッシュ、 テーブル) 性使用するときに必要となる。デフォルトは CtsComponents/JdbcStorage thread.safe timeout tx_outcome また、格納コンポーネントが使用する接続キャッシュとテーブル を指定する 複数の呼び出しを同時に処理できるかどうかを示す Instances(同時 詳細については、508 ページの「Concurrency プロパティ」を参照 実効性) メソッド呼び出しの後、次のメソッド呼び出しまでの間に、アク ティブなコンポーネント インスタンスが自動的に非アクティブに されずにアイドル状態でいられる時間を指定する トランザクションがロールバックされたときに、 CORBA::TRANSACTION_ROLLEDBACK 例外をクライアントに送 出するかどうかを決定する Resources(イン スタンス・タイ ムアウト) Advanced 以下の設定を使用できる always デフォルト。トランザクションがロール バックされる と、サーバからクライアントに例外が送出される • failed トランザクションがロール バックされても、クライアント に例外が送出されない。この設定を使用する場合、RollbackWork トランザクション プリミティブを呼び出した後で説明メッセー ジ付きの別の例外を発生するように、コンポーネントをコー ディングできる • failed 設定を有効にしても、コンポーネントのリクエストによるト ランザクションをコミットできない場合は、CORBA システム例外 が送出されることがある tx_timeout 550 ロールバックされたトランザクションの例外をクライアントに送 りたくない場合や、別の例外を送出する必要がある場合、このプ ロパティを failed に設定できる。この設定は、トランザクションが ロールバックされた後で、クライアントが出力パラメータを得ら れるようにする必要のある場合に役立つ。例外が送出される場合 は、出力パラメータを使用できない EAServer トランザクションの最大継続時間を指定する Resources(トラ ンザクション・ 各メソッドが復帰した後でタイムアウトがチェックされる タイムアウト) PowerBuilder 第 24 章 プロパティ tx_type EAServer コンポーネントの構築 説明 EAServer トランザクションに対するコンポーネントの関与を示す 表示位置 Transactions 有効な値は、以下のとおり • not_supported • supports • requires • requires_new • mandatory • user-managed • never tx_vote type コンポーネントで自動的なデマケーション/不活性化をサポートす Transactions るかどうかを示す ([Automatic Demarcation/ tx_vote に TRUE が設定された場合は、コンポーネントは、 Deactivation] TransactionServer サービス オブジェクトのメソッドを明示的に呼 び出すことによって、トランザクション状態とコンポーネントの チェックボック スがオンである 非アクティブ化を制御する必要がある 場合は、このプ tx_vote に FALSE が設定された場合は、各メソッド呼び出しの後で、 ロパティの値は EAServer は コ ン ポ ーネントを自動的に非アクティブにする。 FALSE) SetComplete はデフォルトで呼び出されるため、SetComplete を明示 的に呼び出して非アクティブにする必要はない。SetAbort を呼び出 せば、デフォルト状態に上書きできる General コンポーネントのタイプを指定する EAServer は PowerBuilder オブジェクトのプロパティを pb に設定す る Web サービスとしての NVO の公開 EAServer コンポーネント ウィザードでは、生成されるコンポーネント を Web サービスとして公開できます。 このウィザードの[EAServer コンポーネントを Web サービスとして公 開]ページには、コンポーネントを EJB 2.1 Web サービス(EAServer 6.x)または EAServer 5.x Web サービスとして公開するオプションがあ ります。コンポーネントを EJB 2.1 Web サービスとして公開する場合 は、ウィザードまたはプロジェクト ペインタの[全般]タブのページ で、Java のパッケージ名を指定する必要があります。 EAServer 5.x Web サービスについては、表 24-8 で説明されるプロパ ティを設定する必要があります。 アプリケーション テクニック 551 Web サービスとしての NVO の公開 表 24-8: Web サービスとして公開されるコンポーネントのプロパティ プロパティ 説明 Web アプリケー コンポーネントの配布先である Web アプリケーションの ション名 名前を指定する。入力した Web アプリケーションが EAServer に存在しない場合は、そのアプリケーションの 作成後にコンポーネントが配布される。アプリケーショ ンを指定しなかった場合、コンポーネントは EAServer の デフォルトの Web アプリケーションである「ws」に配布 される サービス名 コンポーネントを Web サービスとして公開するときに使 用するサービス名を指定する。サービス名を指定しな かった場合、デフォルトの packageName_componentName が使用される WSTAdmin ポ ー EAServer で Web サービスに使用するポートを指定する。 ト番号 ポートを指定しなかった場合、デフォルトの 8080 が使用 される [コンポーネントを Web サービスとして公開]チェックボックスと 3 つのテキスト ボックス フィールドは、EAServer コンポーネントのプ ロパティ ダイアログボックスの[Web サービス]タブにもあります。 したがって、これらのプロパティは、ウィザードを使用せずに設定し たり、ウィザードの完了後に変更したりすることができます。 Web サービスとして配布する EAServer コンポーネント内の構造体オ ブジェクトを参照する場合、そのオブジェクトは自動的にカスタム データ型に変換されます。 現在、EAServer で Web サービスとして公開するコンポーネントには、 次の制限が適用されます。文字データ型を参照渡しする関数が PowerBuilder コンポーネントにある場合、そのコンポーネントを Web サービスとして公開できません。「Can't find prefix for 'http://DefaultNamespace'」などのエラー メッセージが表示されます。 552 PowerBuilder 第 24 章 EAServer コンポーネントの構築 コンポーネントのテストとデバッグ この節では、コンポーネントをテストするための 3 つの方法について 説明します。 • ライブ編集 • リモート デバッグ • EAServer ログへのメッセージ出力 EAServer コンポーネントのトラブルシューティング コンポーネントのトラブルシューティングについての詳細は、EAServer のマニュアルを参照してください。 ライブ編集 コンポーネントをテストまたはデバッグするには、ライブ編集という PowerBuilder の機能を利用すれば、ユーザ オブジェクト ペインタでプ ロジェクトを自動的に作成できます。ライブ編集が有効であれば、対応 するユーザ オブジェクトを保存するたびに、PowerBuilder は EAServer コンポーネントのプロジェクトを作成します。ジェネレータは、EAServer に PBD を配布しないかわりに、必要なオブジェクト定義を含む PBL へ のアクセス方法を EAServer に指示します。 サービス コンポーネント ライブ編集を利用しても、サービス コンポーネントとしてセットアッ プしたコンポーネントはテストできません。サービス コンポーネント は、サーバの稼動中は常に使用されているため、ユーザ オブジェクト ペインタで行った変更の保存はできません。 ライブ編集を有効にす る方法 ユーザ オブジェクトのライブ編集を有効にするには、次の手順を実行 する必要があります。 1 EAServer コンポーネントを生成したいユーザ オブジェクトを含む プロジェクトを作成します。 EAServer への配布を可能にする既存の PBL を使用したり、新規プ ロジェクトを作成してテスト用に使用したりできます。 2 アプリケーション テクニック 必要に応じて、プロジェクトのライブ編集ライブラリ リストを修 正します。 553 コンポーネントのテストとデバッグ リモート マシン上にあるサーバでコンポーネントをテストしてい る場合には、PBL の位置を EAServer に通知する必要があります。 このためには、プロジェクト ペインタで、コンポーネントのプロ パティ シートにある[高度なオプション]ページ(下図参照)の ライブラリ リストを修正します。 ここで指定するライブラリ リストは、Universal Naming Convention (UNC)名を使用する、絶対パス名を含んでいる必要があります。 UNC 名の書式は \\servername\sharename\path\file です。 デフォルトでは、ライブ編集ライブラリ リストは、アプリケーショ ン ライブラリ リストに基づいています。使用しているサーバが ローカルである場合には、ライブ編集ライブラリ リストを修正す る必要はありません。 3 ユーザ オブジェクト ペインタで、コンポーネントの生成に使用す るプロジェクトを指定します。 プロジェクト名は、 [EAServer プロジェクト]フィールドに入力し ます。このフィールドは、ユーザ オブジェクト プロパティ シート の[全般]プロパティ ページ(下図参照)にあります。 指定するプロジェクト名は、以下の要件を満たす必要があります。 コンポーネントの生成 方法 554 • EAServer コンポーネント プロジェクトであること • ユーザ オブジェクト ペインタで現在開いているユーザ オブ ジェクトを含んでいること • プロジェクトのライブラリ リストは、現行のアプリケーショ ン ライブラリ リストと一致すること ユーザ オブジェクト ペインタで EAServer コンポーネントを生成する には、[ファイル|上書き保存]を選択します。 PowerBuilder 第 24 章 コンポーネントを生成 すると何が起きるか EAServer コンポーネントの構築 ユーザ オブジェクト ペインタでプロジェクトを作成すると、以下の処 理が行われます。 • 保存した非ビジュアル オブジェクトを記述する CORBA IDL を生 成。 この IDL は、さらにスタブとスケルトンの作成に使用されます。 IDL ファイル、スタブ、およびスケルトンの名前は、オブジェク トの名前をベースにしています。 コンポーネント ジェネレータは、EAServer のインストール ディレ クトリの Repository サブディレクトリに新しい IDL を格納します。 • EAServer コンポーネントのプロパティを記述する PROPS ファイ ルを生成 PROPS ファイルは、EAServer のインストール ディレクトリのサブ ディレクトリに格納されます。このサブディレクトリのパスは以 下のとおりです。Repository\Component\package-name PowerBuilder は、配布時と同様にコンポーネントを作成します。ただ し、コンポーネントの PBD は生成されません。さらに、コンポーネン ト ジェネレータは、pb.live_edit プロパティを TRUE に設定し、ライブ 編集用に指定したライブラリ リストを pb.librarylist プロパティに割り 当てます。 プロジェクトを作成するとエラーになる場合には、PowerBuilder は、出 力ウィンドウにエラー メッセージを表示します。 ユーザ オブジェクトに対するインスタンス プーリングが有効である 場合には、ジェネレータは、現行の構築に対するプーリングを無効に します。ユーザ オブジェクトを含む PBL が EAServer によってロック された場合には、PowerBuilder はユーザ オブジェクトを保存できない ため、ライブ編集ではプーリングはサポートされていません。 リモート デバッグ PowerBuilder のカスタム クラス ユーザ オブジェクトを EAServer コン ポーネントとして作成している場合には、PowerBuilder デバッガを使 用して、EAServer コンポーネントをデバッグできます。ユーザ オブ ジェクト ペインタのライブ編集機能を利用しても、プロジェクト ペイ ンタから EAServer にコンポーネントを配布しても、コンポーネントを デバッグできます。 ライブ編集についての詳細は、553 ページの「ライブ編集」を参照し てください。 アプリケーション テクニック 555 コンポーネントのテストとデバッグ コンポーネントをデ バッグするための準備 デバッグする EAServer コンポーネ ントの選択 デバッガの起動 556 リモート コンポーネントのデバッグを始める前に、ご使用の構成が以 下の条件を満たすかどうかをチェックしてください。 • 配布されるコンポーネントの開発に使用したものと同じバージョ ンのアプリケーションと PBL を使用している。配布された複数の コンポーネントを同じセッション内でデバッグしたい場合には、 それらのコンポーネントは、すべて同じバージョンの PBL、同じ アプリケーション名、および同じライブラリ リストを使用して作 成されたものでなければならない • プロジェクト ペインタのコンポーネント プロパティのページで、 [リモート デバッグのサポート]チェックボックスがオンになって いる。デバッグ オプションを設定するには、プロジェクト ウィ ザードで[リモートデバッグのサポート]チェックボックスをオ ンにする方法もある • 配布されたコンポーネントに含まれるメソッドとプロパティを実 行するクライアント アプリケーションがある。このアプリケー ションとしては、互換性のある開発ツールで作成されたコンパイ ル済みの実行ファイル、または別の PowerBuilder セッションで実 行されている PowerBuilder アプリケーションでもよい EAServer ターゲットをデバッグする場合、デバッグ可能なコンポーネ ント セットはプロジェクトで決まります。このコンポーネント セット には、プロジェクト ペインタの[コンポーネント]ページで選択した すべてのコンポーネントが含まれ、[リモート デバッグのサポート] チェックボックスがオンになっています。異なるコンポーネント セッ トを選択したり、複数のパッケージからのコンポーネントをデバッグ したりする場合は、デバッガのメニュー バーから[デバッグ|コン ポーネントの選択]を選択するか、ペインタバーの[コンポーネント の選択]ボタンをクリックします。 デバッグを始めるには、配布されたコンポーネントを含むターゲット を開きます。ペインタバーの[リモートを開始]ボタンをクリックし、 ウィザードを完了します。選択できるコンポーネントは、PowerBuilder で[リモート デバッグのサポート]をオンにして生成されたコンポー ネントだけです。 [リモート デバッグのサポート]はセキュリティ設 定の 1 つであり、コンポーネントにデバッグ情報を追加しません。コ ンポーネントをテストするときに[リモート デバッグのサポート]を オンにします。コンポーネントをユーザのサイトに配布するときには、 [リモート デバッグのサポート]をオフにして、ユーザにコードがわ からないようにします。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 ローカル アプリケーションをデバッグするときのようにブレークポ イントを設定してから、リモート コンポーネントを呼び出すクライア ント アプリケーションを起動します(まだ実行されていない場合)。 ローカル デバッグと の違い ローカル アプリケーションとリモート アプリケーションのデバッグ には、2 つの主な違いがあります。 • • デバッガを起動しても、デバッガは最小化されない 新規インスタンス ビューには、デバッグ中のコンポーネントの各 インスタンスが表示される。インスタンスごとに、コンポーネン ト名とパッケージ名、インスタンス番号、およびその現在の状態 (アイドル、実行中、または一時停止)が表示される。複数のイン スタンスがある場合には、現在デバッグ中のインスタンスが黄色 の矢印で示される サポートされていない機能 メモリ内のオブジェクト ビュー、式の評価、および変数値の変更はサ ポートされていません。 状態について インスタンス ビューには、コンポーネントごとに各インスタンスの状 態が示されます。 • コンポーネントは休止中か、インスタンス プール内にあ アイドル る コンポーネントは、現在コードを実行している • 実行中 • 一時停止 コンポーネントはブレークポイントで一時停止して、デ バッガ操作を待機している インスタンスが破棄されると、インスタンス ビューから取り除かれま す。 複数のインスタンス 同時に複数のコンポーネント インスタンスを一時停止させることは 可能ですが、デバッガで行う操作は、ブレークポイントに到達した最 初のインスタンスにだけ作用します。このインスタンスは、インスタ ンス ビューの黄色の矢印によって示されます。メソッドが完了する か、[実行の継続]をクリックした場合には、現行のインスタンスは キュー内の次のインスタンスに変わります。 インスタンス ビューで新規インスタンスをダブルクリックしても、1 つのインスタンスから別のインスタンスにコンテキストを変更できま す。別のコンポーネント インスタンスへの呼び出しを除いて、インス タンス ビューに呼び出されたインスタンスが一時停止したことが示 されている場合には、この方法を利用できます。 アプリケーション テクニック 557 データの印刷 EAServer ログへのメッセージ出力 EAServer で動作している PowerBuilder オブジェクトによって生成され たエラーを EAServer ログに記録するには、ErrorLogging サービス コン テキスト オブジェクトのインスタンスを作成し、その log メソッドを 呼び出します。たとえば、次のようになります。 ErrorLogging inv_el this.GetContextService("ErrorLogging", inv_el) inv_el.log("Write this string to log") ErrorLogging サービスを使用して、サーバ上のシステム エラーまたは 実行時エラーのコンテキストに関する詳細情報を表示できます。この 情報は、システム管理者や開発者が問題を解決する際に役立ちます。 コンポーネントの開発中は、ErrorLogging サービスを使用して、コン ポーネントの実行をトレースできます。たとえば、関数に入るときや 出るときに、ログにメッセージを書き込むことも可能です。このメッ セージによって、コンポーネントの名前、関数に入っているか出てい るか、それはどの関数かを特定できます。 例外情報の自動記録 サーバで実行している PowerBuilder コンポーネントが引き起こす例外 の種類および例外の位置に関する情報は、自動的にサーバ ログに記録 されます。これらの例外についての最低限の情報を取得するためにエ ラー ログ サービスを実行する必要はありません。 XSL-FO を使用して PDF ファイルを生成するときに、詳細情報メッ セージと警告メッセージがログに送信されます。環境変数 PB_FOP_SUPPRESSLOG に 1 を設定すると、これらのメッセージの出 力を抑制できます。 データの印刷 サーバが Windows または Solaris で動作している場合は、データストア を使用してデータをリモート サーバに印刷できます。 558 PowerBuilder 第 24 章 EAServer コンポーネントの構築 プラットフォームに関する注意 次の例は、HP-UX または AIX 上では機能しません。これらのプラット フォームでは、EAServer が Windows の機能を利用しない PowerBuilder 実行環境を使用するため、印刷などのグラフィック処理はサポートし ていません。データストア印刷関数を使用した印刷は、現在 Solaris だ けでサポートしています。ただし、SaveAs 関数と PDF SaveAsType を 使用すれば、データストア オブジェクトをすべての UNIX プラット フォームで印刷できます。 詳細については、563 ページの「PDF への印刷」を参照してください。 この例では、サーバ コンポーネント uo_employees は、print_employees という関数を備えています。print_employees はデータストア ds_datastore のインスタンスを生成し、このデータストアの内容を印刷 します。 print_employees 関数のシグネチャを次に示します。 print_employees( ) returns integer print_employees 関数のスクリプトを次に示します。 datastore ds_datastore int li_rc ds_datastore = create datastore ds_datastore.dataobject = "d_empdata" ds_datastore.SetTransObject (SQLCA) ds_datastore.Retrieve() li_rc = ds_datastore.Print() return li_rc Solaris オペレーティング システムでの印刷 Solaris では、PostScript または PCL5 ファイルに直接印刷できます。 Windows ではなく Solaris でレポートを印刷するためにコードを変更す る必要はありません。Windows の場合と同じプロパティ、関数、およ びイベントを使用できます。 データストアを印刷するには、データストア Print メソッドまたは PrintDataWindow(PrintJobName, DataStoreName) を使用します。データ ストアをデータウィンドウにリンクしてデータウィンドウ オブジェ クトを Solaris で印刷する場合、印刷結果は、データウィンドウ オブ ジェクトで定義したフォントとレイアウトになります。 アプリケーション テクニック 559 データの印刷 スペース Solaris で は 印 刷 ジ ョ ブ で の ス ペ ー ス を サ ポ ー ト し て い な い た め、 PBVM によって、印刷ジョブをプリンタに送信する前に印刷ジョブ名 の各スペースがハイフンに置き換えられます。 フォントの使い方 印刷に使用されるフォントは、dwprinter/fontmetrics ディレクトリに用 意されているフォントです。AFM ファイルと TFM ファイルは、特定 の PostScript(AFM)と PCL(TFM)のフォントに関する情報を含む ASCII 形式のファイルです。PostScript と PCL の各フォントには、対応 するフォント メトリック ファイルがあります。 印刷メカニズムで、フォント メトリック情報を取得するために AFM ファイルと TFM ファイルが読み込まれます。この情報には、文字幅、 ベースライン位置、アセンダ サイズ、ディセンダ サイズ、下線スト ローク幅、下線位置などがあります。次に、このメトリック情報は、 XTextWidth のような Xlib API が要求する形式に変換されます。 最善の方法は、データウィンドウの設計時に、Windows と Solaris の両 方で使用可能なフォントを選択することです。ただし、各プラット フォームには独自のフォントレンダリング エンジンがあるため、 Solaris と Windows でのフォント サイズの違いが気になることがあり ます。Solaris での印刷結果を開発プロセスの早い時期にテストする必 要があります。 制限 データウィンドウ オブジェクトの印刷のサポートは、Bristol Technology の Wind/U 製品に基づいています。Wind/U GDI ライブラリと Xprinter ライブラリには、以下の制限があります。 • マルチバイト文字セット(MBCS)および Unicode はサポートして いない • Xprinter はスレッド セーフではないため、印刷ジョブはシリアラ イズされる プリンタの設定 データウィンドウ オブジェクトを印刷するプリンタを設定するには、 プリンタへのアクセスの追加、dwprint.ini 環境設定ファイルの設定、お よび XPPATH 環境変数の作成を行わなければなりません。 プリンタへのアクセス の追加 560 ルート ユーザで、Solaris admintool ユーティリティを使用して Solaris 上 のプリンタへのアクセスを追加します。詳細については、Solaris のマ ニュアルを参照してください。 PowerBuilder 第 24 章 dwprint.ini の設定 EAServer コンポーネントの構築 $EAServer/bin ディレクトリの dwprint.ini ファイルは、データウィンド ウ印刷用の環境設定ファイルです。このファイルは、Microsoft Windows のプリンタ環境設定方法に厳密に従っています。その結果、このファ イルには[windows] 、 [devices]、 [ports]の各セクションが用意されて おり、各セクションにプリンタの適切なエントリを指定しなければな りません。 通常、このファイルのほかのセクションを変更する必要はありません。 ただし、いくつかの問題を解決するために、ほかのセクションの追加 または変更を行います。たとえば、[intl]セクションに次のようなエ ントリを追加して日付形式を変更できます。 [intl] sShortDate=m/d/yyyy // 4 桁の年を設定します。 dwprint.ini 内のエントリは、.WindU ファイル内のエントリに基づいて います。このファイルの設定方法についての詳細は、Wind/U User’s Guide のサイト http://www.bristol.com/support/windu/wu_ug/ch13.htm を参照してく ださい。 ポートの指定 dwprint.ini の[ports]セクションの各行には、出力ファイルのスプー ルに使用されるユーザ定義のポート名と関連コマンドを記述します。 たとえば、システムに直接接続されている myprinter というプリンタに 印刷ジョブを送信するコマンドは、次のとおりです。 lp -s -d myprinter -t$XPDOCNAME $XPDOCNAME は、プリンタに送信された出力ファイルの名前を表し ます。-s オプションを指定すると、EAServer コンソールでの lp から送 信されたメッセージの表示が抑制されます。 この後に、dwprint.ini ファイルの[ports]セクションの例を示します。 このセクションでは、prnt1、prnt2 というリモート プリンタ用に定義さ れた 2 つのポート、ローカル プリンタ用の 1 つのポート、およびファ イルへの印刷用のエントリが記述されています。出力ファイルの名前 は引用符で囲みます。このように指定すると、複数単語のファイル名 を使用できます。rsh スクリプトで引用符が取り除かれるので、リモー ト サーバでエスケープしなければなりません。 [ports] colorpr1=rsh prntsvr lp -s -d prnt1 -t\"$XPDOCNAME\" colorpr2=rsh prntsvr lp -s -d prnt2 -t\"$XPDOCNAME\" LOCAL=lp -d myprinter -t"$XPDOCNAME" FILE: = アプリケーション テクニック 561 データの印刷 プリンタの種類を定義 済みのポートに合わせ る [devices]セクションには、現在設定されているすべてのプリンタのリ ストを記述します。各行には、プリンタのユーザ定義のエリアス、お よび 3 つの引数としてプリンタ機種、プリンタ モード(PCL4、PCL5、 または PostScript)、プリンタが接続されている 1 つまたは複数のポー トが記述されます。 プリンタ機種は、プリンタで使用されるプリンタ記述ファイル(PPD) の名前です。PPD ファイルは、PBVM のインストール時に dwprinter/ppds ディレクトリにインストールされています。そのディレクトリ内のテ キスト ファイル filename_map.txt で、プリンタ記述を含むファイルの 名前をプリンタの種類にマップします。たとえば、次に示すのは、以 降の例で使用する color_lj モデルのマッピングです。 color_lj.pcl:"HP Color LaserJet PCL Cartridge" color_lj.ps:"HP Color LaserJet PS" プリンタ機種とモードは、スペースで区切ります。モードとポートは、 カンマで区切ります。たとえば、次の[devices]セクションで指定さ れている最初のデバイスの場合は、エリアスが HP Color LaserJet PS で あり、機種は color_lj、モードは PostScript で、2 つのポート(FILE: と colorpr1)が指定されています。 [devices] HP Color LaserJet PS=color_lj PostScript,FILE:,colorpr1 HP Color LaserJet PS=color_lj PCL5,colorpr2 HP Color LaserJet PS=color_lj PostScript,LOCAL HP LaserJet PS=NULL PostScript,FILE: HP LaserJet PCL=NULL PCL,FILE: デフォルト プリンタ の指定 [windows] セクションには、デフォルト プリンタ情報を記述します。 ポートの指定と同様に、各デバイス行で 3 つの引数として PPD ファイ ル、ドライバ、およびポートの名前を指定しますが、[windows]セク ションでは、それらをすべてカンマで区切ります。 次の例は、プリンタ ファイル記述が NULL に設定されたときにファイ ルに印刷するためのデフォルト エントリ、およびほかの 2 つのエント リを示しています。後半 2 行の先頭のセミコロンはコメント文字なの で、現在のデフォルト プリンタは、ポート colorpr1 の HP Color LaserJet プリンタになっています。 [windows] device=color_lj,PostScript,colorpr1 ;device=color_lj,PostScript,colorpr2 ;device=NULL,PostScript,FILE: 562 PowerBuilder 第 24 章 プリンタ オプション の設定 EAServer コンポーネントの構築 dwprint.ini ファイルには、 [windows]、 [devices]、 [ports]の各セクショ ンで定義した機種ごとに環境設定セクションを記述しなければなりま せん。環境設定セクションでは、部数、印刷の向き、ページ サイズ、 DPI などの、プリンタのデフォルト設定情報を指定します。 たとえば、先ほどの例で使用された color_lj プリンタの場合は、次のよ うに環境設定セクションを追加します。 [color_lj,PostScript] Filename=jaguar.ps Scale=1.00 Copies=1 Orientation=Portrait PageSize=Letter DPI=300 [color_lj,PCL5] Filename=jaguar.pcl Scale=1.00 Copies=1 Orientation=Portrait PageSize=Letter DPI=300 XPPATH 環境変数の 設定 印刷ジョブを開始する前に、XPPATH 環境変数を設定します。XPPATH 変数には、プリンタ記述ファイルとプリンタ固有のフォント マッピン グ ファイルを格納しているディレクトリへのパスを設定しなければ なりません。これらのファイルは、PBVM のインストール時に dwprinter ディレクトリにインストールされます。 C シェルの場合は、次のようにパスを設定します。 setenv XPPATH $EAServer/dwprinter Korn シェルまたは Bourne シェルの場合は、次のようにパスを設定し ます。 XPPATH = $EAServer/dwprinter;export XPPATH PDF への印刷 データストアのデータを PDF に保存するには、GNU Ghostscript distiller を利用するか、XSL Formatting Objects(XSL-FO)を使用してデータを 処理する機能を利用します。データウィンドウ オブジェクトのデータ を XSL-FO または PDF に保存し、Java の印刷機能を利用して印刷でき ます。 アプリケーション テクニック 563 EAServer へのコンポーネントの配布 GNU Ghostscript distiller の使い方 GNU Ghostscript distiller を使用するには、Ghostscript ファイルおよびデ フォルト PostScript プリンタ ドライバと関連ファイルをサーバ上の PowerBuilder ランタイム ファイルと同じディレクトリにインストール しておく必要があります。Ghostscript メソッドは、UNIX ではサポート されていません。 XSL-FO の使い方 XSL-FO を使用するには、Apache XSL Formatting Objects プロセッサ (FOP)をサーバ上の PowerBuilder ランタイム ファイルと同じディレク トリにインストールされていて、以下の JAR ファイルがクラスパスに なければなりません。 fop-0.20.4\build\fop.jar fop-0.20.4\lib\batik.jar fop-0.20.4\lib\xalan-2.3.1.jar fop-0.20.4\lib\xercesImpl-2.1.0.jar fop-0.20.4\lib\xml-apis.jar fop-0.20.4\lib\avalon-framework-cvs-20020315.jar これらのファイルを CLASSPATH 環境変数、あるいは User_setenv.bat または Serverstart.bat に追加できます。 EAServer で XSL-FO を使用して PDF ファイルを生成すると、詳細情報 メッセージと警告メッセージが Jaguar ログに書き込まれます。これら のメッセージの出力を抑制するには、環境変数 PB_FOP_SUPPRESSLOG に 1 を設定します。 詳細については、PowerBuilder の『ユーザーズ ガイド』マニュアルの 「データウィンドウ オブジェクトの機能拡張」の章を参照してくださ い。 EAServer へのコンポーネントの配布 サーバ上に PowerBuilder VM が必 要 564 コンポーネントを、Windows、UNIX および Linux 上で稼動している EAServer ホストに配布できます。開発に使用したコンピュータの PowerBuilder VM のバージョンが、サーバ上でも使用できる必要があ ります。 PowerBuilder 第 24 章 EAServer コンポーネントの構築 PowerBuilder VM には、PBVM110.DLL、PBJAG110.DLL、 PBDWM110.DLL など、実行時に必要な PowerBuilder ファイルが用意 されています。UNIX および Linux の場合、共有ライブラリは libpbvm110x.ext、libdwm110x.ext、などと呼ばれ、ext は各プラット フォームの共有ライブラリ拡張子です。EAServer は PowerBuilder ラン タイム ファイルを使用します。PowerBuilder ランタイム ファイルは、 ファイル名の最後に x が付き、印刷を含む Window API の呼び出しや グラフィック処理をサポートしていません。 PowerBuilder NVO からの .NET Web サービスの利用 EAServer で稼働している PowerBuilder コンポーネントから .NET Web サービスを呼び出す場合、Sybase.PowerBuilder.WebService.Runtime.dll、 Sybase.PowerBuilder.WebService.RuntimeRemoteLoader.dll、および動的に 生成される .NET アセンブリを EAServer bin ディレクトリに配布する 必要があります。 EAServer は、同一サーバ上で PowerBuilder VM の複数のバージョンを サポートします。異なるバージョンの PowerBuilder で作成されたコン ポーネントは、必要なバージョンの PowerBuilder VM がサーバ上で使 用できる限り、同一サーバ上で共存できます。 PowerBuilder 11 から EAServer にコンポーネントを配布するときは、 コンポーネントは使用している PowerBuilder VM のバージョンに関連 付けられます。EAServer 5.x の EAServer Manager では、コンポーネン トのプロパティ シートの[Advanced]タブ ページの com.sybase.jaguar.component.pb.version プロパティが 11.0 に設定されま す。EAServer 6.x では、CORBA Packages ノード下のコンポーネントの [General]プロパティ ページに表示されます。 PowerBuilder 開発環境を使用しないで PowerBuilder コンポーネントを EAServer に配布する場合は、EAServer Manager のコンポーネントのプ ロパティ シートに、正しい VM のバージョンを指定できます。 開発環境で使った PowerBuilder VM のバージョンがないサーバでは、 PowerBuilder コンポーネントを配布しても、そのコンポーネントはイ ンスタンス化できません。 EAServer コンポーネ ントの配布について コンポーネントを EAServer に配布するには、プロジェクトを新規作成 して構築します。新規プロジェクトでは、組み込まれるオブジェクト の一覧を表示し、生成されたコンポーネントを格納する出力ライブラ リの名前を指定します。 アプリケーション テクニック 565 EAServer へのコンポーネントの配布 データウィンドウの定義の有効化 データウィンドウ オブジェクトを動的に参照するスクリプトの場合 は、ウィザードまたはペインタの[統合 PBD に参照されないオブジェ クトを含める]ボックスをオンにして、データウィンドウの定義がコ ンポーネントで使用できるようにしなければなりません。 コンポーネントの配布 方法 コンポーネントを EAServer に配布するには、ウィザードによって作成 されたプロジェクトを開いて、 [デザイン|プロジェクトの配布]を選 択します。 EAServer への配布後 の処理内容 コンポーネントを EAServer に配布すると、コンポーネント ジェネレー タによって以下の処理が行われます。 • 配布用に選択した非ビジュアル オブジェクトを記述する CORBA IDL を生成 この IDL は、さらにスタブとスケルトンの作成に使用されます。 IDL ファイル、スタブ、およびスケルトンの名前は、オブジェク トの名前に基づいています。 コンポーネント ジェネレータは、EAServer のインストール ディレ クトリの Repository サブディレクトリに新しい IDL を格納します。 • EAServer コンポーネントのプロパティを記述する PROPS ファイ ルを生成 PROPS ファイルは、EAServer のインストール ディレクトリのサブ ディレクトリに格納されます。このサブディレクトリのパスを次 に示します。Repository\Component\package-name • 配布されたコンポーネントに対して 1 つまたは複数の PBD ファイ ルを生成 PBD ファイルは、EAServer のインストール ディレクトリのサブ ディレクトリに格納されます。このサブディレクトリのパスを次 に示します。Repository\Component\package\component\Ccookie ここで、cookie は構築の生成番号を表します。ライブラリ名が修飾 されていない(パスが指定されない)場合には、コンポーネント ジェネレータは名前の前に円記号(\)を付けます。デフォルトで は、EAServer は最新版のコンポーネントを使用します。 EAServer リポジトリ の後処理 566 ディスク スペースを再度割り当てるには、次の手順で、不要になった ディレクトリを削除します。 PowerBuilder 第 24 章 ❖ 不要なディレクトリと PBD ファイルを削除するには 1 最新のディレクトリ以外のディレクトリをすべて削除します。 2 残りのディレクトリの名前を C1 に変更します。 3 4 コンポーネントのコー ド セットの変更 EAServer コンポーネントの構築 EAServer Manager のコンポーネントのプロパティ シートにある [Advanced]タブ ページ、または Management Console の[Advanced] タブ ページで、pb.cookie プロパティの値を 1 に設定します。 EAServer を再起動します。 PowerBuilder によって配布された EAServer コンポーネントは、自動的 にサーバのコード セットを使用します。コンポーネントに別のコー ド セットを使用させたい場合は、コンポーネントの com.sybase.jaguar.component.code.set プロパティに適切な値を設定しま す。 このプロパティを設定する場合、EAServer Manager では、 [Advanced] タブ ページのコンポーネント プロパティ ダイアログボックスを使用 します。com.sybase.jaguar.component.code.set プロパティを追加して、 big5 や iso_1 などの適切な値を指定します。Management Console では、 [General]ページの[Code Set]ドロップダウン リストから値を選択し ます。 EAServer が utf-8 コード セットを使用して起動され、コンポーネント でユーロまたは英国ポンドの記号、あるいはその両方を含んでいる文 字列を返す場合は、code.set プロパティに cp1252 を設定します。 アプリケーション テクニック 567 EAServer へのコンポーネントの配布 568 PowerBuilder 第 2 5 章 EAServer クライアントの構築 この章について この章では、EAServer コンポーネントにアクセスする PowerBuilder クライアントの作成方法について説明します。セキュリティで保 護された接続については、第 26 章「PowerBuilder クライアントで の SSL の使い方」を参照してください。 内容 項目 EAServer クライアントの構築について EAServer への接続 EAServer プロキシ オブジェクトの生成 コンポーネント メソッドの呼び出し JaguarORB オブジェクトの使用 クライアントとコンポーネントを区別するトランザクション サーバ メッセージ返送の要求 エラー処理 クライアント アプリケーションの配布 ページ 569 571 574 576 583 588 591 596 601 EAServer クライアントの構築について PowerBuilder アプリケーションは、EAServer コンポーネントのク ライアントの役割を果たします。サーバ上のコンポーネントに関 連付けられたメソッドにアクセスするには、PowerBuilder クライ アントは、サーバに接続し、コンポーネントをインスタンス化し、 コンポーネント メソッドを呼び出す必要があります。 EAServer への接続には、接続オブジェクトのインスタンスを使用 するのが一般的ですが、CORBA 互換クライアントを作成する場合 には、JaguarORB オブジェクトを使用してサーバへの接続を確立 することも可能です。 JaguarORB オブジェクトを使うと、 PowerBuilder クライアントは、C++ クライアントと同じ方法で EAServer にアク セスできます。 アプリケーション テクニック 569 EAServer クライアントの構築について この章で説明する技法を使えば、EAServer で実行する EJB コンポーネ ントのクライアントを構築できます。EAServer やほかの J2EE 準拠の サーバで EJB コンポーネントのクライアントを構築する方法について は、第 29 章「EJB クライアントの構築」を参照してください。 ウィザードの使い方について PowerBuilder には、EAServer クライアントの開発に役立つ 2 つのウィ ザードがあります。 • 接続オブジェクト ウィザード サーバへの接続に必要なコードを追 加する • クライアントからアクセスする EAServer コンポーネントのプロキシ オブジェクトを構築するため のプロジェクトの作成に役立つ EAServer プロキシ ウィザード 開発プロセスについて EAServer クライアン トの構築手順 EAServer クライアントを構築して配布するには、以下の手順をすべて 実行する必要があります。 1 EAServer 接続オブジェクト ウィザードを使用して、Connection オ ブジェクトから継承した標準クラスのユーザ オブジェクトを作成 します。その後で、このオブジェクトを、接続を確立するために スクリプトの中で使用できます。 テンプレート アプリケーション ウィザードを使用してクライア ント アプリケーションを作成した場合は、そのウィザードで接続 オブジェクトを作成できます。 570 2 EAServer プロキシ ウィザードを使用して、プロキシ オブジェクト を作成するためのプロジェクト作成します。続いてプロキシ オブ ジェクトを生成します。 3 ユーザ インタフェースの実装に必要なウィンドウ、メニュー、お よびスクリプトを作成します。 4 EAServer コンポーネント インスタンスの作成と、クライアントか ら 1 つまたは複数のコンポーネント メソッドの呼び出しを行うた めに必要なコードを記述します。 5 クライアントのテストとデバッグを行います。 PowerBuilder 第 25 章 6 EAServer クライアントの構築 アプリケーションを配布します。 EAServer への接続 接続オブジェクトの使 用 EAServer に接続するには、接続オブジェクト(サーバとの通信を処理 する非ビジュアル オブジェクト)の機能を利用するのがもっとも簡単 な方法です。サーバに接続するには、接続のためのコードをすべて手 動で記述するか、接続オブジェクト ウィザードを使用して接続を開始 します。 コードを手書きする方法 connection 変数の宣 言 接続オブジェクトは組み込みのグローバル オブジェクトではありま せん。connection 型を指定して、グローバル変数またはインスタンス変 数を宣言する必要があります。 接続の確立 サーバへの接続を確立するには、以下の操作を実行するために必要な PowerScript 文を実行する必要があります。 1 Create 文を使用して、接続オブジェクトをインスタンス化します。 2 接続オブジェクトのプロパティを設定します。 3 ConnectToServer 関数を呼び出して、サーバへの接続を確立します。 4 エラーの有無をチェックします。 これらの操作は、1 つのスクリプトまたは複数のスクリプトで実行で きますが、上記の順に行う必要があります。 次のスクリプトでは、myconnect 接続オブジェクトをインスタンス 化し、EAServer の通信ドライバ、サーバのホスト名とポート番号、お よびデフォルト パッケージを識別するための接続プロパティを設定 します。続いて、このスクリプトは ConnectToServer 関数を呼び出して サーバへの接続を確立し、エラーをチェックします。 例 // グローバル変数 : // connection myconnect long ll_rc myconnect = create connection myconnect.driver = "jaguar" myconnect.location = "Jagserver1:2000" myconnect.application = "PB_pkg_1" アプリケーション テクニック 571 EAServer への接続 myconnect.userID = "bjones" myconnect.password = "mypass" ll_rc = myconnect.ConnectToServer() IF ll_rc <> 0 THEN MessageBox(" 接続失敗 ", ll_rc) END IF 接続オブジェクト プ ロパティの設定 表 25-1 に EAServer と通信する際の、接続オブジェクト プロパティを 設定するためのガイドラインを示します。 表 25-1: EAServer の接続オブジェクト プロパティ プロパティ名 Application Driver Location 説明 EAServer コンポーネントに 使用するデフォルト パッ ケージ EAServer ドライバの名前 サーバのホスト名とポート 番号をコロンで区切ったも の 例 "PB_pkg_1" "jaguar" "localserver:2000" "iiop://srv1:2000" "iiops://srv3:2001" Location プロパティには、 "http://srv5:8000" 以下のいずれかの書式を使 用する。絶対パス URL も指 "iiop://s1:2000;iiop://s2:2000" 定できる iiop://host:port iiops://host:port http://host:port https://host:port Password UserID Options 複数の接続を確立 572 EAserver の負荷分散とフェ イルオーバのサポートを利 用する際、サーバの位置をセ ミコロンで区切ってリスト 形式で指定することも可能 "mypass" EAServer のパスワード "bjones" EAServer のユーザ ID 1 つまたは複数の EAServer "ORBLogFile='jaglog.log'" ORB プロパティ設定 PowerBuilder では、複数の接続オブジェクトをインスタンス化できま す。したがって、1 つのクライアント アプリケーションで複数の接続 を確立できます。たとえば、2 つの別個の接続オブジェクトをインス タンス化して、2 台の別々のサーバ にクライアントを接続することも 可能です。 PowerBuilder 第 25 章 EAServer クライアントの構築 設定オプション 接続オブジェクトまたは JaguarORB オブジェクトのいずれかを使用し て EAServer に接続するときは、EAServer クライアント ORB を使用す ることになります。そのプロパティは、接続オブジェクトの Options 文 字列に設定するか、JaguarORB の Init 関数を使用して設定できます。 使用するコード セッ トの変更 PowerBuilder 9.x 以前のバージョンでは、2 バイト文字を扱う EAServer コンポーネントに接続する際には、コンポーネントが適切なコード セットを設定する必要がありました。 myConnection.Options = "ORBCodeSet='eucksc'" PowerBuilder 10 以降では、UNICODE で処理を行なっているために ORBCodeSet の設定をする必要がなくなりました。以前のバージョン から、ORBCodeSet を使用しているアプリケーションを移行する場合 は、ORBCodeSet パラメータを削除する必要があります。 接続のトラブルシュー ティング 接続が失敗した場合、ORBLogIIOP オプションをオンにし、ORBLogFile オプションの値を指定して、失敗に関する詳細をログ ファイルに記録 できます。設定するオプションが複数ある場合は、それらのオプショ ンを同一の文中に設定しなければなりません。オプションは、次のよ うにカンマで区切ります。 myConnection.Options = & "ORBLogIIOP='TRUE', ORBLogFile='d:\temp\ORBLog.txt'" 全オプションの一覧については、接続オブジェクトに関するオンライ ン ヘルプまたは EAServer のマニュアルを参照してください。 ウィザードを使用した接続オブジェクトの作成 接続オブジェクト ウィザードで、接続タイプとして EAServer を選択 した場合には、接続オブジェクトから継承された標準クラスのユーザ オブジェクトが作成されます。ウィザードで接続オブジェクト プロパ ティを指定し、接続情報の提供元としてレジストリ、INI ファイル、ま たはスクリプトを指定します。接続オブジェクト ウィザードは、開発 者がセットアップした EAServer プロファイルから、接続先のサーバに 関する情報を取得します。EAServer プロファイルの作成方法について は、503 ページの「アプリケーション サーバ プロファイルの作成」を 参照してください。 接続オブジェクトの Constructor イベントは、of_getconnectioninfo 関数を 呼び出して、指定したソースから格納済みの接続情報を取得します。 アプリケーション テクニック 573 EAServer プロキシ オブジェクトの生成 接続オブジェクト ウィザードを使用して接続オブジェクトを作成し たら、以下の操作の実行に必要な PowerScript 文を実行する必要があり ます。 1 Create 文を使用して、接続オブジェクトをインスタンス化します。 2 ConnectToServer 関数を呼び出して、サーバへの接続を確立します。 3 エラーをチェックします(省略可)。 接続オブジェクトのプロパティは設定不要ですが、それらのプロパ ティは of_getconnctioninfo 関数で修正できます。接続オブジェクトのオ プションを constructor イベントで設定することも可能です。たとえば、 次のようにします。 this.options = "ORBHttp='TRUE'" 次のスクリプトでは、ウィザードで作成された n_myclient_connect オブジェクトの myconnect インスタンスをインスタンス化し、 ConnectToServer 関数を呼び出してサーバへの接続を確立し、エラーを チェックします。 例 long ll_rc myconnect = create n_myclient_connect ll_rc = myconnect.ConnectToServer() IF ll_rc <> 0 THEN MessageBox(" 接続失敗 ", ll_rc) END IF 複数の接続を確立 1 つのクライアント アプリケーションで複数の接続を確立できます。2 台の別々のサーバにクライアント接続したい場合には、もう一度接続 オブジェクト ウィザードを実行して、別々の接続プロパティを持つ新 規ユーザ オブジェクトを作成します。 EAServer プロキシ オブジェクトの生成 EAServer プロキシ オ ブジェクトについて 574 各 EAServer コンポーネントには、クライアント アプリケーション内 に対応するプロキシ オブジェクトがあります。EAServer コンポーネン トにアクセスするには、EAServer プロキシを通じて通信する必要があ ります。 PowerBuilder 第 25 章 EAServer クライアントの構築 クライアント アプリケーションには、EJB コンポーネントに対応する 2 つのプロキシ オブジェクト(ホーム インタフェース用とリモート イ ンタフェース用)があります。たとえば、Cart という名前の EJB コン ポーネントは、CartHome と Cart という 2 つのプロキシを生成します。 EJB コンポーネントにアクセスするには、これら 2 つのプロキシを介 して通信する必要があります。 EAServer クライアントのプロキシ オブジェクトは、新規プロジェクト を作成してから生成する必要があります。新規プロジェクトでは、組 み込まれるオブジェクトの一覧を表示し、生成されたプロキシ オブ ジェクトを格納する出力ライブラリの名前を指定します。 EAServer プロキシ ウィザードの使い方 EAServer プロキシ ウィザードは、EAServer プロキシ オブジェクトを 作成するためのプロジェクトの作成に役立ちます。このウィザードを 使うと、EAServer サーバに接続して、クライアントからアクセスでき るようにしたいコンポーネントを選択できます。プロジェクトを作成 したら、続いてプロジェクト ペインタを使用してプロジェクト設定を 修正し、プロキシ ライブラリを作成できます。 EJB クライアントの構築 EAServer やほかの J2EE 準拠のサーバで EJB コンポーネントのサービ スを利用できる EJB クライアントを構築するには、EJB クライアント プロキシ ウィザードを使います。詳細については、第 29 章「EJB ク ライアントの構築」を参照してください。 メソッド名の予約語 PowerBuilder で作成されなかった EAServer コンポーネント用にプロキ シを生成すると、PowerBuilder の予約語を使用するメソッドの名前が 変更されます。プロキシ ジェネレータは、これらのメソッド名の先頭 にアンダースコア(_)を自動的に追加します。たとえば、コンポーネ ントに destroy という名前のメソッドがある場合、プロキシのメソッド は _destroy になります。 TO 句の配列の使い方 CORBA IDL では TO 句がサポートされていないため、TO 句を使用す る配列を含む PowerBuilder コンポーネントのプロキシを生成する場 合、プロキシ オブジェクトは範囲を単一値として表します。たとえば、 Int ar1[5 TO 10] は Int ar1[6] と表します。この [6] は、配列の要 素数を表しています。クライアント アプリケーションは、範囲ではな く単一値を使用して配列を宣言しなければなりません。 アプリケーション テクニック 575 コンポーネント メソッドの呼び出し モジュール名の付加 コンポーネントを定義する IDL モジュールの名前を、作成したプロキ シ オブジェクトの名前の前に付加しておくと、名前が類似するプロキ シ オブジェクトどうしを容易に判別できます。たとえば、CTSSecurity モジュールの SessionInfo コンポーネントを選択して、ウィザードかプ ロジェクト ペインタの[EAServer パッケージ名をオブジェクト名の前 に 追 加]オ プ シ ョ ン を オ ン に す る と、プ ロ キ シ オ ブ ジ ェ ク ト が ctssecrity_sessioninfo という名前になります。一部の EAServer シ ステム モジュール(現在のところ、CtsComponents と XDT)では、名 前の二重定義を避ける目的から、常にモジュール名がオブジェクトに 付加されます。 パッケージ名と IDL モジュールの名前は普通は同じですが、異なって いてもかまいません。いずれの場合にも、前に付加されるのは IDL モ ジュールの名前です。 例外の除外 EAServer コンポーネントのなかには、クライアント アプリケーション で処理できる例外を送出するものが数多くあります。例外を処理しな い既存のクライアント アプリケーションでプロキシを生成して使用 したい場合、または構築しているクライアント内で例外を宣言したく ない場合は、ウィザードかプロジェクト ペインタで、生成されたプロ キシから例外を除外できます。クライアントでのエラー処理について の詳細は、596 ページの「エラー処理」を参照してください。 データ型マッピング EAServer コンポーネント インタフェースはすべて、標準の CORBA IDL で定義されます。EAServer で使用されるデータ型、各データ型の対応 する CORBA IDL、および各データ型がマッピングされる PowerBuilder のデータ型のリストについては、 『PowerScript リファレンス』マニュ アルまたはオンライン ヘルプを参照してください。 コンポーネント メソッドの呼び出し EAServer への接続が確立され、プロキシ オブジェクトかオブジェクト が作成された後ではじめて、クライアント アプリケーションはサーバ コンポーネントを使用できます。 コンポーネント メソッドの呼び出し ほとんどのコンポーネント タイプでメソッドを呼び出す際は、以下の 操作を行うのに必要な PowerScript 文を実行する必要があります。 576 PowerBuilder 第 25 章 1 EAServer クライアントの構築 CreateInstance メソッドを使用して、コンポーネントのインスタンス を作成する 2 メソッドを呼び出す EJB コンポーネント メソッドは、別の方法で呼び出します。578 ペー ジの「EJB コンポーネント メソッドの呼び出し」を参照してください。 例 1 次のスクリプトでは、サーバ上のコンポーネントをインスタンス 化し、コンポーネント メソッドを呼び出します。この例では、パッ ケージを CreateInstance メソッドに指定していません。したがって、 EAServer は、接続オブジェクトの Application プロパティに指定されて いるデフォルト パッケージを使用します。 // グローバル変数 : // connection myconnect uo_customer iuo_customer string ls_custid long ll_rc ls_custid = Trim(sle_custid.text) ll_rc = myconnect.CreateInstance(iuo_customer) if ll_rc <> 0 then MessageBox("CreateInstance 失敗 ", ll_rc) return 999 end if if iuo_customer.retrieve_balance(ls_custid) != 1 then MessageBox(" エラー ", " 検索失敗 !") end if 例 2 次のスクリプトでは、サーバ上のコンポーネントをインスタンス 化して、データ型がコンポーネントのクラスの先祖である変数に、オ ブジェクト参照を割り当てます。CreateInstance 関数の第 2 引数には、 コンポーネントのクラス名に加えて、EAServer パッケージ名も指定し ます。 // グローバル変数 : // connection myconnect uo_person lnv_object string ls_custid long ll_rc ls_custid = Trim(sle_custid.text) ll_rc = myconnect.CreateInstance(lnv_object, & "PB_pkg_1/uo_customer") if ll_rc <> 0 then アプリケーション テクニック 577 コンポーネント メソッドの呼び出し MessageBox("CreateInstance 失敗 ", ll_rc) return 999 end if if iuo_customer.retrieve_balance(ls_custid) != 1 then MessageBox(" エラー ", " 検索失敗 !") end if ローカル インスタンスの呼び出し デフォルトでは、 TransactionServer の CreateInstance メソッドは EAServer のネーム サービスを呼び出してプロキシを作成します。リモート コン ポーネントのプロキシは、ローカルで実行されているインスタンスで はなくネーム サービスから返される場合があります。ローカルのイン スタンスが使用されるようにするには、コンポーネント名として 「local:package/component」を指定します。package はパッケージ名、 component はコンポーネント名です。コンポーネントが同じサーバにイ ンストールされていない場合、呼び出しはエラーになります。 EJB コンポーネント メソッドの呼び出し EJB コンポーネント メソッドを呼び出すには、以下の操作を行うのに 必要な PowerScript 文を実行する必要があります。 1 Lookup 関数を使用して、コンポーネントのホーム インタフェース にアクセスする 2 インタフェースでメソッドを呼び出し、コンポーネントのインス タンスの作成か検索を実行して、コンポーネントのリモート イン タフェースへの参照を取得する 3 リモート インタフェースでビジネス メソッドを呼び出す EJBConnection メソッドに適用されないこと 本節の内容は、EAServer プロキシ オブジェクトと PowerScript 関数を 使用するクライアント アプリケーションに適用されます。EJB クライ アント プロキシと EJBConnection メソッドを使用するクライアント ア プリケーションで EJB メソッドを呼び出す方法については、第 29 章 「EJB クライアントの構築」を参照してください。 578 PowerBuilder 第 25 章 ホーム インタフェー ス名の指定 EAServer クライアントの構築 PowerBuilder の Lookup 関数には第 3 引数(省略可能)が用意されてい て、この引数にホーム インタフェース名を指定できます。EAServer で は、EJB コンポーネントに com.sybase.jaguar.component.home.ids という プロパティが設定されます。home.ids プロパティが次のような形式で あれば、Lookup 関数に第 3 引数を指定する必要はありません。 IDL:PackageName/ComponentNameHome:1.0 例 IDL:vacation/TripFinderHome:1.0 ただし多くの場合は home.ids プロパティに java パッケージの命名ス キーマを使うため、開発者は EJB インタフェースが確実に見つけられ るように、第 3 引数を使用しなければなりません。この引数には、先 頭の IDL: と末尾の :1.0 を除いて、コンポーネントの com.sybase.jaguar.component.home.ids プロパティと一致している文字列 を指定する必要があります。 たとえば、次のような home.ids プロパティがあるとします。 IDL:com/myproj/myejbs/TripFindHome:1.0 この場合、Lookup 関数呼び出しは次のようになります。 myconn.lookup(myTripFindHome,"MyEJBs/TripFindHome", & "com/myproj/myejbs/TripFinderHome") あるいは、ドット表記で指定するホーム インタフェースの完全修飾 Java クラス名を使用することもできます。たとえば、次のようになり ます。 ts.lookup(MyCartHome, "MyEJBs/TripFindHome", & "com.myproj.myejbs.TripFinderHome") Lookup の大文字と小文字の区別 EAServer の Lookup では大文字と小文字が区別されます。Lookup 関数の 引数に指定する文字列の大文字と小文字は、home.ids プロパティの大 文字と小文字に一致させる必要があります。 EJB のインスタンス の作成や検索 EAServer では、3 種類の EJB(セッション Bean、エンティティ Bean、 およびメッセージ駆動型 Bean)をサポートしています。 セッション Bean は、クライアントのリクエストに応答して作成されま す。クライアントは、通常の場合、そのクライアント セッションの持 続中はセッション Bean を排他的に使用します。 アプリケーション テクニック 579 コンポーネント メソッドの呼び出し エンティティ Bean は、データベースに保存される永続情報を表しま す。クライアントは、ほかのクライアントと同時にエンティティ Bean を使用します。エンティティ Bean はクライアントの有効期間が終了し ても持続するため、エンティティ Bean がすでに作成されている場合 は、主キーのクラス名を使用して、既存のコンポーネントの識別や検 索を行う必要があります。 メッセージ駆動型 Bean はステートレス セッション Bean に似ています が、JMS メッセージのみに応答し、直接のクライアント インタフェー スは備えていません。 次の例では、E コマースのショッピング カート機能を提供する EJB コ ンポーネントが EAServer 上で実行されていることを想定しています。 このコンポーネントは Cart と呼ばれ、Shopping というパッケージに含 まれています。 例 1 このスクリプトは、Cart コンポーネントをインスタンス化し、い くつかのコンポーネント メソッドを呼び出します。次の例では、Lookup メソッドの第 2 引数に、コンポーネント名と EAServer パッケージ名を 指定しています。 // インスタンス変数: //Connection myconnect CartHome MyCartHome // EJB のホーム インタフェース Cart MyShoppingCart // EJB のリモート インタフェース long ll_result // ホーム インタフェースを取得 ll_result = & myconnect.Lookup(MyCartHome, "Shopping/Cart", & "com.sybase.shopping.Cart") // Cart コンポーネントのビジネス ロジックへの参照を取得 TRY MyShoppingCart = MyCartHome.Create() CATCH (ctscomponents_createexception ce) MessageBox(" 例外を作成 ", ce.getmessage()) // 例外を処理 END TRY // ショッピング カートを使用 MyShoppingCart.AddItem(66) MyShoppingCart.Purchase() 580 PowerBuilder 第 25 章 EAServer クライアントの構築 CartEJB コンポーネントがエンティティ Bean として定義されて いる場合は、スクリプトは findByPrimaryKey メソッドを使用して、既存 のコンポーネントか永続コンポーネントを検索し参照しなければなり ません。 例2 // インスタンス変数: //Connection myconnect CartHome MyCartHome // EJB のホーム インタフェース Cart MyCart // EJB のリモート インタフェース long ll_result // ホーム インタフェースを取得 ll_result = & myconnect.Lookup(MyCartHome, "Shopping/Cart", & "com.sybase.shopping.Cart") // 前のセッションからの Cart への参照を取得 TRY MyCart = MyCartHome.findByPrimaryKey("MYkey") CATCH ( ctscomponents_finderexception fe ) MessageBox(" 検索例外 ", & fe.getmessage()) // 例外を処理 END TRY // ショッピング カートを使用 MyCart.AddItem(66) MyCart.Purchase() 制約 EJB オブジェクトに対して PowerBuilder クライアントは CORBA クラ イアントの役割を果たします。つまり、PowerBuilder クライアントに は Java クライアントの全機能はありません。Java クライアントは、 javax.ejb.EJBObject インタフェースから継承したメソッドを使用でき ます。 たとえば、Java クライアントはリモート インタフェース インスタンス のハンドルを取得できます。ハンドルは、クライアントと Bean の間の セッション状態を示すバイナリ エンコーディングです。クライアント はハンドルを取得し、それをディスクに保存するか別の場所に送信し、 後でセッションを再び確立できます。PowerBuilder クライアントが同 等の機能を得るには、JaguarORB オブジェクトの Object_To_String 関数 と String_To_Object 関数を使用する必要があります。 アプリケーション テクニック 581 コンポーネント メソッドの呼び出し 例外の処理 EJB コンポーネントのリモート インタフェースに、エラーか警告が示 される場合があります。EJB コンポーネントから送出された標準例外 は、CORBA システム例外にマッピングされます。また EJB コンポー ネントが、ユーザ定義の例外を送出する場合もあります。EAServer コ ンポーネントから送出された例外の処理については、596 ページの「エ ラー処理」を参照してください。 EAServer 内の PowerBuilder コンポーネントからの EJB コンポーネント の呼び出しについては、545 ページの「EJB コンポーネントへのアク セス」を参照してください。 インスタンスの破棄 プロキシ オブジェク トのインスタンスの破 棄 EAServer コンポーネントを使い終わったら、DESTROY 文を使用して EAServer プロキシ オブジェクトを明示的に破棄するか、PowerBuilder のガベージ コレクション機能を利用してオブジェクトを自動的にメ モリから消去できます。いずれの場合でも、クライアントサイド プロ キシ オブジェクトの破棄は、サーバ コンポーネントの有効期間に影響 を与えません。サーバ コンポーネントの破棄は、EAServer によって処 理されます。 コンポーネントのイン スタンスの非アクティ ブ化 コンポーネントの自動的なデマケーション / 不活性化設定が無効であ り、しかもコンポーネントがまだクライアントにバインドされている間に クライアント アプリケーションを閉じた(コンポーネントが SetComplete も SetAbort も呼び出さなかった)場合には、コンポーネントは非アク ティブにされません。コンポーネントのインスタンスを非アクティブ にするには、次のいずれかの操作を行います。 582 • クライアント アプリケーションの Close イベントで、 (SetComplete か SetAbort を呼び出して)コンポーネントを非アクティブにする サーバ コンポーネントのメソッドを呼び出します。 • コンポーネントの Timeout プロパティを 0 に設定してしまうと、コ ンポーネントがタイムアウトしなくなるので、0 以外の値に設定し ます。 PowerBuilder 第 25 章 EAServer クライアントの構築 JaguarORB オブジェクトの使用 CORBA 互換クライアントを作成するには、接続オブジェクトのかわ りに JaguarORB オブジェクトを使用して、サーバへの接続を確立しま す。JaguarORB オブジェクトを使用すると、C++ クライアントと同じ 方法で PowerBuilder クライアントから EAServer へアクセスすること ができます。 2 つの方法 JaguarORB オブジェクトは、String_To_Object 関数と Resolve_Initial_References 関数を使用する 2 つの方法でコンポーネント インタフェースにアクセスできます。 String_To_Object 関数の使用は、接続オブジェクトでの ConnectToServer 関 数 と CreateInstance 関 数 の 内 部 的 な 動 作 と 同 じ 動 作 を し ま す。 String_To_Object 関数では、コンポーネントをホストするサーバへの接 続方法を記述する文字列引数を渡すことで、プロキシのインスタンス をインスタンス化できます。この方法の不利な点は、ネーミング サー ビス API を明示的に使用することによって提供されるサーバ アドレ ス抽象化を活用できないことです。 EAServer ネーミング サービス API を使用する場合は、 Resolve_Initial_References 関数を使用して初期状態のネーミング コンテ キストを取得できます。ただし、この方法は廃止予定の SessionManager::Factory create メソッドを使用する必要があるため、こ の方法はお勧めしません。ほとんどの PowerBuilder クライアントは、 CORBA ネーミング サービスを明示的に使用する必要はありません。 かわりに、接続オブジェクトの CreateInstance 関数と Lookup 関数を使 用して EAServer コンポーネントのインスタンスを作成するときに自 動的に実行される名前解決に頼ることができます。 ネーミング サービス について EAServer ネーミング サービスは、CORBA CosNaming コンポーネント (オブジェクトのバインドと参照のサポートを提供するインタフェー スのコレクション)の実装です。CosNaming モジュールについての詳 細は、EAServer インタフェース リポジトリのマニュアルを参照して ください。インタフェース リポジトリのマニュアルは、URL http://yourhost:yourport/ir/ のサーバに接続すれば、Web ブラウザで参照 できます。ここで、yourhost はサーバのホスト名、yourport は HTTP ポート番号です。 アプリケーション テクニック 583 JaguarORB オブジェクトの使用 String_To_Object を使用したインスタンス化 SessionManage イン タフェースのプロキシ の取得 CORBA ネーミング サービスを明示的に使用せずにプロキシをインスタ ンス化するには、SessionManager モジュールに定義されているインタ フェースと一緒に、JaguarORB オブジェクトの String_To_Object 関数を 使用します。Manager、Session、および Factory インタフェースを使用す るには、事前に、EAServer プロキシ ウィザードを使用して SessionManager モジュールのプロキシ ライブラリ プロジェクトを作成し、プロジェク トを構築して、生成されたプロキシ ライブラリをクライアント ター ゲットのライブラリ リストに含めておく必要があります。 サーバの識別 サーバと対話するには、SessionManager::Manager インタフェースを使 用します。サーバは、Interoperable Object Reference(IOR)か URL を 使うと識別できます。IOR 文字列は、サーバのホスト アドレスと、サー バが IIOP リクエストを受け取るポートをエンコードします。サーバは 起動のたびに、標準エンコーディングで 16 進にエンコードされた IOR 文字列を、接続受け付けごとに 2 つのファイルに書き込みます。1 つ のファイルには IOR 文字列そのものが格納され、もう 1 つのファイル には IOR が、APPLET タグに挿入可能な HTML PARAM 定義の一部と して格納されます。ファイルは、EAServer ディレクトリの HTML サブ ディレクトリに常駐しています。これらのファイルのいずれかから IOR 文字列を取得するように、クライアントのコードを記述できます。 認証済みセッションの 作成 ORB を初期化してサーバの IOR か URL を取得した後で、String_To_Object 関数で文字列を CORBA オブジェクト参照に変換し、それを _Narrow 関 数で Manager インタフェースへの参照に変換できます。その後で、Manager インタフェースの createSession メソッドを使用して、クライアント ア プリケーションとサーバの間で認証されたセッションを作成します。 コンポーネントのイン タフェースへの参照の 作成 セッションの lookup メソッドを使用して、呼び出したいコンポーネン トへのプロキシ オブジェクト参照のファクトリを返します。次に、 Factory オブジェクトの create メソッドを呼び出して、コンポーネント のプロキシを取得します。create メソッドで CORBA オブジェクト参照 が返されたら、_Narrow 関数を使用して、それをコンポーネントのイン タフェースへの参照に変換できます。 コンポーネントのデフォルト名はパッケージ名とコンポーネント名で 構成され、calculator/calc のようにスラッシュで区切られています。た だし、コンポーネントの com.sybase.jaguar.component.naming プロパ ティで別の名前を指定することも可能です。たとえば、 USA/MyCompany/FinanceServer/Payroll などの論理名を指定できます。 ネーミング サービスの環境設定の詳細については、EAServer のマ ニュアルを参照してください。 584 PowerBuilder 第 25 章 例 EAServer クライアントの構築 次の例では、String_To_Object 関数の第 1 引数に、クラスタ内の 2 つの サーバの URL が含まれています。 // PowerBuilder オブジェクト JaguarORB my_JaguarORB CORBAObject my_corbaobj n_bank_acct my_acct // プロキシ オブジェクト Manager my_manager Session my_session Factory my_factory long ll_return my_JaguarORB = CREATE JaguarORB //ORB を初期化 ll_return = my_JaguarORB.init("ORBRetryCount=3, ORBRetryDelay=1000") //URL 文字列をオブジェクト参照に変換 ll_return = my_JaguarORB.String_To_Object (''iiop://JagOne:2000;iiop://JagTwo:2000'', my_corbaobj) //Manager インタフェースへのオブジェクト参照を制限 ll_return = my_corbaobj._narrow(my_manager, "SessionManager/Manager") // セッション オブジェクト参照を作成 my_session = my_manager.createSession("admin", "") // リモート インタフェースへの // プロキシ オブジェクト参照の Factory を作成 my_corbaobj = my_session.lookup("Bank/n_bank_acct ") my_corbaobj._narrow(my_Factory, "SessionManager/Factory") // プロキシを取得し、それをリモート インタフェースに // 制限してメソッドを呼び出す my_corbaobj = my_Factory.create() my_corbaobj._narrow(my_acct, "Bank/n_bank_acct") my_acct.withdraw(1000.0) この例では、コンポーネントは EJB コンポーネントです。ホーム イン タフェースは、CORBA コンポーネントに対してファクトリ インタ フェースが行うのと同じ役割を、EJB に対して効果的に実行します。 アプリケーション テクニック 585 JaguarORB オブジェクトの使用 JaguarORB my_orb CORBAObject my_corbaobj Manager my_mgr Session my_session CartHome my_cartHome Cart my_cart my_orb = CREATE JaguarORB my_orb.init("ORBLogFile='c:\temp\orblog'") my_orb.String_to_Object("iiop://svr1:2000", & my_corbaObj) my_corbaObj._narrow(my_mgr, "SessionManager/Manager" ) my_Session = my_mgr.createSession("admin", "") my_corbaObj = my_session.lookup("Cart") my_corbaObj._narrow(my_CartHome, "shopping/CartHome") my_corbaObj = my_CartHome.create() my_Cart.addItem() 接続オブジェクトの使用 接続オブジェクトの Lookup 関数を使用して、EJB コンポーネントの ホーム インタフェースへの参照を取得できます。578 ページの「EJB コンポーネント メソッドの呼び出し」を参照してください。 ネーミング サービス API によるインスタンス化 CosNaming インタ フェースと SessionManage イン タフェースのプロキシ の取得 CORBA ネーミング サービス API を使用してプロキシをインスタンス 化するには、ネーミング サービス インタフェースのプロキシを生成し て、生成したプロキシをクライアントのライブラリ リストに含める必 要があります。EAServer プロキシ ウィザードを使用して CosNaming モ ジュールのプロキシ プロジェクトを作成し、プロキシ ライブラリを作 成するためのプロジェクトを作成して、プロキシ ライブラリをクライ アント ターゲットのライブラリ リストに追加します。SessionManager モジュールにもプロキシが必要です。 初期状態のネーミング コンテキストの取得 ORB の初期化後、Resolve_Initial_References 関数を呼び出して初期状態 のネーミング コンテキストを取得し、_Narrow を使用してそれを CORBA ネーミング コンテキスト インタフェースへの参照に変換します。次の 例に示すように、クラス名に omg.orb を含めて、CosNaming パッケー ジを識別しなければなりません。 586 PowerBuilder 第 25 章 EAServer クライアントの構築 ネーミング コンテキ ストの解決 ネーミング コンテキストを解決してコンポーネントの Factory オブ ジ ェ ク ト へ の 参 照 を 取 得 し、そ の 後 で そ の イ ン タ フ ェ ー ス を SessionManager::Factory インタフェースへの参照に制限する必要があ ります。resolve メソッドは、一連の NameComponent 構造体である名前 パラメータを取ります。各 NameComponent 構造体には、コンポーネン トを識別する id 属性と、コンポーネントの記述に使用できる kind 属性 があります。次の例では、名前には 1 つのコンポーネントしかありま せん。 コンポーネントのイン タフェースへの参照の 作成 Factory オブジェクトの create メソッドを呼び出して、コンポーネント のプロキシを取得します。create メソッドで CORBA オブジェクト参照 が返されたら、_Narrow 関数を使用して、それをコンポーネントのイン タフェースへの参照に変換できます。 例 次の例で使用されている NamingContext 型と NameComponent 型は、 EAServer の CosNaming パッケージからインポートされたプロキシで、 Factory 型は SessionManager パッケージからインポートされます。 CORBAObject my_corbaobj JaguarORB my_orb NamingContext my_nc NameComponent the_name[] Factory my_Factory n_jagcomp my_jagcomp my_orb = CREATE JaguarORB // URL の名前は単一引用符で囲む my_orb.init("ORBNameServiceURL='iiop://server1:2000'") my_orb.Resolve_Initial_References("NameService", & my_corbaobj) my_corbaobj._narrow(my_nc, & "omg.org/CosNaming/NamingContext") the_name[1].id = "mypackage/n_jagcomp" the_name[1].kind = "" my_corbaobj = my_nc.resolve(the_name) my_corbaobj._narrow(my_Factory, & "SessionManager/Factory") my_corbaobj = my_Factory.create("admin","") my_corbaobj._narrow(my_jagcomp, "mypackage/n_jagcomp") my_jagcomp.getdata() アプリケーション テクニック 587 クライアントとコンポーネントを区別するトランザクション クライアントとコンポーネントを区別するトランザクション クライアント アプリケーションおよび[OTS スタイル]または [Bean Managed]としてマークされた EAServer コンポーネントは、 CORBACurrent コンテキスト サービス オブジェクトの関数を使用し て、EAServer トランザクションに関する情報の作成、制御、および取 得が行えます。CORBACurrent オブジェクトは、CORBACurrent イン タフェース用に定義された数多くのメソッドを備えています。 2 フェーズ コミット クライアントまたはコンポーネントをマークしたトランザクションの コンポーネントは、OTS/XA トランザクション コーディネータを使用 するサーバ上で実行されていなければなりません。このトランザク ション コーディネータは、システム障害から保護するため、すべての 参加者からの詳細レコードを使用する、2 フェーズ コミット プロトコ ルをサポートします。準備フェーズでは、トランザクション コーディ ネータがトランザクションの各参加者から、そのトランザクションが コミットできるという保証を得て、準備レコードをログに書き込みま す。コミット フェーズでは、コーディネータはすべての参加者に対し、 リソースが解放され、トランザクションがコミットされ、コミット レ コードがログに記録されることを通知します。 2 フェーズ コミットを使用するコンポーネントは、XA 準拠の PowerBuilder データベース インタフェースを使用してデータベースに接続しなけ れはなりません。 OTS/XA トランザクション コーディネータは、接続キャッシュではな く XA リソースを使用してトランザクションを管理します。XA リソー スの作成と管理の詳細については、EAServer のマニュアルを参照して ください。 トランザクションを管 理するコンポーネント の作成 CORBACurrent オブ ジェクトの初期化 トランザクションを管理する EAServer コンポーネントを作成するに は、EAServer プロジェクト ウィザードかプロジェクト ペインタの [OTS スタイル]ボックスをオンにします。また、コンポーネント配布後、 EAServer Manager のコンポーネントのプロパティ シートの[Transaction] タブで[OTS Style]を、または Management Console の[Bean Managed] を選択することも可能です。 CORBACurrent コンテキスト サービス オブジェクトの関数を呼び出す 前に、GetContextService 関数を使用してオブジェクトのインスタンスを 作成し、次に Init 関数を使用してそのインスタンスを初期化する必要が あります。 コンポーネントが管理するトランザクションでは、Init 関数を引数なし で呼び出します。 GetContextService("CORBACurrent", myCorbCurr) 588 PowerBuilder 第 25 章 EAServer クライアントの構築 myCorbCurr.Init() クライアントを区別するトランザクションでは、Init 関数に引数を指定 して呼び出さなければなりません。引数は、すでに接続を確立した接 続オブジェクトのインスタンスか有効な EAServer ホストを識別する URL です。 移植性が高いため、接続オブジェクトを使用する方法がよく用いられ ます。 myCorbCurr.Init( myconnect ) // または myCorbCurr.Init( "iiop://localhost:2000") トランザクションの開 始と終了 クライアントかコンポーネントを区別するトランザクションを開始す るには BeginTransaction 関数を呼び出し、終了するには CommitTransaction か RollbackTransaction を呼び出します。トランザクションに関与するた めインスタンス化するコンポーネントは、トランザクションをサポー トしていなければなりません。 // インスタンス変数 : // CORBACurrent corbcurr // Connection myconnect int li_rc long ll_rc boolean lb_rc, lb_success ll_rc = myconnect.CreateInstance(mycomponent) li_rc = this.GetContextService("CORBACurrent", & corbcurr) IF li_rc <> 1 THEN // エラーを処理 RETURN END IF li_rc = corbcurr.Init( myconnect ) IF li_rc <> 0 THEN // エラーを処理 RETURN END IF lb_rc = corbcurr.BeginTransaction() // サーバ上で処理を実行 // 成功か失敗かを検査 ... IF lb_success THEN アプリケーション テクニック 589 クライアントとコンポーネントを区別するトランザクション corbcurr.CommitTransaction() ELSE corbcurr.RollbackTransaction() END IF ネストされないトランザクション 2 番目のトランザクションは、最初のトランザクションのコミットか ロールバックが完了するまでは開始できません。 コンポーネントが OTS スタイルとしてマークされている場合、EAServer はコンポーネントがインスタンス化されたときにはトランザクション を開始しません。EAServer は、コンポーネントが CORBACurrent オブ ジェクトのインスタンスで BeginTransaction 関数を呼び出してトランザ クションを開始するものとみなします。 SetComplete を呼び出さない コンポーネントがトランザクションを開始して SetComplete を呼び出 すには、その前にトランザクションのコミットかロールバックを実行 する必要があります。トランザクションは、タイムアウトするか別の トランザクションによって選択されるまでは、孤立しています。 トランザクションに関 する情報の取得 CORBACurrent には、トランザクションに関する情報を取得するため の GetStatus と GetTransactionName と い う 2 つ の 関 数 が あ り ま す。 GetStatus は、トランザクションがアクティブか、ロールバックのマー クが付いているか、準備フェーズにあるかコミット フェーズにある か、またはコミット済みかロールバック済みかを示す Integer 型の値を 返します。GetTransactionName は、現行トランザクションを識別する String 型の値を返します。これは、デバッグで使用するための関数です。 トランザクションの一 時停止と再開 呼び出しスレッドは、スレッドがトランザクション以外の処理を実行 している間はトランザクションを一時停止し、その後、そのトランザ クションを再開できます。SuspendTransaction は、ResumeTransaction 関 数に渡すことができるトランザクションへのハンドルを返します。 ResumeTransaction は、同じ実行コンテキスト内にある別のスレッドか ら呼び出せます。次の例では、トランザクションが同じスレッドに再 度関連付けられています。 590 PowerBuilder 第 25 章 EAServer クライアントの構築 long ll_rc unsignedlong ll_handle ... ll_rc = corbcurr.BeginTransaction() // トランザクション処理を実行 ll_handle = corbcurr.SuspendTransaction() // 非トランザクション処理を実行 corbcurr.ResumeTransaction(ll_handle) // さらにトランザクション処理を実行 トランザクションのタ イムアウト時間の設定 呼び出し元のスレッドで、トランザクションをロールバックするタイ ムアウト時間を指定できます。次の例では、タイムアウト時間を 3 分 (180 秒)に設定しています。 integer li_rc li_rc = this.GetContextService("CORBACurrent", & corbcurr) IF li_rc <> 1 THEN // エラーを処理して復帰 END IF li_rc = corbcurr.Init() IF li_rc <> 1 THEN // エラーを処理して復帰 END IF corbcurr.SetTimeout(180) corbcurr.BeginTransaction() サーバ メッセージ返送の要求 サーバ プッシュのシ ミュレーション クライアント アプリケーションは、PowerBuilder オブジェクト参照を EAServer に渡せません。したがって、PowerBuilder オブジェクト参照 を使用しても、サーバから PowerBuilder クライアントにメッセージを プッシュできません。しかし、クライアント上の共有オブジェクトを 使用して EAServer と通信することによって、この動作をシミュレート することは可能です。クライアント上の共有オブジェクトがサーバか らデータをプルするため、このテクニックはクライアント プルとみな すことができます。 アプリケーション テクニック 591 サーバ メッセージ返送の要求 動作 サーバ プッシュをシミュレートするには、クライアントは、 SharedObjectRegister 関数と SharedObjectGet 関数を使用して、共有オブ ジェクトを作成します。オブジェクトが作成されたら、クライアント 上のメイン スレッドは、共有オブジェクトのメソッドの非同期呼び 出しを行って、コールバック オブジェクトを渡します。このコール バック オブジェクトは、サーバ上で処理が終了したときに通知され ます。共有オブジェクトのメソッドは、処理を行う EAServer コン ポーネント メソッドの同期呼び出しを行います。共有オブジェクト はクライアント上の別のスレッドで動作しているため、サーバ上でプ ロセスを実行しながら、クライアント上のメイン スレッドはほかの 作業を続行できます。 EAServer の非同期処理 次の例では、POST を使用してクライアント上の共有オブジェクトのメ ソッドを非同期で呼び出します。POST の使用は、EAServer コンポーネ ントへの呼び出しのコンテキストではサポートされていません。EAServer での非同期処理については、EAServer のマニュアルで、ThreadManager モジュールと MessageService モジュールに関する項目を参照してくだ さい。 EAServer 6.x の Thread Manager の詳細については、Automated Configuration Guide のサイト http://infocenter.sybase.com/help/index.jsp?topic=/com.sybase.dc00548_0600/ht ml/easautoconfig/title.htm を参照してください。メッセージ サービスの 詳細については、Java Message Service User’s Guide のサイト http://infocenter.sybase.com/help/index.jsp?topic=/com.sybase.dc00486_0600/ht ml/easjms/title.htm を参照してください。 例 次の例では、共有オブジェクトを使用して、EAServer コンポーネント メソッドに対して非同期リクエストを行い、データをクライアント ア プリケーション ウィンドウに返す方法を示します。 592 PowerBuilder 第 25 章 EAServer クライアントの構築 クライアント アプリケーションのウィンドウ クライアント アプリケーションには、w_employee というウィンドウが あり、従業員データをデータウィンドウ コントロールに表示します。 ユーザがこのウィンドウの[検索]ボタンをクリックすると、クライ アントは、EAServer と通信する共有オブジェクトを作成します。さら に、ユーザ オブジェクトのインスタンスも作成します。このインスタ ンスは、共有オブジェクトのコールバックの処理に使用されます。 インスタンス変数 w_employee ウィンドウには、以下の定義されたインスタンス変数があ ります。 uo_sharedobject iuo_sharedobject uo_callback iuo_callback [検索]ボタン [検索]ボタンは、EAServer と通信する共有オブジェクトを作成しま す。さらに、ユーザ オブジェクトのインスタンスも作成します。この インスタンスは、共有オブジェクトのコールバックの処理に使用しま す。コールバック オブジェクトがウィンドウに処理の終了を通知でき るように、次のスクリプトはコールバック オブジェクト上で PassObject という関数を呼び出し、ウィンドウへの参照を渡します。最後に、こ のスクリプトは、共有オブジェクトの RetrieveData 関数の非同期呼び出 しを行って、コールバック オブジェクトへの参照を渡します。 [検索]ボタンには次のスクリプトがあります。 long ll_rv SharedObjectRegister("uo_sharedobject","myshare") SharedObjectGet("myshare",iuo_sharedobject) iuo_callback = CREATE uo_callback iuo_callback.passobject (parent) iuo_sharedobject.post retrievedata(iuo_callback) SetDW 関数 SetDW 関数は、EAServer コンポーネントから返されたデータウィンド ウ Blob の内容を、ウィンドウ内のデータウィンドウ コントロールに適 用します。SetDW 関数は、Blob 型の引数 ablb_data を受け取り、Long 値 を返します。この関数には、次のスクリプトがあります。 long ll_rv ll_rv = dw_employee.SetFullState(ablb_data) if ll_rv = -1 then MessageBox(" エラー ", "SetFullState 呼び出しに失敗しま した !") end if アプリケーション テクニック 593 サーバ メッセージ返送の要求 return ll_rv EAServer コンポーネント EAServer コンポーネントは、uo_employee という PowerBuilder ユーザ オブジェクトです。この uo_employee オブジェクトには、データスト アを使用してデータベースから従業員の行を取り出す、RetrieveData と いう関数があります。 インスタンス変数 uo_employee オブジェクトには、以下の定義されたインスタンス変数が あります。 protected TransactionServer txnsrv protected DataStore ids_datastore RetrieveData 関数 RetrieveData 関数は、Blob 型の引数 ablb_data を受け取り、Long 値を返 します。この関数には、次のスクリプトがあります。 long ll_rv ll_rv = ids_datastore.Retrieve() ll_rv = ids_datastore.GetFullState(ablb_data) txnsrv.SetComplete() return ll_rv 共有オブジェクトの定義 クライアント アプリケーションは、uo_sharedobject という共有オブ ジェクトを使用して、EAServer コンポーネントと通信します。この共 有オブジェクトには、RetrieveData という 1 つの関数があります。 インスタンス変数 uo_sharedobject オブジェクトには、以下の定義されたインスタンス変 数があります。 uo_employee iuo_employee n_jagclnt_connect myconnect Constructor イベント Constructor イベントは、n_jagclnt_connect というカスタム接続オブジェ クトを使用して、サーバに接続します。続いて、EAServer コンポーネ ントのインスタンスを作成します。 long ll_rc, ll_rv myconnect = create n_jagclnt_connect ll_rc = myconnect.ConnectToServer() ll_rv = myconnect.CreateInstance(iuo_employee, & "uo_employee") 594 PowerBuilder 第 25 章 RetrieveData 関数 EAServer クライアントの構築 RetrieveData 関数は、EAServer コンポーネントの RetrieveData 関数の同 期呼び出しを行います。関数の処理が終了すると、コールバック オブ ジェクトの Notify 関数を呼び出し、サーバ コンポーネントから返され たデータウィンドウ Blob を渡します。 RetrieveData 関数は、uo_callback 型の auo_callback という引数を受け取 ります。 blob lblb_data long ll_rv ll_rv = iuo_employee.retrievedata(lblb_data) auo_callback.notify(lblb_data) return ll_rv コールバック オブジェクトの定義 EAServer コンポーネントが処理を終了したら、共有オブジェクトが uo_callback というユーザ オブジェクトに通知し、このユーザ オブジェ クトが同様に w_employee ウィンドウに通知します。uo_callback オブ ジェクトには、Notify と PassObject という、2 つの関数があります。 Notify 関数 Notify 関数は、w_employee ウィンドウの SetDW という関数を呼び出し、 サーバ コンポーネントから返されたデータウィンドウ Blob に渡しま す。Notify 関数は、Blob 型の引数 ablb_data を受け取り、Long 値を返し ます。この関数には、次のスクリプトがあります。 long ll_rv ll_rv = iw_employee.setdw(ablb_data) if ll_rv = -1 then MessageBox(" エラー ", "SetDW 呼び出しに失敗 !") end if return ll_rv PassObject 関数 PassObject 関数は、w_employee ウィンドウへの参照を iw_employee イン スタンス変数にキャッシュします。この関数は、w_employee 型の引数 aw_employee を受け取り、Long 値を返します。 iw_employee = aw_employee return 1 アプリケーション テクニック 595 エラー処理 エラー処理 PowerBuilder は、EAServer に接続しているクライアントが使用できる 3 階層のエラー処理を提供します。 • EAServer で実行されているコンポーネントから送出された例外を、 try/catch/finally ブロックを使用して処理するメカニズム システム エラーと実行時エラーはすべて、RuntimeError 型から派 生したオブジェクトに変換されます。 • EAServer 接続のコンテキストで発生するエラーを処理する、接続 オブジェクトと JaguarORB オブジェクトの Error イベント • ほかのメカニズムでトラップされなかったエラーを処理する、ア プリケーション オブジェクトの SystemError イベント PowerBuilder では、エラーに関する情報は組み込みの Error 構造に記録 されます。この構造体は、Error イベントと SystemError イベントによっ て使用されます。 クライアントができる こと クライアント アプリケーションは、さまざまな方法で通信エラーを処 理できます。たとえば、クライアントがサーバに接続し、オブジェク トのメソッドを呼び出そうとしたのにそのオブジェクトが存在しな かった場合は、サーバとの接続を解除し、別のサーバに接続して操作 を再試行する方法があります。あるいは、クライアントがユーザにメッ セージを表示して、次に起こることを制御する機会をユーザに与える 方法もあります。 クライアントが操作の再開のために新しいサーバに接続している場 合、エラー発生時には、新しいサーバ上でリモート オブジェクトをイ ンスタンス化してから、リモート オブジェクトのメソッドを呼び出す 必要があります。 エラーが処理される場 所 596 次に、PowerBuilder が EAServer クライアントでエラー処理コードを実 行するシーケンスを示します。 1 接続オブジェクトまたは JaguarORB オブジェクトのコンテキスト でエラーが発生し、そのオブジェクトの Error イベントに関連付け られているスクリプトがある場合は、イベント スクリプトがあれ ば、それが実行されます。 2 以下のいずれかが真の場合、RuntimeError またはその子孫のアク ティブな例外ハンドラが起動されます。 • Error イベントのスクリプトが作成されていない • Error イベントのアクション引数が ExceptionFail! に設定され ている PowerBuilder 第 25 章 • 3 EAServer クライアントの構築 接続オブジェクトまたは JaguarORB オブジェクトのコンテキ ストでエラーが発生しない 例外ハンドラがない場合、または既存の例外ハンドラがその例外 を処理しない場合、アプリケーション オブジェクトの SystemError イベントが実行されます。SystemError イベントのスクリプトが作 成されていない場合は、アプリケーション エラーが起きて、アプ リケーションは終了します。 システム例外ハンドラ PowerBuilder には、致命的なシステム エラーの捕捉を試みる、システ ム例外ハンドラがあります。このハンドラは、個々のクライアント接 続のトラブルによるサーバ停止の防止に役立ちます。クライアント接 続時に致命的なエラーが発生するたびに、PowerBuilder は、サーバを 停止させたり、ほかのクライアント接続を妨げたりすることなく、ク ライアント接続の終了を試みます。トラブルが発見されたら、クライ アント上のほかの実行時エラーの場合と同様に、システム例外ハンド ラはアプリケーション オブジェクト内で SystemError イベントを発生 させます。 コンテキスト対応のエ ラー処理 try/catch メカニズムを利用すると、発生した場所でエラーを処理でき、 コンポーネントから送出されたエラーが、クライアント アプリケー ションで致命的なエラーになる可能性を最小限に抑えることも可能で す。接続オブジェクトの Error イベントをスクリプトで実行させる方法 は正確性が低く、Error イベントのアクション引数を ExceptionFail! に設 定しない限り、try/catch 例外ハンドラを無視してしまいます。 したがって、Error イベントはスクリプトで実行せずに、コードに try/catch ブロックを追加して、もっとも効果的なエラー処理を実現し なければなりません。GetMessage 関数を使用して、例外のエラー メッ セージを取得できます。 例外についての詳細は、39 ページの「PowerBuilder での例外処理」を 参照してください。 作成したエラー処理コードでは発生したすべてのエラーをトラップで きるわけではないため、必ず、アプリケーション オブジェクトの SystemError イベントのスクリプトを作成する必要があります。 アプリケーション テクニック 597 エラー処理 CORBA 例外の処理 CORBA は、コンポーネントがエラーまたは警告を通知するための標 準的な方法を提供します。CORBA は 2 種類の例外をサポートします。 • システム例外 • ユーザ定義の例外 システム例外は、サーバで生成される標準エラーのセットの 1 つです。 これらの例外は、CORBA 仕様で定義されています。 ユーザ定義例外は、コンポーネントの IDL で定義されるエラーまたは 警告です。ユーザ定義例外は新しいデータ型であり、例外が生成され たときにクライアントに返される一連のデータ要素を表します。 システム例外 PowerBuilder では、CORBA システム例外は RuntimeError オブジェクト から継承した一連のオブジェクトにマッピングされます。このような 例外のリストを参照するには、PowerBuilder オブジェクト ブラウザの [システム]タブで「corbasystemexception」を選択し、ポップアップ メ ニューで[階層の表示]を選択して、ツリービュー項目を展開します。 PowerBuilder の CORBASystemException オブジェクトの名前は、 CORBA/IIOP 仕様にアンダースコア文字を省略して定義されている CORBA システム例外の名前にマッピングされます。たとえば、 PowerBuilder CORBACommFailure 例外は CORBA_COMM_FAILURE 例 外にマッピングします。CORBA 例外についての詳細は、OMG のサイ ト http://www.omg.org/ からダウンロードできる CORBA/IIOP 仕様を参照 してください。 コンポーネントのメソッドを呼び出すときには、次に示すような例外 に対してエラー処理を実行できます。 TRY ... // メソッドの呼び出し CATCH (corbacommfailure cf) // コンポーネントによる EAServer トランザクションの異常終了 // またはトランザクションのタイムアウト。 // 必要であれば トランザクションを再試行 CATCH (corbatransactionrolledback tr) // 多くの場合はトランザクションを再試行 CATCH (corbaobjectnotexist one) // 存在しないコンポーネントを初期化しようと // したときに受け取る。また、 // オブジェクト参照の有効期限が切れた場合に // メソッドを呼び出したときも受け取る // これは、コンポーネントがステートフルで、 // 有限の Instance Timeout プロパティが 598 PowerBuilder 第 25 章 EAServer クライアントの構築 // 設定してある場合に実行 // 必要であれば新しいプロキシ インスタンスを作成 CATCH (corbanopermission np) // ユーザに、認証されていないことを通知 CATCH (corbasystemexception se) ... // エラーを通知するが再試行はしない FINALLY // クリーンアップ コードはここに挿入 END TRY ユーザ定義の例外 ユーザ定義例外は、Exception オブジェクトから継承され CORBAUserException オブジェクトにマッピングされます。 PowerBuilder クライアントは、どのコンポーネント タイプから送出さ れた例外も処理できます。 EAServer コ ン ポ ー ネ ン ト に 例 外 を 送 出 す る メ ソ ッ ド が あ る 場 合、 PowerBuilder プロキシ オブジェクトのそのメソッドも、ユーザ定義例 外を送出するように宣言されます。ユーザ定義例外に関する定義は、 開発者がコンポーネント プロキシを作成したときに作成されます。 CORBA では、例外階層構造をサポートしていません。 CORBA IDL では、例外階層構造をサポートしていません。その結果、 例外を継承したサーバ コンポーネントのプロキシを生成すると、生成 されたプロキシはすべて CORBAUserException から直接継承します。 EJB コンポーネントで Create、Remove、および FindByPrimaryKey メソッ ドをすべて使用すると、EJB の CreateException、RemoveException、お よび FinderException 例外が送出されます。これらの例外は、EAServer の CtsComponents パッケージでは同名の IDL 例外で表されています。 Error イベントのスクリプト作成 実行方法 接続オブジェクトの Error イベントのエラーを処理するには、オブジェ クトの定義をカスタマイズするユーザ オブジェクトを作成します。カ スタム接続オブジェクトを作成したら、接続オブジェクトを使用する スクリプト内のどこからでも、そのオブジェクトを参照できます。 JaguarORB イベントを使用する場合は、同じように Error イベントのス クリプトを作成できます。 接続オブジェクト ウィザードは、カスタム接続オブジェクトを作成し ます。573 ページの「ウィザードを使用した接続オブジェクトの作成」 を参照してください。 アプリケーション テクニック 599 エラー処理 Error イベントの引数 カスタム接続オブジェクトの Error イベントには引数がいくつかあり ます。これらの引数を使うと、エラーの原因となった条件についての 情報を取得できます。たとえば、エラー番号とエラー メッセージに加 えて、エラーを起こしたオブジェクトの名前や、エラーが発生したス クリプトの全テキストなども、これらの引数から取得できます。 エラー情報を提供する引数に加えて、Error イベントには次に実行すべ き動作を指定する引数があります。動作を指定するには、4 つの値 (ExceptionFail!、ExceptionRetry!、ExceptionIgnore!、 ExceptionSubstituteReturnValue!)の 1 つを Error イベントの Action 引数に 指定します。 例 次の例では、Error イベント スクリプトは、通信エラーを引き起こした 条件をユーザに伝えて、次に起こることを制御する機会をユーザに与 えます。ユーザの入力に応じて、クライアント アプリケーションは、 異常終了したり、操作を再試行したり、エラーを無視して処理を続行 したりします。 int li_choice li_choice = MessageBox(" 接続エラー " + & string(ErrorNumber), ErrorText, & Question!,AbortRetryIgnore!) CHOOSE CASE li_choice CASE 1 Action = ExceptionFail! CASE 2 Action = ExceptionRetry! CASE 3 Action = ExceptionIgnore! END CHOOSE SystemError イベントのスクリプト作成 実行方法 アプリケーション オブジェクトの SystemError イベントには、 PowerBuilder にアプリケーションの実行を中断させたり、エラーを無 視するように指示するスクリプトを記述したりできます。 例 次の例では、SystemError イベント スクリプトは、メッセージを表示し て、ユーザに通信エラーを引き起こした条件を知らせ、ユーザに次に 起こることを制御する機会を与えます。ユーザの入力に応じて、クラ イアント アプリケーションは、実行を中断するか、エラーを無視して 処理を続行します。 600 PowerBuilder 第 25 章 EAServer クライアントの構築 string ls_logline = " システム エラー : " ls_logline += String(error.number) + " " + error.text ls_logline += " エラー発生行 " + & String(error.line) + " " ls_logline += " イベント " + error.objectevent ls_logline += " オブジェクト " + error.object if Messagebox(" システム エラー ", ls_logline + & "~r~n~r~n プログラムを終了しますか ?", & Question!, YesNo!)= 1 then HALT CLOSE end if クライアント アプリケーションの配布 分散コンピューティング環境でクライアント アプリケーションを配 布する手順は、ほかの PowerBuilder アプリケーションの配布手順とほ ぼ同じです。クライアント アプリケーションのパッケージ化には 2 つ の基本的な方法があります。 • アプリケーションのオブジェクトをすべて含む、1 つのスタンドア ロン実行ファイル(EXE)として • 実行ファイルと 1 つまたは複数の動的ライブラリとして ビットマップやアイコンのような、アプリケーションが使う補助的な リソースをいくつか供給しなくてはいけないこともあります。リソー スは、実行ファイルや動的ライブラリで供給するか、別々に配布する ことも可能です。 ア プ リ ケ ー シ ョ ン の 実 行 フ ァ イ ル を 作 成 す る 方 法 に つ い て は、 PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください。 アプリケーションと一緒に配置する必要があるファイルについては、 第 41 章「アプリケーションとコンポーネントの配布」を参照してくだ さい。 アプリケーション テクニック 601 クライアント アプリケーションの配布 602 PowerBuilder 第 2 6 章 PowerBuilder クライアントでの SSL の使い方 PowerBuilder クライアントは、Secure Sockets Layer(SSL)を使用 して EAServer に接続できます。ほかのセキュリティ機能の中で も、SSL は、証明書に基づくサーバ認証、証明書に基づく任意の クライアント認証、およびネットワーク経由で送信される任意の データの暗号化を提供します。 内容 項目 EAServer とのセキュアな接続 PowerBuilder での SSL 接続 セキュアな接続の確立 SSL コールバックの使い方 セッション セキュリティ情報の取得 ページ 603 605 609 612 616 EAServer とのセキュアな接続 SSL プロトコルでは、デジタル認証に基づく公開鍵の暗号化と認 証のアルゴリズムを利用して、安全に接続できます。SSL は「ラッ パー」プロトコルであり、ほかのプロトコル用のパケットは、SSL パケットの内部に埋め込むことによって保護されます。たとえば、 HTTPS は、各 HTTP パケットを SSL パケット内に埋め込むことに よって保護される HTTP です。同様に、IIOPS は、SSL 内に埋め込 まれた IIOP です。 EAServer の組み込み SSL ドライバは、動的ネゴシエーション、 キャッシュ セッション、共有セッション、および X.509 デジタル 証明書サポートによるクライアント / サーバの認証をサポートし ます。 アプリケーション テクニック 603 EAServer とのセキュアな接続 EAServer でのセキュリティの概要および EAServer と SSL の詳細につ いては、EAServer のマニュアルを参照してください。EAServer 6.x の 詳細については、Security Administration and Programming Guide のサイト http://infocenter.sybase.com/help/index.jsp?topic=/com.sybase.dc38035_0600/ht ml/eassec/title.htm を参照してください。 保護の質 EAServer パッケージ、コンポーネント、およびメソッドの保護の質 (QOP: quality of protection)は、Management Console で設定できます。 QOP は、クライアントがコンポーネントのビジネス ロジックにアクセ スするために満たさなければならない、最低レベルの暗号化および認 証を構築します。たとえばコンポーネントに対する QOP を設定するに は、コン ポー ネント のプ ロパ ティ シート の[Advanced]ペ ージ で com.sybase.jaguar.component.qop プロパティを追加し、EAServer が提供 する sybpks_intl などのセキュリティ特性を設定します。 サーバでの QOP の設定について、および EAServer が提供するセキュ リティ特性のリストについては、EAServer のマニュアルを参照してく ださい。この章では、クライアントでの QOP の設定について説明しま す。 SSL の証明書に基づ く認証 Management Console では、リスナを設定し、そのリスナにセキュリティ プロファイルを関連付けることで、セキュアな IIOP または HTTP ポー トを構成できます。プロファイルは、目的のサーバでの接続終了を確 認するためにクライアントに送信されるセキュリティ証明書と、その ほかのセキュリティ設定を指定します。 PowerBuilder クライアントには、デジタル証明書の管理のために公開 鍵基盤(PKI: Public key Infrastructure)システムが必要です。EAServer 証明書データベースを管理する Security Manager を使用できます。 PKI およびセキュアなポートと認証オプションの設定の詳細について は、EAServer のマニュアルを参照してください。 クライアント側のイン ストール要件 604 EAServer は、いくつかのクライアント ランタイム ファイルを提供し ます。PowerBuilder クライアントの SSL サポートは、クライアント ORB を介して提供されるため、PowerBuilder SSL クライアントが動作 するコンピュータには SSL ランタイム ファイルをインストールする 必要があります。このインストールには、クライアント側のセキュリ ティ データベース、SSL サポート ライブラリ、クライアント側の Security Manager などが含まれます。また、アプリケーションの実行時 にクライアント ライブラリが読み込まれるように、クライアントのイ ンストールを構成する必要もあります。詳細については、『EAServer Installation Guide』マニュアルを参照してください。 PowerBuilder 第 26 章 PowerBuilder クライアントでの SSL の使い方 PowerBuilder での SSL 接続 PowerBuilder は、セキュアな接続に使用する 2 つのシステム オブジェ クトを提供します。 • SSLServiceProvider サービス オブジェクト SSLServiceProvider オブ ジ ェ ク ト は、EAServer の CtsSecurity::SSLServiceProvider イ ン タ フェースの実装です。このインタフェースの詳細については、Web ブラウザでお使いのサーバ(http://hostname:portnumber)に接続し て、EAServer インタフェース リポジトリ ドキュメントを参照して ください。 SSLServiceProvider オブジェクトの GetGlobalProperty および SetGlobalProperty 関数を使用して、グローバル SSL プロパティを設 定します。設定または取得、あるいはその両方が可能なグローバル プロパティについては、605 ページの「SSL プロパティ」を参照し てください。 また、接続オブジェクトまたは JaguarORB オブジェクトに対して、 SSL プロパティを Options 文字列で指定して、接続レベルで設定す る こ と も で き ま す。対 話 型 の ア プ リ ケ ー シ ョ ン で は 一 般 に、 SSLServiceProvider オブジェクトは SSLCallback オブジェクトとと もに使用されます。ユーザとの対話操作を提供しないアプリケー ションでは、接続レベルで SSL 設定を構成するのが普通です。接 続レベルでのプロパティの設定については、608 ページの「ORB プロパティ」を参照してください。 • SSLCallback オブジェクト EAServer で、コールバック メソッドを 使用してクライアントに追加情報を要求する場合は、SSLCallBack オブジェクトのインスタンスにコールバック メソッド用の独自の ロジックを実装できます。SSLCallback オブジェクトは、EAServer の CtsSecurity::SSLCallback インタフェースの実装です。 SSL プロパティ 表 26-1 に、SetGlobalProperty または GetGlobalProperty を使用して設定ま たは取得できるプロパティを示します。SSL 接続では、qop(quality of protection)プロパティを設定しなければなりません。また、このプロ パティを取得するためのコールバックを実装しない場合は、pin プロパ ティを設定する必要があります。選択したセキュリティ レベルをサ ポートするサーバ アドレスに接続する必要もあります。これについて は、608 ページの「セキュアなサーバ アドレス」に記載されています。 アプリケーション テクニック 605 PowerBuilder での SSL 接続 PowerBuilder セッションでのグローバル プロパティの設定 PowerBuilder でクライアント アプリケーションを実行している場合、 PowerBuilder のセッション時にグローバル プロパティを設定できるの は一度だけです。グローバル SSL プロパティを設定するコードをテス トするたびに、PowerBuilder を再起動する必要があります。 設定されていないプロパティか、誤って設定されているプロパティが ある場合は、SSL コールバック メソッドが呼び出されます。SSLCallback オブジェクトのインスタンスを指定していない場合は、デフォルトの コールバック実装によって接続試行が中断されます。 表 26-1: SSL プロパティのリスト プロパティ callbackImpl certificateLabel qop cacheSize SessLingerTime SessShareCount pin 説明 取得 SSLCallback オブジェクトのインスタンス。詳細については、612 可 ページの「SSL コールバックの使い方」を参照してください。 相互認証が必要な接続で使用するクライアント証明書。ラベル 可 は、PKCS #11 トークンの X.509 証明書およびプライベート キー を識別する単純な名前 相互認証で必要このプロパティを設定せずに接続の相互認証を 要求すると、コールバック メソッド getCertificateLabel が呼び出さ れ、使用可能な証明書名の配列が入力パラメータとして渡される 使用するセキュリティ特性の名前。SSL で必要。詳細については、 607 ページの「セキュリティ特性の選択」を参照してください。 SSL セッション ID のキャッシュのサイズ。デフォルトは 100 前回の接続で使用したセッション ID エントリをキャッシュに保 管する期間(秒単位)。デフォルトは 28800 秒(8 時間) 同じセッション ID を同時に使用できる SSL セッションの数。デ フォルトは 10 PKCS #11 トークンの PIN 設定 可 可 可 可 可 可 可 可 可 可 不可 可 これは、クライアント認証のために PKCS #11 トークンにログイ ンする場合、および信頼情報を取得する場合に必要。SSL で必要 availableQop availableQopDesc availableVersions 606 このプロパティが設定されていない場合は、any が設定される。 また、誤って設定されている場合は、コールバック メソッド getPin が呼び出される 使用可能なセキュリティ特性のリスト。qop プロパティには、こ 可 のリスト内の値のみ設定できる 使用可能なセキュリティ特性の説明のリスト。availableQop プロ 可 パティの値と同じ順序で指定する SSL ランタイム エンジンでサポートされる SSL プロトコル バー 可 ジョンのリスト 不可 不可 不可 PowerBuilder 第 26 章 プロパティ entrustReady entrustIniFile entrustUserProfile useEntrustID entrustPassword PowerBuilder クライアントでの SSL の使い方 説明 取得 クライアントで Entrust PKI ソフトウェアが使用できる場合は 可 TRUE、それ以外の場合は FALSE Entrust へのアクセス方法に関する情報を定義した Entrust INI 可 ファイルへのパス名。useEntrustid プロパティが true に設定されて いる場合に必要 このプロパティが設定されていない場合は、コールバック メソッ ド getCredentialAttribute が呼び出される Entrust ユーザ プロファイルを含むファイルへのフル パス。Entrust 可 のシングルログイン機能が使用可能な場合は省略できる。それ以 外の場合は必ず指定する このプロパティが設定されていない場合は、コールバック メソッ ド getCredentialAttribute が呼び出される 認証に、Entrust ID または Sybase の PKCS #11 トークンのどちら を使用するかを指定する。これは Boolean 型のプロパティである 可 このプロパティが FALSE に設定されている場合、Sybase の PKCS #11 トークンのプロパティが有効になり、Entrust 固有のプロパ ティは無視される。このプロパティが TRUE に設定されている場 合、Entrust 固有のプロパティが有効になり、Sybase の PKCS #11 トークンのプロパティは無視される 指定されたユーザ プロファイルを使用して Entrust にログインす 不可 る際のパスワード。Entrust のシングルログイン機能が使用可能な 場合は省略できる。それ以外の場合は必ず指定する 設定 不可 可 可 可 可 パスワードが必要な場合に、このプロパティが設定されていない ときや、誤って設定されているときは、コールバック メソッド getPin が呼び出される セキュリティ特性の選 択 SSL を使用するには、使用可能なセキュリティ特性の名前を qop プロ パティに指定しなければなりません。この特性は、SSL 接続のネゴシ エーションの際にクライアントが使用する CipherSuite を定義します。 接続時に、クライアントは自分が使用する CipherSuite のリストをサー バに送信します。サーバは、そのリストから CipherSuite を選択します。 サーバは、そのリスト内から、使用可能な最初の CipherSuite を選択し ます。サーバで使用できる CipherSuite がない場合、接続は失敗します。 EAServer のマニュアルでは、EAServer から提供されるセキュリティ特 性について説明しています。サーバで使用可能な特性のリストおよびそ の説明を取得するには、GetGlobalProperty を使用して availableQop およ び availableQopDesc プロパティを取得します。 アプリケーション テクニック 607 PowerBuilder での SSL 接続 セキュアなサーバ ア ドレス qop 設定で要求されるセキュリティ レベルと同じまたはそれ以上のレ ベルのサーバ リスナにのみ接続できます。JaguarORB.string_to_ オブ ジェクトを使用して SessionManager::Manager インタフェースのプロシ キのインスタンスを作成する場合、サーバ アドレスで指定されるリス ナでは、クライアントの qop 設定と一致するセキュリティ プロファイ ルを使用しなければなりません。 ORB プロパティ 接続オブジェクトまたは JaguarORB オブジェクトのいずれかを使用し て EAServer に接続する場合、EAServer のクライアント ORB を使用し ます。そのプロパティは、接続オブジェクトの Options 文字列に設定 するか、JaguarORB の Init 関数を使用して設定できます。以下のプロパ ティは、特にセキュアな接続に対して適用される ORB プロパティで す。 • ORBqop • ORBcertificateLabel • ORBpin • ORBuseEntrustID • ORBentrustPassword • ORBentrustIniFile • ORBentrustUserProfile 以上のプロパティの機能は、対応する SSL プロパティと同じですが、 その値は確立中の接続にのみ影響し、セッション全体には影響しませ ん。ORBqop に sybpks_none を設定すると、どの SSL も接続で使用さ れなくなります。この設定が便利なのは、SSLServiceProvider オブジェ クトを使用してすべての ORB に対して QOP をグローバルに設定して いる場合に、単一の接続の QOP をオーバーライドするときです。 ORB プロパティのリストについては、接続オブジェクトのヘルプを参 照してください。 次の例では、ORBqop プロパティに sybpks_simple を設定し、ログ ファ イルを指定します。 myconnect.options = "ORBqop='sybpks_simple', " & + "ORBLogFile='C:\tmp\log.txt'" 608 PowerBuilder 第 26 章 PowerBuilder クライアントでの SSL の使い方 セキュアな接続の確立 EAServer へのセキュアな接続を確立するには、次の手順を行います。 1 SSLServiceProvider オブジェクトのインスタンスを作成します。 2 (省略可能)GetGlobalProperty 関数を使用して、サーバからセキュ リティ情報を取得します。 3 SetGlobalProperty 関数を使用して、サーバに必要なプロパティを設 定します。 4 SSLServiceProvider オブジェクトのインス タンスの作成 接続オブジェクトの ConnectToServer 関数を使用して、サーバに接 続します。 次のコードは、SSLServiceProvider オブジェクトのインスタンスを作成 します。 SSLServiceProvider sp GetContextService( "SSLServiceProvider", sp ) サーバからの情報の取 得 GetGlobalProperty を使用して、サーバのセキュリティ特性に関する情報 を取得します。次の例では、サポートされている CipherSuite の情報を availableQop プロパティから取得し、その情報をドロップダウン リス トボックスに表示します。 int i, rc string ls_values[] rc = sp.GetGlobalProperty("availableQop", ls_values) IF rc <> 0 THEN MessageBox("Qop の取得に失敗しました ", & "rc = " + string(rc)) RETURN END IF FOR i = 1 to UpperBound(ls_values) ddlb_1.AddItem( ls_values[i] ) NEXT RETURN グローバル プロパ ティの設定 サーバに接続するには、まず必要なグローバル プロパティを設定しな ければなりません。次のコードでは、qop に値 sybpks_intl を設定し、 pin に値 sybase を設定します。 int rc rc = sp.SetGlobalProperty( "qop", "sybpks_intl" ) アプリケーション テクニック 609 セキュアな接続の確立 IF rc <> 0 THEN MessageBox( "QOP の設定に失敗しました ", & "rc = " + string(rc) ) ELSE MessageBox( "SSL の QOP プロパティの設定 ", & " 成功しました " ) END IF rc = sp.SetGlobalProperty( "pin", "sybase" ) IF rc <> 0 THEN MessageBox( "PIN の設定に失敗しました ", & "rc = " + string(rc) ) ELSE MessageBox( "SSL の PIN プロパティの設定 ", & " 成功しました " ) END IF SetGlobalProperty を使用して設定するプロパティのほとんどは、クライ アントの実行中に一度だけ設定できます。これらのプロパティは、ク ライアントがサーバとの接続を解除した場合またはサーバに再接続し た場合も有効です。 PowerBuilder の再起動 PowerBuilder でクライアント アプリケーションを実行している場合、 PowerBuilder のセッション時にグローバル プロパティを設定できるの は一度だけです。グローバル SSL プロパティを設定するコードをテス トするたびに、PowerBuilder を再起動する必要があります。 SSLCallback オブジェクトのインスタンスを使用して、ユーザ入力を対 話形式で取得する場合は、グローバル プロパティ CallBackImpl を設定 する必要があります。612 ページの「SSL コールバックの使い方」を 参照してください。 サーバへの接続 610 セキュアなセッションを開始すると、クライアントおよびサーバは SSL ハンドシェイク プロセスでメッセージを交換します。クライアン トは、サーバとの通信で必要とされる情報を提供し、サーバはクライ アントに対してサーバ自身の認証を行ったうえで、プロセスを継続し ます。サーバがクライアント認証を必要とする場合は、プロセスを継 続する前にクライアントが認証されなければなりません。必要な認証 が完了すると、クライアントおよびサーバは、暗号化、復号化、およ び SSL セッションの不正箇所の検出に使用する、双方で対称的なキー を作成します。このプロセスで発生する例外を取り込むには、try-catch ブロックに ConnectToServer 呼び出しを置く必要があります。 PowerBuilder 第 26 章 PowerBuilder クライアントでの SSL の使い方 セキュアな接続が確立したら、接続オブジェクトの location プロパティ で iiop ではなく iiops を使用します。サーバは一般的には、ポート 2001 または 2002 でセキュアな接続要求を待機します。次の例では、グ ローバル変数として宣言された接続オブジェクト g_connect を使用し ます。ここでは、接続オブジェクトの options プロパティを使用して、 この接続に別の CypherSuite を指定します。 long l_rc g_connect.userid = sle_user.text g_connect.password = sle_password.text g_connect.driver = "jaguar" g_connect.application = "myserverpkg" g_connect.location = "iiops://myserver:2001" g_connect.options = "ORBqop='sybpks_simple'" TRY l_rc = g_connect.ConnectToServer() CATCH (userabortedexception uae) MessageBox("UserAbortedException を取得しました ", & "ConnectToServer が次を取得しました :" & + uae.getMessage() ) l_rc = 999 CATCH ( CORBASystemException cse ) MessageBox("CORBASystemException を取得しました ", & "ConnectToServer が次を取得しました :"& + cse.getMessage() ) l_rc = 998 END TRY IF l_rc <> 0 THEN MessageBox(" エラー ", " 接続に失敗しました - コード : " & + string(l_rc) ) MessageBox(" エラー情報 ", " エラーコード = " & + string(g_connect.ErrCode) + "~nErrText= " & + g_connect.ErrText) ELSE MessageBox("OK", " 接続が確立されました ") END IF 接続のトラブルシュー ティング セキュアな接続が失敗した場合は、セキュアでない接続の場合と同じ エラー メッセージが表示されます。そのエラー メッセージには、失敗 の原因に関する情報は示されません。ログ ファイルに記録された詳細 情報を取得するには、ORBLogIIOP オプションを有効にし、ORBLogFile オプションに値を指定します。上の例であれば、g_connect.options 文を次のような文で置き換えます。 アプリケーション テクニック 611 SSL コールバックの使い方 g_connect.options = "ORBqop='sybpks_simple'" + & "ORBLogIIOP='TRUE', ORBLogFile='d:\temp\ORBLog.txt'" また、環境変数 JAG_LOGFILE を設定して、初期化に関するエラーを 記録するログ ファイルを指定することもできます。 SSL コールバックの使い方 SSLCallback オブジェクトは、サーバからクライアント アプリケーショ ンに送られる追加認証情報に対する SSL リクエストを処理します。pin など必要な設定が指定されていない場合や、無効な値が指定されてい る場合は、C++ ORB によってコールバック メソッドが呼び出されま す。 コールバックは、有効期限が切れたサーバ証明書など、例外的な状況 に対応します。相互認証を使用する場合、コールバック メソッド getCertificateLabel を使うと、使用可能な証明書のリストをユーザに提示 できます。また、コールバックを使用すると、ユーザが無効な証明書 や無効なパスワードを登録した際の再試行ロジックの処理を簡素化で きます。 SSL コールバック メカニズムを使用するには、次の手順を行う必要が あります。 1 EAServer の CTS Security モジュールに対してプロキシ オブジェク トを作成して、SSL セッション情報を取得します。 2 SSLCallback オブジェクトから継承した、標準カスタム クラス ユー ザ オブジェクトを作成し、必要なコールバック関数を実装します。 3 SSL のグローバル プロパティ CallBackImpl に SSLCallback オブ ジェクトの名前を設定し、サーバに接続します。 セッション情報の取得 どの SSL コールバック関数からでも、SSL セッション情報にアクセス できます。この情報を使用することで、クライアント アプリケーショ ンのユーザに対して、必要な認証情報を提供するために必要となる情 報を渡さなければなりません。 SSL セッション情報をコールバック関数で使用するためには、 CTSSecurity モジュールに対して EAServer プロキシを作成します。 612 PowerBuilder 第 26 章 ❖ PowerBuilder クライアントでの SSL の使い方 CTSSecurity モジュールに対してプロキシを作成するには 1 新規作成 ダイアログボックスの[プロジェクト]ページで[EAServer プロキシ ウィザード]を選択し、[ターゲット]ドロップダウン リストボックスから対象のクライアント アプリケーションを選択 します。 2 いずれかの EAServer ホストに接続し、CTSSecurity モジュールを選 択します。 CTSSecurity モジュールは、すべてのサーバで使用可能な標準モ ジュールです。 ウィザードでの操作を完了し、プロジェクトを作成します。 3 システム ツリーに表示されるプロキシ オブジェクトのうち、 Sessioninfo オブジェクトはすべての SSLCallback 関数に渡されま す。 SSLCallback オブジェクトの実装 4 つのコールバック関数があります。 表 26-2: SSL コールバック関数 関数 呼び出しのタイミング GetCertificateLabel サーバがクライアント認証を要求しているが、クラ イアント アプリケーションにクライアント認証用の 証明書ラベルが設定されていない場合 クライアント アプリケーションにアカウント情報属 性が設定されていない場合 GetCredentialAttribute GetPin アプリケーション テクニック この属性は、クライアント アプリケーションで SSLServiceProvider オブジェクトを使用して UseEntrustId プロパティを設定した場合に使用され る。Entrust ID を使用している場合のみ GetCredentialAttribute が便利。Entrust および PKCS 11 トークンの詳細については、EAServer のマニュアル を参照してください。 PKCS11 トークンがログインされず、PIN が SSLServiceProvider オブジェクトのプロパティとし て設定されていない場合。また、ログイン セッショ ンがタイムアウトした場合にも呼び出される 613 SSL コールバックの使い方 関数 呼び出しのタイミング TrustVerify サーバ内部での SSL 信頼確認チェックが失敗して、 サーバの証明書チェーンを確認できない場合、また は Sybase の PKCS11 トークンにログインするための pin が設定されていないか正しくない場合、 TrustVerify は SSL プロトコルを使用する場合も呼び 出すことができる サーバ認証は SSL ハンドシェイク プロセスで必要 な手順のため、任意の SSL プロトコルを使用してい るときに TrustVerify を呼び出すことができる。ユーザ は、内部チェックをオーバーライドして SSL 接続を 続行するかどうかを選択できる 以上の各関数は、SSLCallback クラスによって実装されており、デフォ ルトの実装があります。コールバックを使用する場合は、その関数を 実装する必要があります。各関数の実装例については、 『PowerScript リ ファレンス』マニュアルまたはオンライン ヘルプを参照してくださ い。 ❖ SSLCallBack クラスを実装するには 1 デフォルトの実装 新規作成 ダイアログボックスの[PB オブジェクト]ページから [標準クラス]を選択します。 2 標準クラス データ型の選択 ダイアログボックスで[SSLCallback] を選択し、[OK]をクリックします。 3 セッション情報をユーザに提供し、ユーザから必要な認証情報を 返させるための、コールバック関数のコードを記述します。 4 実装するそのほかのコールバック関数に対して、手順 3 を繰り返 します。 実装を提供していない場合、または実装から空の文字列が返された場 合は、コールバックのデフォルトの実装が使用されます。 GetCertificateLabel および GetCredentialAttribute の場合、引数リストには、 コールバックに対して有効な戻り値である文字列値の配列が含まれま す。これらのコールバックのデフォルトの実装は、この配列が空の場 合、例外を送出し、配列が空でない場合は、その配列の最初の要素を 返します。その結果、配列の最初の要素がサーバで受け入れ可能であ れば、接続プロセスは継続しますが、受け入れ可能でなければ失敗し ます。 TrustVerify の場合、デフォルトの実装は現行の接続を拒否します。 614 PowerBuilder 第 26 章 例外の処理 PowerBuilder クライアントでの SSL の使い方 GetPin、GetCertificateLabel、および GetCredentialAttribute の実装では、要 求された情報をユーザが提供できない場合には、ユーザ側で接続を キャンセルできるようにする必要があります。これを実現するには、 関数の実装内で例外を送出し、ConnectToServer 呼び出しを置く try-catch ブロック内でその例外を取り込みます。コールバック関数内で送出し た例外によって、CTSSecurity::UserAbortedException 例外が発生します。 関数によって送出できる例外は、その関数のプロトタイプの Throws 句 に追加する必要があります。 SSLCallback オブジェクトの指定 サーバに接続するには、まず、SSLCallback オブジェクトの名前を SSLServiceProvider の CallbackImpl プロパティに指定します。 SSLServiceProvider sp int rc getcontextservice("SSLServiceProvider", sp) rc = sp.setglobalproperty( "CallbackImpl", & "uo_sslcallback" ) IF rc <> 0 THEN MessageBox("CallbackImpl の設定に失敗しました ", "rc= " + string(rc)) RETURN END IF MessageBox( "CallbackImpl プロパティの設定 ", & " 成功しました " ) RETURN & クライアント アプリケーションの実行バージョンでコールバック オ ブジェクトを参照できるようにするために、アプリケーション内でそ のコールバック オブジェクト型の変数を宣言しておく必要がありま す。次に例を示します。 uo_sslcallback iuo_sslcb このような宣言を行う理由は、コールバック オブジェクトはその文字 列名によってのみ参照されるため、技術的には非参照オブジェクトで あり、実行ファイルには含まれないためです。宣言した変数をコード で使用する必要はありません。 アプリケーション テクニック 615 セッション セキュリティ情報の取得 セッション セキュリティ情報の取得 CtsSecurity.SSLSession および CtsSecurity.SSLSessionInfo クラスを使用す ると、クライアント アプリケーションでは、プロキシからサーバへの 接続で SSL が使用されるかどうかを判断でき、SSL が使用される場合 には、SSL セッション設定を取得してユーザに対して表示できます。 値を取得できるプロパティの一覧については、Web ブラウザでお使い のサーバ(http://hostname:portnumber/ir/CtsSecurity__SSLSessionInfo.html)に 接続して、SessionInfo に関する EAServer インタフェース リポジトリの マニュアルを参照してください。 long rc string stmp CTSSecurity_sslSessionInfo mySessionInfo rc = thesessioninfo._narrow( mySessionInfo, & "SessionInfo" ) MessageBox( str_header, "Narrow:rc=" + string(rc)) sTmp sTmp stmp sTmp stmp = += += += += "Properties" "~nVersion: " mySessionInfo.getProperty( "Version" ) "~nHost: " mySessionInfo.getProperty( "host" ) stmp += "~nport: " stmp += mySessionInfo.getProperty( stmp += "~nciphersuite: " stmp += mySessionInfo.getProperty( stmp += "~nCertificateLabel: " stmp += mySessionInfo.getProperty( ) stmp += "~nUserData: " stmp += mySessionInfo.getProperty( stmp += "~ntokenName: " stmp += mySessionInfo.getProperty( stmp += "~nuseEntrustID: " stmp += mySessionInfo.getProperty( MessageBox( str_header, stmp) 616 "port" ) "ciphersuite" ) "certificateLabel" "UserData" ) "tokenName" ) "useEntrustID" ) PowerBuilder 第 2 7 章 COM/COM+ コンポーネントの構築 この章について この章では、PowerBuilder を使用して、COM/COM+ コンポーネン トを構築する方法について説明します。 内容 項目 ページ 617 COM/COM+ コンポーネントの構築について 620 コンポーネント オブジェクト モデルについて 624 コンポーネント インタフェースの定義 628 COM コンポーネントからデータベースへのアクセス 632 トランザクションのサポート 635 別のサーバ コンポーネントのメソッドの呼び出し 636 セキュリティ問題 プロジェクト ペインタでの COM/COM+ コンポーネントの構 637 築 641 PowerBuilder COM オブジェクトの実行 642 PowerBuilder COM サーバの配布 643 クライアントから PowerBuilder COM サーバへのアクセス COM/COM+ コンポーネントの構築について ビジネス ロジックを含むカスタム クラス ユーザ オブジェクトを PowerBuilder で開発すると、そのオブジェクトを COM サーバまた は COM+ アプリケーションとしてパッケージ化することができま す。 Windows 2000 や Windows XP などの COM+ をサポートしているプ ラットフォームでは、COM+ アプリケーションを構築して COM+ に配布できます。 この章以降では、COM と COM+ をサポートしているコンポーネ ントのことを、COM コンポーネントと呼んでいます。 アプリケーション テクニック 617 COM/COM+ コンポーネントの構築について PowerBuilder COM アプリケーションには、 1 つまたは複数の PowerBuilder カスタム クラス ユーザ オブジェクトを組み込むことができます。ユー ザ オブジェクトをユーザ オブジェクト ペインタでコード化してから、 プロジェクト ペインタでサーバを構築します。アプリケーションを ローカルの COM+ サーバに直接配布したり、プロジェクト ペインタで COM+ Microsoft インストーラ パッケージを作成したりすることもで きます。 PowerBuilder COM アプリケーションを生成して配布すると、ユーザ は、PowerBuilder、Visual Basic、C++ コンパイラなどのツールで構築さ れた COM 対応クライアント アプリケーションから、PowerBuilder COM アプリケーションに格納された PowerBuilder オブジェクトのメ ソッドを呼び出すことができます。 ウィザードの使い方について PowerBuilder は、COM コンポーネントの開発と配布を簡単にする以下 のウィザードを用意しています。 • ターゲット ウィザード 新規のアプリケーション、新規のカスタム クラス ユーザ オブジェクト、および新規のプロジェクトを作成し ます。 • 既存のアプリケーションに新規のカスタ ム クラス ユーザ オブジェクトを作成し、新規のプロジェクトを作 成します。 • プロジェクト ウィザード 1 つまたは複数の既存のカスタム クラス ユーザ オブジェクトから、COM サーバの構築に使用するプロジェ クトを作成し、オプションで COM+ パッケージも作成します。 オブジェクト ウィザード COM/COM+ のターゲット ウィザードまたはオブジェクト ウィザード を使用して、新規のユーザ オブジェクトを作成した場合、以下のとお りとなります。 618 • オブジェクトには、Activate と Deactivate という、2 つの新しいイ ベントがあります。 • オブジェクトは、COM の検証のサポートを有効にしています。 • ウィザードの最終ページのボックスをオンにした場合には、ウィ ザードは To-Do リストに項目を追加することによって、開発のす べてのステップを実行するよう注意を促します。 PowerBuilder 第 27 章 ウィザードを使用する タイミング COM/COM+ コンポーネントの構築 単一の新規カスタム クラス ユーザ オブジェクトを 含むサーバを構築する場合には、ターゲット ウィザードまたはオブ ジェクト ウィザードを使用して、その機能を利用します。 新規オブジェクト 複数の新規カスタム クラス ユーザ オブジェクトを含むサーバを構築 する場合にターゲット ウィザードまたは オブジェクト ウィザードを 使用すると、オブジェクトごとに異なるプロジェクトが作成されます。 したがって、いずれか 1 つのプロジェクトにすべてのオブジェクトを 追加し、それ以外のプロジェクトは破棄する必要があります。 また、ターゲット ウィザードもオブジェクト ウィザードも使用せずに 新規カスタム クラス ユーザ オブジェクトを作成し、その後でプロジェ クト ウィザードまたはプロジェクト ペインタを使用してプロジェク トを作成することもできます。 ユ ー ザ オ ブ ジ ェ ク ト ペ イ ン タ で は、COM の 検 証 を 有 効 に し て、 Activate イベントと Deactivate イベントをユーザ定義イベントとして 追加することができます。詳細については、627 ページの「COM の検 証」を参照してください。 COM サーバとして配布する 1 つまたは複数のカス タム クラス ユーザ オブジェクトがある場合は、それらのオブジェク トが、624 ページの「コンポーネント インタフェースの定義」および それ以降の節で説明する要件を満たしていることを確認してくださ い。新規のユーザ オブジェクトに関しては、ユーザ オブジェクト ペ インタで COM の検証を有効にし、Activate イベントと Deactivate イベ ントをユーザ定義イベントとして追加します。サーバの構築準備がで きたら、プロジェクト ウィザードを使用してプロジェクトを設定しま す。 既存オブジェクト 開発プロセスについて 1 つまたは複数のカスタム クラス ユーザ オブジェクトから PowerBuilder COM サーバを構築および配布するには、以下の手順を実行する必要が あります。 1 新規カスタム クラス ユーザ オブジェクトを作成するか、または既 存のユーザ オブジェクトを開きます。 ターゲット ウィザードまたはオブジェクト ウィザードを使用す る場合には、新規オブジェクトの作成と配布に使用するプロジェ クト オブジェクトも作成します。 2 アプリケーション テクニック ユーザ オブジェクト ペインタでユーザ オブジェクトのスクリプ トを記述します。 619 コンポーネント オブジェクト モデルについて 624 ページの「コンポーネント インタフェースの定義」を参照し てください。 3 場合によっては、同じアプリケーションで追加のユーザ オブジェ クトの作成とスクリプトの記述を行います。 4 ウィザードを使わずにユーザ オブジェクトを作成した場合は、 COM/COM+ プロジェクト ウィザードまたはプロジェクト ペイン タを使用してプロジェクトを作成します。 637 ページの「プロジェクト ペインタでの COM/COM+ コンポー ネントの構築」を参照してください。 5 プロジェクトを開いて、必要であれば、選択されたオブジェクト とそのプロパティのリストを修正し、プロジェクトを作成します。 6 サーバを配布します。 642 ページの「PowerBuilder COM サーバの配布」を参照してくだ さい。 コンポーネント オブジェクト モデルについて Microsoft コンポーネント オブジェクト モデル(COM)は、ソフトウェ ア コンポーネントが互いにサービスを提供するための標準的な方法 を定義します。実行環境、レジストリ エントリ、およびタイプ ライブ ラリ(オプション)を提供すれば、どの PowerBuilder カスタム クラス ユーザ オブジェクトでも、COM オブジェクトとして使用できます。 PowerBuilder や Visual Basic などの COM 準拠ツールで作成したクライ アントは、COM オブジェクトのビジネス ロジックを使用できます。そ れには、COM オブジェクトのインスタンスを作成し、そのインタ フェースによって公開されているメソッドを呼び出します。サポート するインタフェースによって、COM オブジェクトは、Java と C++ の クライアントからも使用できます。 COM+ は、より多くのリソース管理タスクに対処し、スレッド プーリ ング、オブジェクト プーリング、ジャストインタイムのオブジェクト のアクティブ化を実現することで、COM を拡張したものです。 620 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 PowerBuilder COM サーバについて PowerBuilder は、単一の PowerBuilder COM サーバを作成します。この COM サーバには、プロジェクト作成時に選択したすべてのカスタム ク ラス ユーザ オブジェクトに対応する PowerBuilder COM オブジェクト が含まれています。 COM は、オブジェクトを作成と破棄する方法、インタフェースを公開す る方法、メソッドの呼び出し方法を指定します。PowerBuilder COM サー バは COM 仕様に従います。つまり、PowerBuilder COM オブジェクト が、PowerBuilder 仮想マシンを介してカスタム クラス ユーザ オブジェ クトとやり取りしていることを、クライアントが意識することはあり ません。 オートメーション サーバと PowerBuilder COM サーバの比較 PowerBuilder では、PowerBuilder COM サーバとオートメーション サー バという 2 つの方法で COM オブジェクトを生成できます。いずれも ウィザードとプロジェクト ペインタからアクセスできます。 PowerBuilder COM サーバは、オートメーション サーバより多くの機能を提供しま す。 PowerBuilder COM サーバには、複数のカス タム クラス ユーザ オブジェクトを含めることができます。ユーザ オ ブジェクトをコーディングした後で、プロジェクト ペインタを使用し て、すべてのオブジェクト用の 1 つの自己登録型 DLL を生成します。 構築コンピュータ上で実行する場合には、作成した COM サーバは、 COM+ に直接配布できます。また、COM+ パッケージを作成すること もできます。COM サーバ内の PowerBuilder COM オブジェクトは、実 行時セッションを共有できます。また、同じ COM クライアントから 作成されたオブジェクト間で参照を受け渡すこともできます。 PowerBuilder COM サーバ COM サーバには、埋め込み PowerBuilder 動的ライブラリ(PBD)ファ イルも含まれています。PBD ファイルは、選択したすべてのカスタム クラス ユーザ オブジェクトとそれに依存するコンパイル済みオブ ジェクトに加えて、レジストリとタイプ ライブラリの情報も含みま す。 アプリケーション テクニック 621 コンポーネント オブジェクト モデルについて PowerBuilder カ ス タ ム ク ラ ス ユ ー ザ オ ブ ジェクトから作成されたオートメーション サーバには、1 つのオブ ジェクトだけが含まれています。ユーザ オブジェクトを記述した後、 そのオブジェクトを含む PBL からランタイム ライブラリを作成し、続 いてプロジェクト ペインタを使用して、レジストリ ファイルとオプ ションのタイプ ライブラリ ファイルを作成します。オートメーション サーバを配布するとき、ユーザのコンピュータに合わせてレジストリ ファイルをカスタマイズし、そのレジストリ ファイルを実行してオー トメーション サーバを登録します。 オートメーション サーバ PowerBuilder オートメーション サーバまたは PowerBuilder COM サー バに加えて、サーバが必要とするほかの PowerBuilder ランタイム ファ イルもあわせて、仮想マシンを配布します。 ディスパッチ、デュア ル、カスタムの各イン タフェース オートメーション サーバは、ディスパッチ インタフェース(dispinterface ともいう)を使用します。これによって、ユーザは、IDispatch という 標準 COM インタフェースの Invoke メソッドを使用して、サーバ上の メソッドを呼び出すことができます。 COM サーバでは、ディスパッチベースのインタフェースよりも高いパ フォーマンスを提供する、カスタム インタフェースまたはデュアル イ ンタフェースを使用できます。カスタム インタフェースは、サーバの インタフェース内のメソッドへのポインタが格納された仮想テーブル (VTBL または vtable ともいう)を介して、サーバ上のメソッドへのア クセスを提供します。デュアル インタフェースを使用すれば、クライ アントは、IDispatch::Invoke または仮想テーブルのどちらを使用しても、 メソッドを呼び出すことができます。 詳細については、640 ページの「カスタム インタフェースとデュアル インタフェースの選択」を参照してください。 サーバ間の相違のまと め 622 表 27-1 に、PowerBuilder オートメーション サーバと、デュアル インタ フェースまたはカスタム インタフェースを使用する PowerBuilder COM サーバとの相違をまとめます。 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 表 27-1: オートメーション サーバと COM サーバの比較 機能 インプロセス サーバのサポート IDL ファイルの生成 C++ クライアントのサポート Java クライアントのサポート PowerBuilder クライアントのサ ポート Visual Basic 4 クライアントのサ ポート Visual Basic 5 カスタム インタ フェースのサポート インスタンス変数およびメソッ ド引数タイプとしての PowerBuilder 構造体のサポート すべての C 言語データ型のサ ポート 埋め込みタイプ ライブラリのサ ポート 自己登録サーバ DCOM のサポート # EAServer のサポート COM+ のサポート 別個のプロキシ / スタブ DLL が 必要 PowerBuilder ランタイム DLL が 必要(最低限 PBVM110.DLL と その依存ライブラリ) ライブラリ ペインタで作成した アプリケーション ランタイム ラ イブラリの配布が必要 オートメー ション サー COM サーバ バ(ディス (デュアル パッチ イン インタ タフェース) フェース) Yes* Yes No Yes No Yes Yes Yes Yes Yes COM サーバ (カスタム インタ フェース) Yes Yes Yes No No Yes Yes No No No Yes No No No No No No No Yes Yes No Yes Yes No No Yes Yes Yes Yes No Yes Yes No Yes No Yes Yes Yes Yes No No * PowerBuilder 実行 DLL(PBVM110.dll)は、インプロセス サーバです。 # PowerBuilder 実行 DLL を収容するために、代理ホストを使用する必要があります。 アプリケーション テクニック 623 コンポーネント インタフェースの定義 コンポーネント インタフェースの定義 PowerBuilder カスタム クラス ユーザ オブジェクトを COM コンポーネ ントとして構築した場合には、そのオブジェクトに定義された関数と インスタンス変数(オプション)がコンポーネント インタフェースに 表示されます。PowerBuilder が生成する IDL ファイルでは、サーバ内 に含まれるカスタム クラス ユーザ オブジェクトごとの COM クラス と 1 つのインタフェースに加えて、PowerBuilder COM サーバのタイプ ライブラリ名と関連する ID も定義します。 メソッドとデータ型 関数 各 PowerBuilder COM オブジェクトは単一のインタフェースをサポー トしており、これによって、カスタム クラス ユーザ オブジェクト内 のユーザ定義パブリック関数ごとにメソッドを公開します。 関数の戻り値は、追加の retval 引数によって表されます。たとえば、オ ブジェクトに以下のユーザ オブジェクト関数が存在するとします。 f_addtwo (long al_num1, long al_num2) returns long f_getinfo (REF string as_name, REF integer ai_age, REF character ac_gender) returns integer IDL ファイル内に以下のメンバー関数が生成されます。 HRESULT f_addtwo( [in] long al_num1, [in] long al_num2, [out, retval] long * retval ); HRESULT f_getinfo( [in, out] BSTR * as_name, [in, out] short * ai_age, [in, out] unsigned char * ac_gender, [out, retval] short * retval ); インスタンス変数 COM オブジェクトは自分のデータを公開しないため、カスタム クラ ス ユーザ オブジェクト内のパブリック インスタンス変数は、COM オ ブジェクトにおいて変数値を取得および設定するためのインタフェー ス メソッドとして表現します。変数のアクセサ メソッドをインタ フェースとして公開するための指定は、プロジェクト ウィザードまた はプロジェクト ペインタの[オブジェクト]プロパティ ページで行い ます。 パブリック変数が書き込み可能である場合には、Put メソッドが公開され ます。プライベート変数とプロテクト変数、privateread または protectedread として宣言された変数、および privatewrite または protectedwrite として 宣言された変数の場合には、メソッドは生成されません。変数がパブ リックに読み込み可能である場合には、Get メソッドが公開されます。 たとえば、オブジェクトに以下のインスタンス変数があるとします。 624 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 public string is_name private integer ii_a public privatewrite string is_label constant real lr_pi = 3.14159265 IDL ファイル内に以下のメソッドが作成されます。 [id(4), propget] HRESULT BSTR *is_name); [id(4), propput] HRESULT BSTR is_name); [id(1), propget] HRESULT BSTR *is_label); [id(6), propget] HRESULT float * lr_pi); データ型マッピング is_name([out,retval] is_name([in] is_label([out,retval] lr_pi( [out,retval] 表 27-2 で示すように PowerBuilder のデータ型は COM のデータ型に マップします。 表 27-2: PowerBuilder と COM のデータ型のマッピング PowerBuilder データ型 COM のデータ型(バリアント) Boolean Variant_BOOL Character Unsigned char Integer Short UnsignedInteger Unsigned short Long Long UnsignedLong Unsigned long Real Float Double Decimal String Date Time DateTime Blob SAFEARRAY(Unsigned char) Arrays(PowerBuilder データ型) ResultSet SAFEARRAY(COM データ型) LPDISPATCH カスタム クラス ユーザ オブジェ クト * Any LPDISPATCH グローバル構造体 OLEObjects アプリケーション テクニック Double Double BSTR DATE DATE DATE サポートなし サポートなし サポートなし 625 コンポーネント インタフェースの定義 * カスタム クラス ユーザ オブジェクトは、同じ COM アパートメントの同じクライア ント内(つまり、同じスレッド内)で作成する必要があります。 コーディング上の制約 ユーザ オブジェクトを COM コンポーネントとして配布する場合に は、コードで使用できない要素がいくつかあります。 関数の多重定義は使用 できない COM は、COM オブジェクトへのインタフェースにおいて、関数の多 重定義をサポートしていません。ユーザ オブジェクト(およびその先 祖)内の各関数の名前は一意でなければなりません。PowerBuilder COM オブジェクトは単一のインタフェースしか持ちません。同じ名前で あってもシグネチャが異なる複数の関数は、複数のインタフェースが 必要となります。 先祖変数と先祖関数の 表現方法 子孫ユーザ オブジェクトから PowerBuilder COM オブジェクトを生成 すると、先祖と子孫のパブリック インスタンス変数と関数がその COM オブジェクトに表現されます。一部のコンポーネント メソッドは先祖 オブジェクトから派生したものになりますが、そのことはクライアン トからは見えません。上述の関数の多重定義の制約によって、子孫オ ブジェクトの関数は先祖オブジェクトの関数を上書きはできますが、 多重定義することはできません。 引数と戻り値のデータ 型 COM オブジェクトとして配布する非ビジュアル オブジェクトに関連 付けられたメソッドは、以下のデータ型を持つ引数を受け取ることが できます。 • 標準の OLE オートメーション データ型 • カスタム クラスの(非ビジュアル)ユーザ オブジェクト COM コンポーネント メソッドは、PowerBuilder 構造体または Any 型の 引数または戻り値を受け取ることができません。引数として Any 変数 を受け取ったり、Any 変数を返したりする PowerBuilder 非ビジュアル オブジェクト上で定義された関数は、そのオブジェクトのローカルな コードからは呼び出せますが、クライアントまたはそのほかの COM コ ンポーネントからこれらの関数にアクセスすることはできません。 コンポーネント メソッドへの引数には、ビジュアル オブジェクト (ウィンドウやメニューなど) 、および大半のシステム タイプ(Transaction オブジェクトや DataStore オブジェクトなど)も指定できません。サ ポートされている唯一のシステム タイプは、ResultSet オブジェクトで す。 626 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 コンポーネント メソッドの戻り値には、任意の標準データ型を指定で きます。また、カスタム クラス(非ビジュアル)ユーザ オブジェクト も指定できます。 COM の検証 COM コンポーネントとして配布する予定のカスタム クラス ユーザ オ ブジェクトを設計する場合には、COM において有効でないコード要素 を使用したときに、PowerBuilder に警告させることができます。 COM の検証では、関数の多重定義の有無をチェックし、パブリック イ ンスタンス変数とパブリック関数で、システム タイプ、ビジュアル タ イプ、構造体、および Any 変数が使用されていないかチェックします。 ユーザ オブジェクト ペインタで、メニューバーから[デザイン| COM 検証]がチェックされていることを確認してください。オブジェクト を保存すると、出力ウィンドウに以下のような警告が一覧表示されま す。 情報 C0197: コンポーネント検証 警告 C0198: 適切でない COM タイプ : 'any' arg type for function: 'of_badfunc' 警告 C0198: 適切でない COM タイプ : 'window' arg type for function: 'of_badfunc' 検証状態は、ユーザ オブジェクト ペインタではなく、編集中のオブ ジェクトに関連付けられます。オブジェクトを再び開くと、オブジェ クトの検証状態は閉じたときと同じになります。新規の COM オブジェ クトは、COM 検証がチェックされた状態で作成されます。 ログ ファイルへのエラー記録 COM+ で動作している COM オブジェクトによって生成されたエラー を、Windows シ ス テ ム の ア プ リ ケ ー シ ョ ン ロ グ に 出 力 す る に は、 ErrorLogging サービス コンテキスト オブジェクトのインスタンスを作 成し、その log メソッドを呼び出します。たとえば、次のようになり ます。 ErrorLogging el this.GetContextService("ErrorLogging", el) el.log(" この文字列をログに書き込みます ") アプリケーション テクニック 627 COM コンポーネントからデータベースへのアクセス 例外情報の自動記録 サーバで実行している PowerBuilder コンポーネントが引き起こす例外 の種類および例外の位置に関する情報は、自動的にサーバ ログに記録 されます。これらの例外についての最低限の情報を取得するためにエ ラー ロギング サービスを実行する必要はありません。 COM コンポーネントからデータベースへのアクセス COM+ のトランザクション管理サポートを活用するには、COM+ がサ ポートするデータベース インタフェースのいずれかを使用してデー タベースに接続する必要があります。PowerBuilder で開発したコン ポーネントのデータベース接続の詳細については、 『データベースとの 接続』マニュアルを参照してください。 PowerBuilder で開発された COM コンポーネントは、データストアを使 用して、データベースとの対話処理を行うことができます。データス トア は非表示のデータウィンドウ コントロールです。つまり、データ ウィンドウ コントロールと同じように動作しますがビジュアル属性 を持ちません。データストア オブジェクトを分散アプリケーションで 使用すると、データベース処理を、各クライアント コンピュータ上で はなくリモート サーバ上で行うことができます。 トランザクション サーバ環境におけるデータベース アクセスに デー タストア を使用する方法についての詳細は、523 ページの「データス トアの使い方」を参照してください。 628 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 結果集合の受け渡し PowerBuilder は、3 つのシステム オブジェクトによって、トランザク ション サーバ環境で動作しているコンポーネントから結果集合を取 得したり、トランザクション サーバ コンポーネントとして動作してい る PowerBuilder ユーザ オブジェクトから結果集合を返したりする操作 を行います。これらのシステム オブジェクト(ResultSet、ResultSets、 および ADOResultSet)は、データストア オブジェクトとの間でトラン ザクション サーバの結果集合の変換を簡単にするために設計された ものであり、状態情報を含んでいません。また、データベースの更新 用には設計されていません。ADOResultSet は、COM コンポーネント でのみ使用できます。 COM+ は、ActiveX Data Objects(ADO)RecordSet オブジェクトを使用 して、結果集合を返します。ADO Recordset オブジェクトは、レコード (行)とフィールド(カラム)から構成され、データベース テーブル 内のレコードの集合を表します。 ADO Recordsets と PowerBuilder システ ム オブジェクト PowerBuilder では、PowerBuilder ADOResultSet システム オブジェクト 上の関数を使用して、データを取得および設定します。データは ADO Recordset として受け渡しされます。PowerBuilder クライアントは、 OLEObjects を使用して ADO Recordsets を処理します。ResultSet オブ ジェクトに格納された結果集合のデータストアへの変換とデータスト ア オブジェクトから結果集合への変換を行うには、データストア オブ ジェクトの CreateFrom 関数と GenerateResultSet 関数を使用します。 GenerateResultSet について GenerateResultSet には、EAServer で MASP(Method as Stored Procedure) を使用するとき、結果集合を戻すのに使用する別の構文もあります。 表 27-3 に、これらのオブジェクトの対話方法を示します。 表 27-3: 結果集合オブジェクト 使用する変数の タイプ ResultSet OLEObject アプリケーション テクニック 使用方法 COM コンポーネントに定義されたメソッド(関数)の戻 り値として使用する。データは ADO Recordset としてマー シャリングされる ResultSet を返す COM コンポーネント上のメソッドから 返された ADO Recordset を保持する。OLEObject は、 MoveFirst などの ADO Recordset 関数を使用して操作でき る 629 COM コンポーネントからデータベースへのアクセス 使用する変数の タイプ 使用方法 ADOResultSet SetResultSet を使用して、ADOResultSet オブジェクトに ResultSet オブジェクトのデータ値を設定する SetRecordSet を使用して、ADOResultSet オブジェクトに、 ADO Recordset を保持する OLEObject のデータ値を設定す る DataStore GetRecordSet を使用して、OLEObject に ADOResultSet の データ値を設定する。OLEObject は、MoveFirst などの ADO Recordset 関数を使用して操作できる CreateFrom を使用して、ResultSet 型または ADOResultSet 型のオブジェクトからデータストアを作成する GenerateResultSet を使用して、トランザクション サーバ上 のメソッドでデータストア オブジェクトから ResultSet オ ブジェクトを生成する。ResultSet オブジェクトは、クライ アントに返すことができる PowerBuilder クライ アントから COM コン ポーネント内の結果集 合にアクセス PowerBuilder クライアントが、ADO Recordset を返す COM コンポーネ ント メソッドを呼び出すと、返されたデータは OLEObject オブジェクト に格納されます。ADO Recordset 内のデータを操作するには、Recordset 関数を使用します。これについては、次の「PowerBuilder における ADO Recordset の使い方」で説明します。 OLEObject オブジェクト内のデータを使用してデータストア オブジェ クトを設定するには、ADOResultSet オブジェクトを作成してから、そ の SetRecordSet 関数を呼び出して、OLEObject オブジェクトに格納さ れたデータ値を設定します。 ADOResultSet オブジェクト内のデータをデータストア オブジェクト に設定するには、CreateFrom データストア関数を使用します。 OLEObject loo_mycomponent OLEObject loo_ADOrecordset ADOresultset lrs_ADOresultset datastore ds_local integer li_rc loo_mycomponent = CREATE OLEObject li_rc = loo_mycomponent.ConnectToNewObject("PB.Test") if li_rc <> 0 then MessageBox(" 接続失敗 ", string(li_rc) ) Return end if // OLEObject を使用して、COM コンポーネント上の 630 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 // メソッドから返された ADO Recordset を保持する loo_ADOrecordset = loo_mycomponent.GetTestResult() // ADOResultSet を作成し、渡された ADO Recordset を // 保持している OLEObject からそのデータを取得する lrs_ADOresultset = CREATE ADOResultSet lrs_ADOresultset.SetRecordSet(loo_ADOrecordset) // CreateFrom を使用して、ADOResultSet オブジェクト // のデータをデータストアに設定する ds_local = CREATE datastore ds_local.createfrom(lrs_ADOresultset) PowerBuilder におけ る ADO Recordset の 使い方 MoveFirst や MoveNext な ど の ADO Recordset メ ソ ッ ド を 使 用 し て、 PowerBuilder で ADO Recordset を操作する場合は、SetResultSet 関数と GetRecordSet 関数を使用します。SetResultSet 関数を使用して、新規の ADOResultSet オブジェクトに ResultSet オブジェクトのデータ値を設 定し、GetRecordSet 関数を使用して ADO Recordset を返します。 次の例では、既存の データストア オブジェクトから、ResultSet オブ ジェクトに結果集合を生成しています。ResultSet オブジェクトを使用 し て、新 し い ADOResultSet オ ブ ジ ェ ク ト に デ ー タ を 設 定 し ま す。 ADOResultSet オブジェクト上の GetRecordSet 関数を使用して、ADO Recordset を OLEObject として返し、この OLEObject を ADO Recordset メソッドで使用します。 ResultSet lrs_resultset ADOresultset lrs_ADOresultset OLEObject loo_ADOrecordset // 既存のデータストアから結果集合を生成する ds_source.GenerateResultSet(lrs_resultset) // 新しい ADOResultSet オブジェクトを作成し、生成された // 結果集合をそのオブジェクトに設定する lrs_ADOresultset = CREATE ADOResultSet lrs_ADOResultset.SetResultSet(lrs_resultset) // ADOResultSet オブジェクト内のデータを // OLEObject に渡し、ADO Recordset として使用できるようにする loo_ADOrecordset = CREATE OLEObject lrs_ADOResultset.GetRecordSet(loo_ADOrecordset) // OLEObject 上のネイティブな ADO Recordset メソッドを // 呼び出す loo_ADOrecordset.MoveFirst() アプリケーション テクニック 631 トランザクションのサポート COM および COM+ コンポーネントから結 果集合を返す COM または COM+ に配布される PowerBuilder ユーザ オブジェクトと の間で結果集合を受け渡しするには、関数の引数または戻り値のデー タ型に ResultSet を指定します。GenerateResultSet 関数を呼び出して、 COM または COM+ 内のデータストア オブジェクトから結果集合を作 成すると、結果集合はマーシャリングされて、ADO Recordset としてク ライアントに返されます。 次の例では、データストア オブジェクトを作成し、その中にあるデー タを取り出し、続いて GenerateResultSet 関数を使用して、クライアン トに返す結果集合を作成しています。 datastore ds_datastoreresultset lrs_resultset integer li_rc ds_datastore = create datastore ds_datastore.dataobject = "d_empdata" ds_datastore.SetTransObject (SQLCA) IF ds_datastore.Retrieve() = -1 THEN // エラーを返して復帰 END IF li_rc = ds_datastore.generateresultset(lrs_resultset) IF li_rc <> 1 THEN // エラーを返して復帰 END IF return lrs_resultset トランザクションのサポート コンポーネントがトランザクションをサポートする場合、COM+ は、 コンポーネントのデータベース操作がトランザクションの一部として 実行されるようにします。 トランザクション サービス コンテキス ト オブジェクトの使 い方 632 COM+ で動作する PowerBuilder コンポーネントは、トランザクション コンテキスト サービスを使用して、トランザクションを制御できま す。PowerBuilder COM オブジェクトが作成するコンテキスト オブジェ クトによって、PowerBuilder コンポーネントは Microsoft DTC を利用す ることができます。TransactionServer オブジェクトによって、COM+ で動作する COM オブジェクトは、オブジェクトに関連付けられてい るコンテキストにアクセスできるため、トランザクションとアクティ ブ化をより厳しく管理できます。また、セキュリティ コンテキストに 関しても部分的に制御が可能です。 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 TransactionServer オブジェクトとそのメソッドのについての詳細は、 『オブジェクトとコントロール』マニュアルおよび『PowerScript リファ レンス』マニュアルを参照してください。 トランザクション コンテキスト サービスを使用するには、その前に、 TransactionServer 型の変数を宣言し、GetContextService 関数を呼び出し てサービスのインスタンスを作成する必要があります。 TransactionServer txninfo_base this.GetContextService("TransactionServer", & txninfo_base) コンポーネントのトランザクション コンテキストに関する情報にア クセスしてトランザクションを制御するには、たとえば、次のように、 TransactionServer オブジェクトのインスタンス上のメソッドを呼び出 します。 IF txninfo_base.IsInTransaction() THEN txninfo_base.DisableCommit() END IF ... txninfo_base.SetComplete() サービスへの参照が不要になったら、次のように破棄してください。 DESTROY txninfo_base COMMIT と ROLLBACK の動作 PowerBuilder コンポーネントが COM+ で動作しており、 UseContextObject DBParm パラメータに Yes が設定されている場合に は、TransactionServer インタフェースを使用してトランザクションを 制御します。UseContextObject の DBParm パラメータに Yes が設定さ れていると、COMMIT 文と ROLLBACK 文でデータベース エラーが発生 します。このトランザクションは、TransactionServer コンテキスト オ ブジェクトのインスタンスを介して SetComplete または SetAbort が発行 されるまでは、アクティブ状態を保ちます。 アプリケーション テクニック 633 トランザクションのサポート PowerBuilder 6 コンポーネントの移行 PowerBuilder 6 で作成したコンポーネントは、 COM+ に対する SetComplete または SetAbort 呼び出しの発行を、PowerBuilder のデータベース ドラ イバで行っています。これらのコンポーネントを現行のバージョンの PowerBuilder に移行する場合には、TransactionServer インタフェースを 使 用 す る よ う に、コ ー ド を 修 正 し な け れ ば な り ま せ ん。ま た は、 UseContextObject DBParm に No を設定する方法もあります。この場合、 COMMIT は SetComplete と等しくなり、ROLLBACK は SetAbort と等しく なります。この方法は、PowerBuilder のオブジェクトをコードを修正 せずに移行する場合にだけお勧めします。 コンポーネントがトラ ンザクションをサポー トするかどうかの指定 各 COM+ コンポーネントには、コンポーネントのトランザクションへ の参加方法を指示するトランザクション プロパティがあります。 COM+ におけるコンポーネント トランザクション プロパティに[新規 が必要]を設定すると、PowerBuilder COM オブジェクトは、新規のコ ンテキスト オブジェクトを作成します。PowerBuilder COM オブジェク トのコンポーネント トランザクション プロパティに、[必要]または [サポート]を設定すると、既存のオブジェクトからトランザクション を継承するか、または新規トランザクションを作成します。 このプロパティは、COM/COM+ プロジェクト ウィザードまたはプロ ジェクト ペインタで設定します。設定可能な値は、表 27-4 のとおりで す。 表 27-4: コンポーネント トランザクション プロパティの値 トランザクションの 種類 [サポートなし] [サポート] 634 説明 コンポーネントはトランザクションの一部として実 行されない。コンポーネントが、トランザクション 内部で実行中の別のコンポーネントによってアク ティブにされた場合には、その新しいインスタンス の作業は既存のトランザクションの外部で行われる コンポーネントは COM+ トランザクションのコンテ キスト内で実行できるが、コンポーネントのメソッ ドを実行するために接続は必要ない。コンポーネン トがクライアントによって直接インスタンス化され た場合には、COM+ はトランザクションを開始しな い。コンポーネント A がコンポーネント B によって インスタンス化され、コンポーネント B はトランザ クション内部で実行されている場合には、コンポー ネント A は同じトランザクション内で実行される PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 トランザクションの 種類 説明 [必要] コンポーネントは常にトランザクション内で実行さ れる。コンポーネントがクライアントによって直接 インスタンス化された場合には、新しいトランザク ションが始まる。コンポーネント A がコンポーネン ト B によってアクティブにされ、しかも B はトラン ザクション内で実行されている場合には、A は同じ トランザクション内で実行される。B がトランザク ション内で実行されていない場合には、A は新しい トランザクション内で実行される [新規が必要] コンポーネントがインスタンス化されるたびに、新 しいトランザクションが始まる。コンポーネント A がコンポーネント B によってアクティブにされ、B がトランザクション内部で実行されている場合に は、A は B のトランザクションの結果に影響されな い新しいトランザクションを開始する。B がトラン ザクション内で実行されていない場合には、A は新 しいトランザクション内で実行される トランザクションの仕組みについての詳細は、MSDN Library のサイト http://msdn.microsoft.com/library/default.asp に あ る Microsoft COM+ の マ ニュアルを参照してください。 別のサーバ コンポーネントのメソッドの呼び出し COM+ では、あるサーバ コンポーネントのメソッドが、別のサーバ コ ンポーネントのメソッドを呼び出すことができます。この別のサーバ コンポーネントは、PowerBuilder コンポーネントである必要はなく、 COM+ によってサポートされている任意の言語で実装できます。 OLEObject オブジェ クトの使い方 別のコンポーネントのメソッドにアクセスするには、クライアントか らコンポーネントを呼び出す場合と同様に、OLEObject 型の変数を宣 言し、ConnectToNewObject 関数を呼び出して、コンポーネントに接続し ます。ConnectToNewObject は、サーバ オブジェクトのトランザクショ ン コンテキストを自動的に継承します。 アプリケーション テクニック 635 セキュリティ問題 TransactionServer オ ブジェクトの使い方 現行のサーバ内の別のコンポーネントのメソッドにアクセスするには、 PowerBuilder が提供する、TransactionServer というトランザクション サービス コンテキスト オブジェクトを使用できます。 TransactionServer イ ンタフェースが提供する CreateInstance というメソッドを使用すれば、 ロ ー カ ル で 使 用 す る ほ か の コ ン ポ ー ネ ン ト に ア ク セ ス で き ま す。 CreateInstance は、呼び出し元のコンポーネントに適用されるのと同じ ユーザ情報とパスワード情報を使用します。 セキュリティ問題 COM+ に配布するコンポーネントを開発するときには、ロールを定義 して、特定のトランザクションの実行を許可されるユーザまたはユー ザのグループを決定することができます。コンポーネントを配布する ときには、COM+ Component Services ツールで特定のユーザにロールを 割り当てます。 プロジェクト ペイン タまたはウィザードで の権限の設定 ウィザードを使用して COM/COM+ プロジェクトを作成した場合に は、コンポーネントを呼び出すクライアントのセキュリティ資格を チェックするよう、COM+ に指示することができます。プロジェクト ペインタでは、[COM+ コンポーネント]と[COM+ パッケージ]の プロパティ ページで、コンポーネントとパッケージの 2 つのレベルで のチェックを指定することができます。 セキュリティを有効にするには、Microsoft Management Console 内で COM アプリケーションにロールを追加し、ユーザをそのロールに割り 当て、そのロールをコンポーネントに与えます。 プログラムによるセ キュリティ 636 PowerBuilder がトランザクション サービス オブジェクトで提供してい る関数をコンポーネント内で使用すれば、呼び出し側に特定のメソッ ドを呼び出す権限があるかどうか、プログラムで判定することができ ます。IsSecurityEnabled は、コンポーネントのセキュリティが有効であ るかどうかを判定します。IsCallerInRole は、コンポーネントのメソッド を呼び出すクライアント プロセスまたはサーバ プロセスが、呼び出し 権限を持つロールに含まれるどうかを判定します。 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 IsCallerInRole は、現行のメソッドの直接の呼び出し側のロールを調べ ます。クライアントがコンポーネント上のメソッドを呼び出し、その メソッドがデータベースにアクセスする場合には、データベースへの アクセス権は、クライアントではなく、コンポーネントのセキュリティ コンテキストによって決定されます。PowerBuilder がトランザクショ ン サービス オブジェクトに提供する追加関数によって、コンポーネン トは、クライアントに権限のない操作を実行する前に、クライアント のセキュリティ コンテキストを判断することができます。 ImpersonateClient は、クライアントのセキュリティ コンテキストを判断 します。IsImpersonating は、コンポーネントがそのクライアントのセ キュリティ コンテキスト内で動作しているかどうかを判断します。ま た、RevertToSelf は、コンポーネントのセキュリティ コンテキストを復 元します。 偽装 プロジェクト ペインタでの COM/COM+ コンポーネント の構築 PowerBuilder COM サーバは、プロジェクト ペインタで構築します。 ユーザ オブジェクトの作成時にプロジェクトを作成しなかった場合 には、COM/COM+ プロジェクト ウィザードを使用して作成できます。 [プロジェクト]タブの[COM/COM+ コンポーネント]アイコンを選 択すれば、プロジェクト ペインタで COM コンポーネントを直接作成 するプロジェクトを設定できます。 COM サーバに組み込みたい 1 つまたは複数のオブジェクトに対して、 COM/COM+ プロジェクトをすでに作成している場合には、プロジェク ト ペインタで修正し、必要に応じてオブジェクトを追加します。 プロジェクト ペインタのワークスペースは読み取り専用の領域であ り、ウィザードで選択したオプション、またはペインタのオブジェク トの選択 ダイアログボックスおよびプロパティ ダイアログボックス で選択したオプションが表示されます。PowerBuilder COM サーバを構 築する際、このワークスペースには、構築プロセスの各ステップのス テータスとオブジェクト検査レポートも表示されます。 ❖ PowerBuilder COM サーバ プロジェクトを定義および構築するには 1 アプリケーション テクニック 新規作成 ダイアログボックスの[プロジェクト]タブから [COM/COM+ コンポーネント ウィザード]を選択します。 637 プロジェクト ペインタでの COM/COM+ コンポーネントの構築 2 プロジェクトの名前と位置を含む、プロジェクト プロパティを指 定します。 3 サーバに組み込みたい 1 つまたは複数のオブジェクトを選択しま す。 4 各オブジェクトのプロパティを指定し、必要なら COM+ の配布オ プションも指定して、[完了]をクリックします。 プロパティを指定する際には、ウィザードの状況依存ヘルプまた は以下の項目を参考にしてください。 プロパティ インタフェース オプ ション 構築オプション コンポーネントの登録 COM+ の配布オプショ ンとパッケージ オプ ション COM+ トランザクショ ンの設定 COM+ セキュリティ 参照箇所 640 ページの「カスタム インタフェースと デュアル インタフェースの選択」と 624 ペー ジの「インスタンス変数」 640 ページの「埋め込み PBD の設定」 639 ページの「コンポーネントの自動登録」 639 ページの「COM+ にコンポーネントを配 布」 634 ページの「コンポーネントがトランザク ションをサポートするかどうかの指定」 636 ページの「セキュリティ問題」 5 [ファイル|開く]を選択し、作成したばかりのプロジェクトを選 択して、プロジェクト ペインタを開きます。 正しいオブジェクトが選択されていることを確認するには、メ ニューバーから[編集|オブジェクトの選択]を選択します。 6 [編集|プロパティ]を選択してウィザードで設定したプロパティ を確認し、必要なら修正します。 一部の高度な COM+ パッケージ プロパティは、プロジェクト ペイ ンタでのみ設定できます。 7 プロジェクト ペインタで[配布]ボタンをクリックして、 PowerBuilder COM サーバを構築します。 こ の 構 築 プ ロ セ ス で は、選 択 し た 各 ユ ー ザ オ ブ ジ ェ ク ト の PowerBuilder COM オブジェクトを含む PowerBuilder COM サーバ (DLL)と IDL ファイルが作成されます。COM+ への配布を指定 し、COM+ がコンポーネントを生成するコンピュータ上にインス トールされ動作している場合、コンポーネントはサーバに直接配 布されます。このとき、追加の配布ファイルが作成されることも あります。 638 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 PowerBuilder COM サーバに含まれる埋め込み型 PBD ファイルに は、カスタム クラス ユーザ オブジェクトと、それらのオブジェク トが参照する補助オブジェクトに加えて、埋め込みのタイプ ライ ブラリも含まれています。 オブジェクト呼び出し後のプロジェクトの構築 開発環境で COM オブジェクトを呼び出すと、COM オブジェクトは PowerBuilder と同じプロセスで管理されるので PowerBuilder が終了す るまでメモリに残ります。オブジェクトを呼び出してから変更し、プ ロジェクト ペインタで再生成しようとすると、コンパイル エラーとリ ンク エラーが発生します。プロジェクトを構築する前に、PowerBuilder をシャットダウンして再起動し、メモリからオブジェクトを解放して ください。 コンポーネントの自動登録 プロジェクト ウィザードまたはプロジェクト ペインタでは、構築に成 功したときに、生成されたすべての PowerBuilder COM オブジェクトを 自動登録するように指定できます。これによって、使用コンピュータ でのコンポーネントのテストが簡単になります。使用コンピュータ上 で不必要なレジストリ エントリが作成されるのを避けるため、このオ プションを選択するのは、PowerBuilder COM サーバのテスト準備が完 了してからにしてください。 COM+ にコンポーネントを配布 正常に構築されたコンポーネントは、COM+ に自動的に配布できます。 アプリケーションを Microsoft Windows Installer(MSI)ファイルにエク スポートし、これを使って別のコンピュータ上の COM+ サーバにパッ ケージをインポートできます。次にアプリケーション プロキシを MSI ファイルとしてエクスポートし、それをクライアント コンピュータ上 にインストールすると、リモートの COM+ サーバにアクセスできるよ うになります。COM+ コンポーネントの配布についての詳細は、MSDN Library のサイト http://msdn.microsoft.com/library/default.asp にある Microsoft COM+ のマニュアルを参照してください。 アプリケーション テクニック 639 プロジェクト ペインタでの COM/COM+ コンポーネントの構築 カスタム インタフェースとデュアル インタフェースの選択 COM オブジェクトを生成するときには、クライアントにカスタム イ ンタフェースとデュアル インタフェースのどちらを公開するのかを 選択する必要があります。PowerBuilder COM オブジェクトでは、現在、 どちらのインタフェース タイプでも、標準の OLE オートメーション データ型しか使用できません。 カスタム インタ フェース カスタム インタフェースは、サーバ オブジェクトの仮想関数テーブル (VTBL)へのアクセスを通じて、ディスパッチベースのインタフェー スより高いパフォーマンスと、デュアル インタフェースよりすっきり した使用モデルを提供します。クライアントを C++ などのコンパイル 言語で記述する場合、または Visual Basic などのツールでカスタム イ ンタフェースのサポートを活用する場合には、カスタム インタフェー スの使用を考えてください。 カスタム インタフェースを使用する PowerBuilder COM オブジェクト は、COM によって提供される標準のマーシャル処理を使用します。 デュアル インタ フェース デュアル インタフェースを使用すれば、プログラマは、仮想関数テー ブルとディスパッチ インタフェースのどちらを使用しても、COM オ ブジェクト内のメソッドを呼び出すことができます。デュアル インタ フェースは、広範囲のクライアントをサポートし、メソッドへの高速 アクセスを提供します。 埋め込み PBD の設定 COM サーバに含まれる埋め込み PowerBuilder 動的ライブラリ(PBD) ファイルには、選択したコンパイル済みのすべてのカスタム クラス ユーザ オブジェクトとその依存オブジェクトが含まれています。追加 の未参照オブジェクトを PBD に組み込むには、[ライブラリ]プロパ ティ ページで、そのオブジェクトを含むライブラリを選択します。選 択したライブラリ内のすべてのオブジェクトが PBD に含められます。 ライブラリに関連付けられた PowerBuilder リソース(PBR)ファイル の名前を指定できます。PBR ファイルは、ビットマップなどの動的に 割り当てられたリソースのリストを含むテキスト ファイルです。詳細 については、837 ページの「リソースについて」を参照してください。 640 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 PowerBuilder COM オブジェクトの実行 PowerBuilder COM オ ブ ジ ェ ク ト の イ ン ス タ ン ス を 設 定 す る た め、 PowerBuilder 仮想マシン(PBVM110.dll)は、COM サーバ DLL に埋め 込まれた PBD からカスタム クラス オブジェクトをロードし、適切な セッション情報とインスタンス情報を作成します。クライアントが PowerBuilder COM オブジェクトのメソッドを呼び出すと、そのメソッ ドは PowerBuilder 仮想マシンをコールバックし、適切な PowerScript コードを実行します。 PowerBuilder COM サーバは、COM の single-threaded apartment(STA) モデルを使用しています。実行時セッションは、同じスレッド上に作 成されたオブジェクト間で共有できます。クライアントが PowerBuilder COM オブジェクトのインスタンスを要求すると、PowerBuilder COM サーバは実行時セッションを確立し、その実行時セッション中にカス タム クラス ユーザ オブジェクトのインスタンスを作成します。サー バが同じスレッドから COM オブジェクトのインスタンスに対する新 しいリクエストを受け取ると、既存の実行時セッションを使用して、 オブジェクトをインスタンス化します。 いずれの場合も、個々のクライアントは異なる PowerBuilder 仮想マシ ン セッションを使用します。 メモリの割り当て クライアントが PowerBuilder COM サーバから PowerBuilder COM オブ ジェクトのインスタンスを初めて要求すると、サーバは PowerBuilder 仮想マシンをロードし、メモリ ブロックを割り当て、実行時セッショ ンを開始します。PowerBuilder 仮想マシン、キャッシュ メモリ、およ び実行時セッションに約 4 MB のメモリが割り当てられます。 オブジェクトが同じ実行時セッションを共有できる場合には、それ以 降のリクエストでは追加のメモリ割り当てが不要になります。 それ以降のリクエストにおいて、リクエストが別のクライアントまた はスレッドから作成されたなどの理由で、PowerBuilder COM オブジェ クトを別の COM アパートメントで作成する必要がある場合、オブジェ クトは新しい実行時セッションでインスタンス化されます。新しい各 セッションは、PowerBuilder 仮想マシンのインスタンスとキャッシュ メモリを共有するため、約 200 KB のメモリを消費するだけで済みま す。 アプリケーション テクニック 641 PowerBuilder COM サーバの配布 PowerBuilder COM サーバの配布 PowerBuilder COM サーバを生成したら、COM 対応のクライアント ア プリケーションを使用して、PowerBuilder COM オブジェクトを作成 し、それらのメソッドにアクセスすることができます。COM 対応の任 意のアプリケーションでサーバを使用したり、サーバをパッケージと して COM+ に配布したりすることができます。 COM 対応のアプリケーションによる PowerBuilder COM サーバの使い方 ❖ COM 対応のアプリケーションで PowerBuilder COM サーバを使用するには 1 PowerBuilder COM サーバをユーザのコンピュータに配布します。 2 PowerBuilder 仮想マシン(PBVM110.dll)とそのほかの必要なモ ジュール(PBCOMRT110.DLL、PBDWE110.DLL、あるいは必要な データベース ソフトウェアなど)を、PowerBuilder COM サーバ をインストールしたコンピュータに配布します。 3 PowerBuilder COM サーバをユーザのコンピュータに登録します。 4 PowerBuilder COM サーバ内の PB オブジェクト関数を呼び出すク ライアント アプリケーションを記述します。 643 ページの「クライアントから PowerBuilder COM サーバへのア クセス」を参照してください。 PowerBuilder COM サーバの登録 PowerBuilder COM サーバを配布する ときには、レジストリに情報を追加して、COM がサーバ オブジェクト のインスタンスを作成できるようにする必要があります。PowerBuilder COM サーバは自己登録型なので、登録ファイルを別に作成する必要は ありません。PowerBuilder COM サーバを登録するには、次のように REGSVR32 ユーティリティを使用します。 regsvr32.exe path_to_server\mycomserver.dll リモート クライアントからサーバにアクセスする場合には、レジスト リをさらに変更する必要があり、サーバへのリモート アクセス用にク ライアントの設定が必要になる場合もあります。詳細については、647 ページの「DCOM での PowerBuilder COM サーバとオブジェクトの使 い方」を参照してください。 642 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 テスト用の自動登録 テスト目的の場合には、 [全般]プロパティ ページにあるチェックボッ クスをオンにします。これにより、サーバが生成されるとそのサーバ は開発コンピュータに自動登録されます。使用コンピュータ上で不必 要なレジストリ エントリが作成されるのを避けるため、このオプショ ンを選択するのは、PowerBuilder COM サーバのテスト準備が完了して からにしてください。 クライアントから PowerBuilder COM サーバへのアクセス COM 準拠のツールで作成したクライアントは、PowerBuilder COM コ ンポーネント上のメソッドにアクセスできます。COM+ の場合、クラ イアントは Microsoft Windows Installer を必要とします。COM サーバが クライアント マシンに登録されているか、COM+ アプリケーション プ ロキシ ファイルがインストールされていなければなりません。 リモート クライアントから PB COM サーバにアクセスする方法につ いては、647 ページの「DCOM での PowerBuilder COM サーバとオブ ジェクトの使い方」を参照してください。 以下の例では、Visual Basic または C++ から PowerBuilder COM オブジェ クトにアクセスする方法を示します。これらの例では、ccuo_employee と いうユーザ オブジェクトから生成され、PB110.employee というプログ ラム ID を持つ PowerBuilder COM オブジェクトを使用します。 PowerBuilder クライアントの作成方法と、同じ COM オブジェクトの使 用例については、第 28 章「COM/COM+ クライアントの構築」を参照 してください。 クライアントとしての Visual Basic Visual Basic では、そのプログラム ID を使用して登録オブジェクトに 接続できます(実行時バインド)。Visual Basic 5 以降では、そのクラス 名も使用できます(事前バインド)。 ❖ Visual Basic で PowerBuilder COM オブジェクトにアクセスするには 1 アプリケーション テクニック 次のどちらかを実行します。 643 クライアントから PowerBuilder COM サーバへのアクセス • オブジェクトを宣言し、そのプログラム ID を使用して接続し ます。 Dim EmpObj As Object Set EmpObj = CreateObject("PB110.employee") • PowerBuilder COM オブジェクトに対して生成されたタイプ ラ イブラリへの参照をプロジェクトに追加し、そのクラス名を使 用してオブジェクトのインスタンスを宣言します(Visual Basic 5 以降)。 Dim EmpObj As New CoEmployee 2 接続が確立されたことを確認します。 Dim response If EmpObj Is Nothing Then response = MsgBox("Employee オブジェクトの作成 ", vbOKOnly, " エラー ") End If 3 オブジェクトの関数またはプロパティにアクセスします。 Dim units, time as Long Dim DoubleReturn as Double Dim StringReturn As String DoubleReturn = EmpObj.f_calcdayavg units, time StringReturn = EmpObj.f_teststring EmpObj.ll_hours = 37 4 オブジェクトを破棄します。 Set EmpObj = Nothing クライアントとしての C++ C++ では、COM ライブラリ関数を使用して、PowerBuilder COM オブ ジェクトのインスタンスを作成します。クライアントを作成するとき には、PowerBuilder COM オブジェクトの C/C++ 定義も使用する必要が あります。Microsoft IDL(MIDL)コンパイラは、PowerBuilder COM ジェネレータによって作成された IDL ファイルから、これらの定義を 生成します。 たとえば、PowerBuilder COM オブジェクト Employee に対して生成さ れた IDL ファイルを使用する場合は、次のようになります。 midl.exe employee.idl 644 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 MIDL コンパイラは、IDL ファイル内の全オブジェクトのインタフェー スの定義を含んでいるヘッダ ファイル(employee.h)、およびオブジェ クトに関連付けられた CLSID とインタフェース ID(IID)を定義する C ファイル(employee_i.c)を生成します。 そのほかのファイル MIDL コンパイラはプロキシ/スタブ コードも(employee_p.c と dlldata.c に)生成します。ただし、C++ クライアント実行ファイルを作成した り、PowerBuilder COM オブジェクトにアクセスするのに、プロキシ / スタブ コードを使用したりする必要はありません。 PowerBuilder COM オブジェクト内のメソッドに アクセスできる C++ クライアント実行ファイルを作成するには、生成 されたヘッダ ファイルを組み込む C++ ソース ファイルを作成し、 MIDL コンパイラによって生成された C ファイルと C++ クライアント ソース ファイルの両方をコンパイルし、それによって得られるオブ ジェクト ファイルをリンクして実行ファイルを作成します。 クライアントの作成 Employee の例では、次のようになります。 1 client.cpp という C++ ソース ファイル(下記参照)を作成します。 2 client.cpp をコンパイルします。 3 employee_i.c をコンパイルします。 4 client.obj と employee_i.obj をリンクして、実行ファイル(たとえ ば、employee_ecl.exe)を作成します。 Employee.h 以下のコードは、MIDL コンパイラによって生成された employee.h ヘッダ ファイルの一部で、C++ クライアントによって使用 される定義を表します。 typedef interface DIEmployee DIEmployee; EXTERN_C const IID IID_DIEmployee; interface DECLSPEC_UUID("A2F59F71-D5FB-11D1-92B900A0247712F1") DIEmployee :public IDispatch { public: virtual /* [id] */ HRESULT STDMETHODCALLTYPE f_calcdayavg( /* [in] */ long units, /* [in] */ long time, /* [retval][out] */ double __RPC_FAR *retval) = 0; アプリケーション テクニック 645 クライアントから PowerBuilder COM サーバへのアクセス virtual /* [id] */ HRESULT STDMETHODCALLTYPE f_teststring( /* [retval][out] */ BSTR __RPC_FAR *retval) = 0; }; EXTERN_C const CLSID CLSID_CoEmployee; Client.cpp 次のサンプル クライアント ファイルでは、MIDL によって 生成された、PowerBuilder COM オブジェクトの C/C++ 定義を使用して います。client.cpp に示されている COM API 呼び出しについての詳細 は、Microsoft ソフトウェア開発キットの資料を参照してください。 #include <windows.h> // employee.h I( MIDL.EXE から ) #include "employee.h" int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR, int) { HRESULT hr; DIEmployee *pDIEmployee = 0; // COM を初期化する CoInitialize(0); hr = CoCreateInstance(CLSID_CoEmployee,NULL, CLSCTX_INPROC_SERVER, IID_DIEmployee, (void **)&pDIEmployee); if (FAILED(hr)) ErrorMessage("CoCreateInstance", hr); // メソッドの変数 long units, time; double dReturn; BSTR strReturn = NULL; // メソッドを呼び出す hr = pDIEmployee->f_calcdayavg(units, time,&dReturn); if (FAILED(hr)) ErrorMessage("f_calcdayavg",hr); hr = pDIEmployee->f_teststring(&strReturn); if (FAILED(hr)) ErrorMessage("f_teststring",hr); 646 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 // インタフェース ptr を解放 pDIEmployee->Release(); CoFreeUnusedLibraries(); // 完了 CoUninitialize(); return 0; } DCOM での PowerBuilder COM サーバとオブジェクトの使い方 DCOM を使用すれば、リモート クライアントから PowerBuilder COM オブジェクトをアクティブにすることができます。オブジェクトは、 指定されたホスト コンピュータ上のサーバ プロセスでアクティブに する必要があります。アウト オブ プロセス サーバ(EXE ファイル) はサーバ プロセスを作成しますが、インプロセス サーバ(DLL ファ イル)は代理プロセス下で動作させる必要があります。 COM は、PowerBuilder COM サーバ DLL のホストとして使用できる汎 用の代理ホスト(DLLHOST.EXE)を提供しています。代理ホストを 使用するように、PowerBuilder COM サーバにマークを付けることは、 PowerBuilder COM オブジェクトをリモート クライアントからアクセ スを可能にするための最も重要なステップです。DCOM 環境設定ユー ティリティ(DCOMCNFG.EXE)を使用して、位置、セキュリティ、お よび識別情報の値を変更できますが、多くの場合にはデフォルトのま まで十分です。詳細については、DCOMCNFG ユーティリティのオンラ イン ヘルプを参照してください。 PowerBuilder COM サーバが代理ホストを 使用できるようにする PowerBuilder COM サーバが代理ホストを使用できるようにするには、 2 つの方法があります。 • レジストリ エディタ(REGEDIT32.EXE)を使用して、PowerBuilder COM サーバのレジストリ エントリ AppID を編集する • Microsoft Visual C++ 5.0 以降に付属する OLE/COM オブジェクト ビューア(OLEVIEW.EXE)を使用する コンピュータのレジストリを手作業で編集すると、コンピュータの構 成の一部または全部が動作不能になることがあるため、一般には OLEVIEW の使用をお勧めします。 アプリケーション テクニック 647 クライアントから PowerBuilder COM サーバへのアクセス ❖ レジストリ エディタを使用して、COM サーバが代理プロセスを使用できる ようにするには 1 サーバの生成に使われたプロジェクトを開き、 [全般]プロパティ ページから PowerBuilder COM サーバの AppID 値をコピーします。 2 REGEDIT.EXE を実行し、 マイ コンピュータ \HKEY_CLASSES_ROOT\AppID の位置にある サーバの AppID キーを探して選択します。 3 メニューバーから[編集|新規作成|文字列の値]を選択します。 4 名前に DllSurrogate を入力し、データ フィールドは空のままに しておきます。 データ フィールドが空である場合、COM はデフォルトの代理ホス ト(DLLHOST.EXE)を使用します。AppID 値のキーは次のように なります。 名前 (デフォルト) DllSurrogate ❖ データ PowerBuilder 11.0 が生成したサーバ :servername.dll "" OLE/COM オブジェクト ビューアを使用して、COM サーバが代理プロセス を使用できるようにするには 1 OLEVIEW.EXE を実行します。 2 リストビューでオートメーション オブジェクトを展開し、 PowerBuilder COM サーバのオブジェクトを選択します。 3 PowerBuilder COM サーバに関連付けられたオブジェクトを選択し ます。 4 [Implementation]タブを選択します。 5 [Inproc Server]タブを選択し、[Use Surrogate Process]チェック ボックスをオンにします。 クライアント コン ピュータを設定して、 リモート PowerBuilder COM オ ブジェクトをアクティ ブにする 648 リモート コンポーネントをアクティブにするには、クライアント アプ リケーションが、オブジェクトのクラス識別子(CLSID)を、リモー ト ホストに対するアクティブ化リクエストに指定して渡す必要があ ります。 PowerBuilder 11.0 や C++ で作成されたクライアントなど、一部のクラ イアントは、リモート オブジェクトのインスタンスを作成するとき に、メソッド呼び出しでオブジェクトの CLSID を使用できます。これ らのクライアント アプリケーションは、クライアント側の環境設定を 必要としません。 PowerBuilder 第 27 章 COM/COM+ コンポーネントの構築 多くのクライアントは、オブジェクトの CLSID ではなく、オブジェク トの名前(ProgID)によってオブジェクトを参照します。このような 場合、リモート アクティブ化リクエストを行うためには、クライアン ト コンピュータのレジストリに、ProgID を CLSID にマップするため に必要な情報が含まれていなければなりません。必要なレジストリ情 報をクライアント コンピュータに追加するには、次のどちらかの方法 を使用します。 • リモート アクセスを必要とするクライアント コンピュータごとに、 PowerBuilder COM サーバを登録します。 この方法を使用するには、適切なバージョンの PBVMn0.dll がイン ストールされていなければなりません。 • PowerBuilder COM サーバが登録されているホスト上で、 REGEDIT.EXE を使用して、必要なレジストリ情報を .REG ファイ ルにエクスポートし、続いてリモート アクセスを必要とする各ク ライアント コンピュータのレジストリに、これらのファイルをコ ピーおよびインポートします。 PowerBuilder COM オブジェクトごとに、以下のレジストリ キーを エクスポートします。 HKEY_CLASSES_ROOT\PB110.objectname HKEY_CLASSES_ROOT\PB110.objectname.version_number HKEY_CLASSES_ROOT\CLSID\{objects_clsid} PowerBuilder COM サーバには、以下のレジストリ キーが必要なこ ともあります。 HKEY_CLASSES_ROOT\TypeLib\{comserver_typelib_id} HKEY_CLASSES_ROOT\AppID\{comserver_application_id} PowerBuilder を使用 してリモート オブ ジェクトに接続する PowerBuilder クライアントは、ConnectToNewRemoteObject 関数を使用し てリモート オブジェクトをアクティブにすることができます。この部 分のコードは次のようになります。 OLEObject remobj remobj = CREATE OLEObject remobj.ConnectToNewRemoteObject("myremotehostname", "PB110.employee") & リモート オブジェクトの CLSID 文字列を classname パラメータに指定 することもできます。 remobj.ConnectToNewRemoteObject("myremotehostname", "clsid:0EA53FED-646A-11D2-BF8E-00C04F795006") アプリケーション テクニック & 649 クライアントから PowerBuilder COM サーバへのアクセス classname パラメータにオブジェクトの CLSID を指定すると、クライ アント側での環境設定は不要になります。 C++ を使用したリ モート オブジェクト に接続 生成された PowerBuilder COM サーバの IDL ファイルから作成された ヘッダ ファイルを使用する C++ クライアントは、アクティブ化リクエ ストで、リモート オブジェクトの CLSID を使用できます。 COSERVERINFO ServerInfo; MULTI_QI mqi[1]; OLECHAR wszHostName[MAXFILE]; LPTSTR pszHost=NULL; memset(&ServerInfo,0,sizeof(ServerInfo)); pszHost =GetUserRequestedHostName(); mbstowcs(wszHostName,pszHost,MAXFILE); ServerInfo.pwszName = wszHostName; mqi[0].pIID = &IID_Iemployee; mqi[0].pItf = NULL; mqi[0].hr = S_OK; // 目的のサーバに employee オブジェクトを作成する hr = CoCreateInstanceEx(CLSID_Employee,NULL, CLSCTX_REMOTE_SERVER,&ServerInfo,1,mqi); 650 PowerBuilder 第 2 8 章 COM/COM+ クライアントの構築 この章について この章では、COM または COM+ サーバ コンポーネントにアクセ スする PowerBuilder クライアントの構築方法について説明しま す。 内容 項目 COM/COM+ クライアントの構築について COM サーバへの接続 COM コンポーネントとのやり取り クライアントからのトランザクション制御 ページ 651 652 653 654 COM/COM+ クライアントの構築について PowerBuilder アプリケーションは、COM サーバのクライアントと して機能できます。COM サーバは、PowerBuilder またはそのほか の COM に準拠したアプリケーション開発ツールを使用して作成 できます。また、リモート コンピュータ上でインプロセス サーバ として、または COM+ 環境でローカルに実行できます。 アプリケーション ウィザードを使用すれば、COM および COM+ クライアントを簡単に構築できます。 クライアント コンピュー タを設定してリモート コ ンポーネントにアクセス アプリケーション テクニック COM コンポーネントがリモート コンピュータ上で動作している 場合、クライアント コンピュータは、そのメソッドに透過的にア クセスできなければなりません。そのためには、クライアント側 にサーバに対応するローカルのプロキシ DLL を用意し、クライア ント コンピュータのレジストリにリモート サーバを識別するエ ントリを登録する必要があります。クライアント コンピュータは、 Windows 2000 または Windows XP 上で動いていなければなりませ ん。 651 COM サーバへの接続 コンポーネントが COM+ にインストールされている場合は、COM+ コ ンポーネント サービス ツールを使用して 、クライアント コンピュー タ 上 に ア プ リ ケ ー シ ョ ン プ ロ キ シ を イ ン ス ト ー ル す る Microsoft Windows インストーラ(MSI)ファイルを作成します。 サーバが COM+ にインストールされていない場合は、クライアント ファイルとプロキシ ファイルをクライアントにコピーし、サーバを代 理プロセスで動作させるように設定する必要があります。詳細につい ては、647 ページの「DCOM での PowerBuilder COM サーバとオブジェ クトの使い方」を参照してください。 レジストリに書き込まれたリモート サーバ名 COM サーバを別のコンピュータに移動した場合には、クライアント上 のレジストリ エントリを更新する必要があります。 COM サーバへの接続 COM サーバ内のコンポーネントに関連付けられたメソッドにアクセ スするために、PowerBuilder クライアントは、コンポーネントのプロ グラム識別子(ProgID)またはクラス識別子(CLSID)を使用して、コ ンポーネントに接続します。 プログラム ID または CLSID、および登録した PowerBuilder COM オブ ジェクトのメソッドを表示するには、PowerBuilder オブジェクト ブラ ウザの OLE タブや OLEVIEW などのツールを使用します。 COM サーバへの接続を確立するには、以下の操作を実行するために必 要な PowerScript 文を実行する必要があります。 1 OLEObject 型の変数を宣言し、Create 文を使用してその変数をイン スタンス化します。 2 オブジェクトの ProgID または CLSID を使用して、オブジェクトに 接続します。 3 接続が確立されたことを確認します。 例 次のスクリプトでは、OLEObject オブジェクト EmpObj をインスタ ンス化し、PowerBuilder COM オブジェクト PBcom.Employee に接続し て、エラーをチェックしています。 OLEObject EmpObj Integer li_rc 652 PowerBuilder 第 28 章 COM/COM+ クライアントの構築 EmpObj = CREATE OLEObject li_rc = EmpObj.ConnectToNewObject("PBcom.employee") IF li_rc < 0 THEN DESTROY EmpObj MessageBox("COM オブジェクトへの接続に失敗 ", & " エラー :" + String(li_rc)) Return END IF COM コンポーネントとのやり取り コンポーネント メ ソッドの呼び出し COM コンポーネントへの接続が確立されると、クライアント アプリ ケーションはコンポーネント メソッドを使用できるようになります。 出力パラメータには REF キーワードを使用する 出力パラメータを持つ COM オブジェクト上のメソッドを呼び出すと きには、REF キーワードを使用しなければなりません。たとえば、 of_add( arg1, arg2, REF sum ) のように指定します。 前の例で作成した EmpObj オブジェクトを使用して、次の例では、 コンポーネント上の 2 つのメソッドを呼び出し、続いてサーバとの接 続を切断し、インスタンスを破棄しています。 例 Long units, time Double avg, ld_retn String ls_retn ld_retn = EmpObj.f_calcdayavg(units, time, REF avg) ls_retn = EmpObj.f_teststring() EmpObj.DisconnectObject() DESTROY EmpObj 結果集合の受け渡し PowerBuilder は、3 つのシステム オブジェクトを提供することによっ て、トランザクション サーバ環境で動作しているコンポーネントから 結果集合を取得したり、トランザクション サーバ コンポーネントとし て動作している PowerBuilder ユーザ オブジェクトから結果集合を返し たりする操作に対処します。これらのシステム オブジェクト(ResultSet、 ResultSets、および ADOResultSet)は、データストア オブジェクトと の間でトランザクション サーバの結果集合の変換を簡単にするため に設計されたものであり、状態情報を含んでいません。 アプリケーション テクニック 653 クライアントからのトランザクション制御 詳細については、629 ページの「結果集合の受け渡し」を参照してく ださい。 実行時エラー処理 OLE オートメーション オブジェクト、COM オブジェクト、または COM+ コンポーネントとして実行されているカスタム クラス ユーザ オブジェクトからの実行時エラー情報は、オブジェクトを保持するコ ンテナに例外として(オートメーション オブジェクトの場合は、例外 または機能エラーとして)レポートされます。PowerBuilder SignalError 関数への呼び出しも、コンテナにレポートされます。PowerBuilder オ ブジェクトによって生成された実行時エラーを処理するには、OLE ク ライアントの ExternalException イベントを記述します。 OLE オブジェクトまたは COM オブジェクトにおける実行時エラー処 理についての詳細は、390 ページの「エラー処理」を参照してください。 クライアントからのトランザクション制御 PowerBuilder クライアントは、OLEObject 型ではなく、OleTxnObject 型 の変数を使用して COM オブジェクトに接続することによって、COM+ サーバ上のトランザクションを明示的に制御できます。 COM+ のインストールが必要 COM+ がクライアント コンピュータにインストールされていないと、 OleTxnObject での ConnectToNewObject 呼び出しは失敗します。 OLEObject オブジェクトから派生した OleTxnObject オブジェクトに は、クライアントがトランザクション制御に参加するための 2 つの関 数(SetComplete と SetAbort)が追加定義されています。クライアント が SetComplete を呼び出すと、そのトランザクションは、トランザク ションの別の参加者が SetAbort を呼び出していなければコミットされ ますが、そうでない場合は失敗します。クライアントが SetAbort を呼 び出すと、トランザクションは常に中断します。 例 次の例では、 ボタンの Clicked イベントによって OleTxnObject 型の 変数を作成し、サーバ上の PowerBuilder COM オブジェクトに接続し、 オブジェクト上のいくつかのメソッドを呼び出しています。すべての メソッドが復帰すると、クライアントは SetComplete を呼び出して、 サーバとの接続を切断します。 654 PowerBuilder 第 28 章 COM/COM+ クライアントの構築 integer li_rc OleTxnObject lotxn_obj lotxn_obj = CREATE OleTxnObject li_rc = lotxn_obj.ConnectToNewObject("pbcom.n_test") IF li_rc <> 0 THEN MessageBox(" 接続が失敗しました ", string(li_rc) ) HALT END IF lotxn_obj.f_dowork() lotxn_obj.f_domorework() lotxn_obj.SetComplete() lotxn_obj.DisconnectObject() サーバの PowerBuilder COM オブジェクトに定義されている f_dowork 関数は、トランザクション コンテキスト サービスのインスタンスを作 成し、その DisableCommit メソッドを呼び出すことによって、次のメ ソッド呼び出しまでの間にトランザクションが早期にコミットされる のを防止します。そして何らかの作業を行った後、その作業が正しく 完了しなかった場合には SetAbort を、正しく完了した場合には、SetComplete を呼び出します。 TransactionServer txninfo_one integer li_rc li_rc = GetContextService( "TransactionServer", txninfo_one ) txninfo_one.DisableCommit() & // 処理を実行し、リターン コードを返す IF li_rc <> 0 THEN txninfo_one.SetAbort() return -1 ELSE txninfo_one.SetComplete() return 1 END IF トランザクション内のすべてのメソッドが SetComplete または EnableCommit を呼び出すと、クライアント上の SetComplete 呼び出し によってトランザクションがコミットされます。 アプリケーション テクニック 655 クライアントからのトランザクション制御 656 PowerBuilder 第 2 9 章 EJB クライアントの構築 この章について この章では、J2EE 準拠のアプリケーション サーバ上で動作する Enterprise JavaBeans コンポーネント用の PowerBuilder クライアン トの構築方法について説明します。この章で説明するオブジェク トの関連情報については、 『PowerBuilder エクステンション リファ レンス』 マニュアルおよびオンライン ヘルプを参照してください。 内容 項目 EJB クライアントの構築について アプリケーションへの pbejbclient110.pbx の追加 EJB プロキシ オブジェクトの生成 Java VM の作成 サーバへの接続 コンポーネント メソッドの呼び出し 例外処理 クライアント管理のトランザクション クライアントのデバッグ ページ 657 659 660 668 671 672 677 679 680 EJB クライアントの構築について PowerBuilder アプリケーションは、J2EE 準拠のアプリケーション サーバ上で実行する EJB 1.1 または 2.0 コンポーネントに対するク ライアントとして動作することが可能です。この機能は、Sybase が 提供する PowerBuilder エクステンション ファイルに依存します。 PowerBuilder エクステンション ファイルは、PowerBuilder Native Interface(PBNI)を使用して開発されたものです。EJB クライアン ト を 作 成 す る た め に PBNI に 関 す る 知 識 は 必 要 あ り ま せ ん。 PowerBuilder エクステンションについての詳細は、 『PowerBuilder エクステンション リファレンス』マニュアルに記載されていて、 また、PBNI についての詳細は、『PowerBuilder ネイティブ インタ フェース プログラマーズ ガイドとリファレンス』マニュアルに記 載されています。 アプリケーション テクニック 657 EJB クライアントの構築について EAServer 用 EJB クライアント EAServer 用の EJB クライアントを開発する場合、この章で説明するテ クニックを使用することができます。また、PowerBuilder 接続オブジェ クトと EAServer プロキシ オブジェクトを使用するクライアントを作 成することもできます。 EJB クライアント エクステンションは Java 対応のラッパーであるた め、より柔軟に EJB と通信できます。たとえば、EJB クライアントは、 EJB プロキシを介して EJB メソッド呼び出しから返された Java クラス を操作できます。 EJB クライアントが存在するコンピュータ上に JRE をインストールす る必要がないので、PowerBuilder 接続オブジェクトはより小さくなり、 配備しやすくなります。また、PowerBuilder 接続オブジェクトを使用 すると、JRE ロードによる遅滞が生じないために、サーバへの接続も 速くなります。 PowerBuilder 接続オブジェクトを使用した EAServer 上で動作する EJB コンポーネント用の EJB クライアント構築についての詳細は、第 25 章 「EAServer クライアントの構築」を参照してください。 pbejbclient110.pbx と pbejbclient110.pbd サーバに接続して EJB コンポーネントと通信するためには、クライア ントは接尾辞 PBX を持つ DLL ファイル、pbejbclient110.pbx に実装さ れているクラスのセットを使用します。この PBX ファイル内のクラス を使用するには、クライアント アプリケーション内のライブラリにク ラスの定義をインポートする必要があります。pbejbclient110.pbd ファ イルをターゲットのライブラリ探索パスに追加することもできます。 このファイルは、PBX ファイルのラッパーとして機能します。 EJB プロキシ オブ ジェクトについて PowerBuilder クライアントは、リモート EJB コンポーネントのメソッ ド呼び出しを EJB コンポーネントのローカル プロキシ オブジェクト に任せます。各 EJB コンポーネントは最小限、クライアント アプリ ケーション内で、ホーム インタフェース用プロキシとリモート インタ フェース用プロキシによって表されます。たとえば、Cart という EJB コンポーネントには、CartHome と Cart の 2 つのプロキシがあります。 それぞれのプロキシには、これらのインタフェースのパブリック メ ソッドのシグネチャのみが含まれます。 さらに、ホーム インタフェースとリモート インタフェースによって使 用される例外と補助クラスに対しても、プロキシが生成されます。詳 細については、660 ページの「EJB プロキシ オブジェクトの生成」を 参照してください。 658 PowerBuilder 第 29 章 EJB クライアントの構築 EJB クライアントを構築するには、以下の手順をすべて実行する必要 があります。 プロセスの概要 1 ワークスペースと PowerScript ターゲットを作成します。 2 pbejbclient110.pbx をアプリケーションに追加します。 3 プロキシ オブジェクトの構築のためのプロジェクトを作成します。 4 プロキシ オブジェクトを生成するためにプロジェクトを作成します。 5 クライアント アプリケーションのユーザ インタフェースを実装 するために必要なウィンドウを作成します。 6 Java VM をインスタンス化します。 7 サーバへの接続を確立し、EJB を検索します。 8 EJB コンポーネントのインスタンスを作成し、クライアントから コンポーネント メソッドを呼び出します。 9 クライアントのテストとデバッグを行います。 アプリケーションへの pbejbclient110.pbx の追加 PBEJBClient クラスを PowerBuilder ターゲットに追加する最も簡単な 方法は、pbejbclient110.pbx PBX ファイル内のオブジェクト ディスクリ プションを PowerBuilder システム ツリー内のライブラリにインポート することです。 PowerBuilder をインストールするときに、Shared\PowerBuilder ディレ ク ト リ に pbejbclient110.pbx と pbejbclient110.pbd フ ァ イ ル が イ ン ス トールされます。EJB クライアント アプリケーションを作成する場合、 pbejbclient110.pbx を別の場所にコピーする必要はありませんが、アプ リケーションの探索パス内のディレクトリに、クライアント実行ファ イルとともにこのファイルを配布する必要があります。 ❖ エクステンション内のディスクリプションをライブラリにインポートするには 1 2 アプリケーション テクニック システム ツリーでエクステンションを使用したいターゲットを展 開し、ライブラリを右クリックして、ポップアップ メニューから [PB エクステンションのインポート]を選択します。 PBX ファイルの位置まで移動し、[開く]をクリックします。 659 EJB プロキシ オブジェクトの生成 PBX 内の各クラスがシステム ツリーに表示されます。そのため、 クラスを展開し、そのプロパティ、イベント、およびメソッドを 表示して、それらをスクリプトに追加するためにドラッグアンド ドロップできます。 pbejbclient110.pbx をインポートすると、システム ツリーには以下のオ ブジェクトが表示されます。 オブジェクト EJBConnection EJBTransaction JavaVM 説明 EJB サーバに接続し、EJB を配置するために使用す る javax.transaction.UserTransaction インタフェースに マップする。EJB クライアントからトランザクショ ンを制御するために使用する Java VM のインスタンスを作成するために使用す る EJB プロキシ オブジェクトの生成 EJB プロキシ オブジェクトを生成するには、EJB クライアント プロキ シ プロジェクトを作成する必要があります。EJB クライアント プロキ シ プロジェクトの作成には、プロジェクト ペインタかウィザードを使 用します。 EJB プロキシ プロジェクトの使い方 EJB クライアント プロキシ プロジェクトを新規に作成するには、新規 作成 ダイアログボックスの[プロジェクト]ページから次のいずれか を選択します。 • [EJB クライアント プロキシ]アイコン • [EJB クライアント プロキシ ウィザード]アイコン [EJB クライアント プ ロキシ]アイコン 660 [EJB クライアント プロキシ]アイコンを選択すると、EJB プロキシ用 のプロジェクト ペインタが開きます。このプロジェクト ペインタを使 用すると、プロジェクトの作成、オプションの指定、およびプロキシ ライブラリの構築ができます。 PowerBuilder 第 29 章 ❖ EJB クライアントの構築 プロジェクト ペインタで EJB クライアント プロキシ プロジェクトを作成す るには 1 新規作成 ダイアログボックスの[プロジェクト]ページで、 [EJB クライアント プロキシ]アイコンをダブルクリックします。 2 EJB を指定するには、 [編集|オブジェクトの選択]を選択し、テ キストボックスに、com.sybase.jaguar.sample.svu.SVULogin や portfolio.MarketMaker など、コンポーネントのリモート インタフェー スの完全修飾名を入力します。 3 [クラスパス]ボックスに、EJB のスタブを含むディレクトリまた は JAR ファイルのパスを入力し、[OK]をクリックします。 スタブ ファイルがディレクトリに格納され、EJB の完全修飾名が packagename.beanname である場合、packagename を含むディレクト リを入力します。 4 プロキシ オブジェクトを格納する PBL を指定するには、[編集| プロパティ]を選択し、ターゲットのライブラリ リスト内のライ ブラリの格納場所を指定します。 生成された各プロキシ名の先頭に追加する接頭辞を任意に指定で きます。接頭辞を追加すると、指定した EJB に関連付けられたプ ロキシの特定が容易になり、クラス名と PowerBuilder 予約語の衝 突を避けることができます。ただし、例外のプロキシ、ストリーム オ ブジェクトのプロキシ、および EJBHome、EJBObject、EJBMetaData、 Handle、HomeHandle のプロキシなど、この EJB 固有でないプロキ シ名には、接頭辞は追加されません。 5 ダイアログボックスを閉じて、 [ファイル|すべて保存]を選択し てプロジェクトを保存します。 新規プロジェクトは、プロキシが生成される EJB コンポーネントを一 覧にし、生成されたプロキシ オブジェクトを格納する出力ライブラリ 名を指定します。 [EJB クライアント プ ロキシ ウィザード] アイコン EJB クライアント プロキシ ウィザードを使用すると、プロジェクトを 容易に作成できます。 ❖ ウィザードを使用して EJB クライアント プロキシ プロジェクトを作成するには 1 新規作成 ダイアログボックスの[プロジェクト]ページで[EJB クライアント プロキシ ウィザード]アイコンをダブルクリック し、ウィザードの最初のページで[次へ]をクリックします。 2 プロジェクト オブジェクトを格納するライブラリを選択し、 [次へ] をクリックします。 アプリケーション テクニック 661 EJB プロキシ オブジェクトの生成 3 プロジェクト名を指定し、必要に応じてプロジェクトの説明を指 定して、[次へ]をクリックします。 4 次に示すように、テキストボックスに、cocoPortfolio.Portfolio など、コンポーネントのリモート インタフェースの完全修飾名を 入力します。 コンポーネントのホーム インタフェース名は、標準の命名規約に 従って自動的に入力されます。必要であれば、ウィザードでこの 名前を変更できます。 5 EJB スタブを格納した JAR ファイル、または EJB スタブ パッケー ジを格納したディレクトリを参照して選択します。 スタブ ファイルがディレクトリに格納され、EJB の完全修飾名が packagename.beanname である場合、packagename を含むディレクト リを入力します。 6 生成された各プロキシ名の先頭に追加する任意の接頭辞を指定 し、[次へ]をクリックします。 接頭辞を追加すると、指定した EJB に関連付けられたプロキシの 特定が容易になり、クラス名と PowerBuilder 予約語の衝突を避け ることができます。ただし、例外のプロキシ、サポートしている クラスのプロキシ、および EJBHome、EJBObject、EJBMetaData、 Handle、HomeHandle のプロキシなど、この EJB 固有でないプロキ シ名には、接頭辞は追加されません。 7 662 既存のライブラリを参照して選択し、 [次へ]をクリックし、 [完了] をクリックします。 PowerBuilder 第 29 章 EJB クライアントの構築 プロキシ オブジェクトが生成され、このライブラリに格納されま す。このライブラリをターゲットのライブラリ リストに追加する 必要があります。 ウィザードを使用してプロジェクトを作成した後、プロジェクト ペイ ンタを使ってプロジェクトの設定を変更できます。 プロキシの作成 EJB プロキシ プロジェクトの作成にウィザードまたはペインタのいず れを使用する場合も、最後にプロキシ オブジェクトを作成します。プ ロキシ オブジェクトを作成するには、ペインタ バーで[配布]アイコ ンをクリックするか、メニュー バーから[デザイン|プロジェクトの 配布]を選択します。 プロキシの生成には javap.exe が必要 PowerBuilder は、javap.exe ユーティリティを使ってプロキシ オブジェ クトを生成します。この実行ファイルは、システム パスに置く必要が あります。デフォルトでは、EJB クライアントの開発に PowerBuilder とともにインストールされる Sun JDK 1.4 を使用します。Java VM に必 要なパスとクラスパスは、現在のセッションで使用するパスとクラス パスに自動的に追加されます。 別の JDK を使用する場合は、[ツール|システム オプション]を選択 し、システム オプション ダイアログボックスの[Java]ページで[JDK ロケーションの設定]をクリックします。WebSphere を使用する場合 は、IBM JDK のパスを使用します。 EJB のホーム インタフェースとリモート インタフェースのプロキシ に加え、EJB が参照するすべての Java クラス、先祖クラス、EJB とそ のサポートするクラスから送出されるすべての例外、および以下のイ ンタフェースに対してもプロキシが生成されます。 オブジェクト EJBHome EJBMetaData EJBObject アプリケーション テクニック 説明 すべての EJB ホーム インタフェースの基本クラスであ る、javax.ejb.EJBHome インタフェースのプロキシ javax.ejb.EJBMetaData インタフェースのプロキシ。 EJBMetaData を使用すると、クライアントは、EJB の ホーム インタフェース、EJB のホーム インタフェース とリモート インタフェースのクラス オブジェクト、お よびエンティティ Bean の主キー クラスを取得し、Bean がセッション オブジェクトまたはステートレス セッ ション オブジェクトかどうかが判断可能になる すべての EJB リモート インタフェースの基本クラスで ある、javax.ejb.EJBObject インタフェースのプロキシ 663 EJB プロキシ オブジェクトの生成 オブジェクト Handle HomeHandle 説明 javax.ejb.Handle インタフェースのプロキシ。EJB への堅 牢で永続的な参照を提供する javax.ejb.HomeHandle インタフェースのプロキシ。ホーム オブジェクトへの堅牢で永続的な参照を提供する これらのインタフェースについての詳細は、javax.ejb package のサイト http://java.sun.com/j2ee/sdk_1.3/techdocs/api/index.html に掲載のマニュアル を参照してください。 プロジェクトは、Java クラスのプロキシ名へのマッピングを格納する 構造体も生成します。この構造体は内部的に使用されるものなので、 変更しないでください。 ejb2pb110 ツールの使い方 プロキシの生成には、ejb2pb110 コマンドライン ツールを使用する方法 もあります。このツールを使用した場合、以下が生成されます。 • 指定した EJB のホーム インタフェースとリモート インタフェー スのプロキシ、および EJB が依存するクラスのプロキシ(.srx ファ イル) • ejbname_ejb_pb_mapping.srs という名前の PowerBuilder 構造体オブ ジェクト。この場合、ejbname は EJB 名。この構造体は、Java クラ ス名と PowerBuilder プロキシ名との間のマッピング テーブルをホ ストする • ejbproxies.txt という名前のテキスト ファイル。エラーが発生した 場合は、ejbproxies.err という名前のテキスト ファイル これらのファイルは、コマンドの呼び出し元のディレクトリ内に生成 されます。構文は次のとおりです。 ejb2pb110 [ -classpath pathlist ] EJBName [EJBHomeName][ prefix ] D:\Program Files のように、pathlist 引数にスペースが含まれる場合は、 pathlist を引用符で囲む必要があります。EJBName は、完全修飾リモー ト インタフェース クラス名です。標準の命名規約に従ったホーム イ ンタフェース名を使用する場合、完全修飾ホーム インタフェース名の 引数 EJBHomeName はオプションです。オプションの prefix を指定す ると、生成されたプロキシ名の先頭に接頭辞が追加されます。 664 PowerBuilder 第 29 章 EJB クライアントの構築 たとえば、次のステートメントは、EAServer 上の cocoPortfolio パッケー ジ内の Portfolio クラスのプロキシを生成します。Portfolio クラスの ホーム インタフェースとリモート インタフェースのプロキシには、接 頭辞として pf_ が追加され、生成されたファイルは D:\work\proxies ディレクトリに書き込まれます。 cd D:\work\proxies ejb2pb110 -classpath "D:\Program Files\Sybase\EAServer\ html\classes" cocoPortfolio.Portfolio pf_ EJB のホーム クラスとリモート クラス、およびそれに従属するクラス は、指定したクラス パスに置く必要があります。 プロキシを生成した後に、生成したプロキシをターゲットにインポー トするには、クライアントを含むライブラリを選択し、ポップアップ メニューから[インポート]を選び、表示されたダイアログボックス から .srx ファイルを選びます。.srx ファイルをインポートする順序に は注意が必要です。ほかのクラスに従属するプロキシは、その従属す るクラスのプロキシをインポートした後でないとインポートできませ ん。 生成されたプロキシの表示方法 生成されたプロキシはシステム ツリーに表示されます。プロキシ ノー ドを展開すると、EJB コンポーネントのホーム インタフェースとリ モート インタフェースのメソッドのシグネチャ、およびプロキシを生 成したほかのすべてのオブジェクトのメソッドのシグネチャが表示さ れます。 アプリケーション テクニック 665 EJB プロキシ オブジェクトの生成 予約語との衝突 666 コンポーネントのメソッド名が PowerBuilder の予約語と衝突する場 合、メソッドを PowerBuilder にインポートできるように、プロキシ内 のメソッド名に文字列 _j が追加されます。たとえば、Java Iterator クラ スには Next メソッドがあり、このメソッドは、PowerBuilder の予約語 NEXT と衝突します。プロシキ内で、このメソッドには next_j という 名前が付けられます。 PowerBuilder 第 29 章 EJB クライアントの構築 データ型マッピング EJB プロキシ ジェネレータは、次の表に示すように Java と PowerBuilder の間でデータ型をマップします。 Java のデータ型 PowerBuilder のデータ型 short Integer int Long long LongLong float Real double Double byte Int char(16 ビット、符号なし) Char java.lang.String String boolean Boolean java.util.Date Datetime プリミティブ型の配列 パラメータ : プリミティブ型の配列 戻り値 :Any パラメータ :String または DateTime の配列 戻り値 :Any java.lang.String または java.util.Date オブジェクトの配列 配列の配列 Java クラスの引数または戻り値 その他 Any Java クラスの PowerBuilder プロキシ Any double 型の精度の相 違 PowerBuilder の double 型は 15 桁の精度(1.79769313486231E+308)を 持ち、Java の double 型は 17 桁の精度(1.7976931348623157e+308)を 持ちます。EJB クライアント アプリケーションの場合、double 型の精 度は、PowerBuilder の範囲(2.2250738585073E-308 ~ 1.79769313486231E+308)に制限されます。 配列の配列 PowerBuilder は、Java とは異なり、可変長多次元配列をサポートしてい ません。Java メソッドがパラメータとして配列の配列を受け取る場合、 これに対応する PowerBuilder プロキシ メソッドは Any 型のパラメータ を受け取ります。PowerBuilder 内でメソッドを呼び出すには、Java 配 列と同じ次元で PowerBuilder 配列を宣言し、その配列をパラメータと して渡します。 アプリケーション テクニック 667 Java VM の作成 Java VM の作成 EJB コンポーネントを呼び出す場合、事前に JavaVM クラスの CreateJavaVM メソッドを使用して Java VM を作成する必要があります。 最初の引数は、Java VM によって使用されるクラスパスの先頭に追加 するクラスパスを指定する String 型です。 Java VM がすでにロードされている場合 Java VM がすでに実行されている場合、クラスパス引数は無視されま す。 createJavaVM の第 2 引数は、デバッグ情報をテキスト ファイルに書き 出すかどうかを指定する Boolean 型の引数です。680 ページの「クライ アントのデバッグ」を参照してください。 これ以外に、JavaVM クラスには、Java VM の作成に使用可能な以下の メソッドがあります。 • CreateJavaInstance メソッド。このメソッドは、プロキシ名から Java オブジェクトのインスタンスを作成する • IsJavaVMLoaded メソッド。このメソッドは、Java VM がすでにロー ドされているかどうかを判断する。Java VM がすでにロードされ ているかどうかによって、アプリケーションの一部の機能を有効 または無効にする場合には、CreateJavaVM を呼び出す前にこのメ ソッドを使用する。これにより、CreateJavaVM に渡されるクラス パス引数は無視される • GetJavaVMVersion メソッド。このメソッドは、実行中の Java VM の バージョンを判断する • GetJavaClasspath メソッド。このメソッドは、Java VM のランタイ ム クラスパスを判断する CreateJavaVM を使用して作成する JavaVM は、クライアント アプリ ケーションのグローバル変数またはインスタンス変数でなければなら ず、明示的に破棄されないようにします。 開発環境における Java VM クラスパス PowerBuilder が Java VM を起動すると、Java VM は内部パスとクラス パス情報を使って、必要な Java クラスが常に使用できる状態にします。 開発環境では、JVM が実行されているかどうか、実行されている場合 は JVM がどのクラスパスを使用しているかをシステム オプション ダ イアログボックスの[Java]ページで確認できます。クラスパスは、以 下のパスを結合して作成されます。 668 PowerBuilder 第 29 章 ランタイム Java VM クラスパス EJB クライアントの構築 • Java VM の起動時にプログラムによって追加されるクラスパス。た とえば、CreateJavaVM メソッドに渡すクラスパス • PowerBuilder ランタイム スタティック レジストリ クラスパス。こ のパスは、pbjvm110.dll に組み込まれる。このパスには、実行時に EJB クライアント、 および Java VM を使用するそのほかの PowerBuilder 機能に必要なクラスが含まれる • PowerBuilder システム クラスパス。このパスは、PowerBuilder のイ ンストール時にインストールされる Windows レジストリ キー内に 保存される。このパスには、設計時に JSP ターゲットおよび JDBC 接続などの Java 関連の PowerBuilder 機能に必要なクラスが含まれ る • PowerBuilder ユーザ クラスパス。このパスは、システム オプション ダイアログボックスの[Java]ページで指定するパス • システムの CLASSPATH 環境変数 • 現行ディレクトリ 実行時に、GetJavaClasspath メソッドを使用すると、Java VM が使用し ているクラスパスを判断できます。Java VM は、実行時に以下のクラ スパスを使用します。 • Java VM の起動時にプログラムによって追加されるクラスパス • PowerBuilder ランタイム スタティック レジストリ クラスパス • システムの CLASSPATH 環境変数 • 現行ディレクトリ 実行時の Java クラスパスについての詳細は、879 ページの「Java サポー ト」を参照してください。 サーバが必要とするク ラス クラスパスには、EAServer 4.2 用の EJB クライアントが必要とするク ラスが含まれます。別の J2EE サーバを使用する場合、アプリケーショ ン サーバが必要とするクラスをシステムの CLASSPATH にさらに追加 する必要があります。たとえば、次のようになります。 • WebLogic の場合、weblogic.jar。このファイルは、サーバ上の wlserver6.1\lib または weblogic700\server\lib にインストールされる • WebSphere の場合、JAR ファイルが、サーバ上の websphere\appserver\lib にインストールされる クライアント上での各アプリケーション サーバに対して必要なファ イルについての詳細は、サーバのマニュアルを参照してください。 アプリケーション テクニック 669 Java VM の作成 例 この例では、EAServer インストール内の html\classes フォルダをクラ スパスとして指定する Java VM のインスタンスの作成を示します。 // グローバル変数 javavm g_jvm、 // boolean gb_jvm_started boolean isdebug string classpath if NOT gb_jvm_started then //JAVAVM を作成します。 g_jvm = create javavm // EJB の Java パッケージは、 // EAServer html/classes フォルダにあります。 classpath = & "D:\Program Files\Sybase\EAServer\html\classes;" isdebug = true choose case g_jvm.createJavaVM(classpath, isdebug) case 0 gb_jvm_started = true case -1 MessageBox(" エラー ", "Java VM のロードに失敗 ") case -2 MessageBox(" エラー ", "EJBLocator のロードに失敗 ") end choose end if 使用する Java VM バージョンとクラスパスのレコードを作成するに は、上記の例に次のコードを追加します。 integer li_FileNum string ls_classpath, ls_version, ls_string li_FileNum = FileOpen("C:\temp\PBJavaVM.log", & LineMode!, Write!, LockWrite!, Append!) ls_classpath = i_jvm.getjavaclasspath() ls_version = i_jvm.getjavavmversion() ls_string = String(Today()) + " " + String(Now()) ls_string += " Java VM Version:" + ls_version ls_string += " ~r~n" + ls_classpath + "~r~n" FileWrite(li_FileNum, ls_string) FileClose(li_filenum) 670 PowerBuilder 第 29 章 EJB クライアントの構築 サーバへの接続 EJB サーバに接続し EJB を検索するには、EJBConnection クラスを使用 します。EJBConnection クラスには、次の 4 つのメソッドがあります。 ConnectToServer、DisconnectServer、Lookup、および GetEJBTransaction で す。 サーバへの接続を確立するには、以下の操作を行うために必要な PowerScript ステートメントを実行する必要があります。 1 EJBConnection クラスのインスタンスを宣言します。 2 EJBConnection オブジェクトのプロパティを設定します。 3 CREATE 文を使用して、EJBConnection オブジェクトをインスタン ス化します。 ConnectToServer メソッドを呼び出して、サーバへの接続を確立し 4 ます。 エラーの有無をチェックします。 5 クラスパス要件 アプリケーション サーバに接続し、EJB オブジェクトを作成するには、 システムの CLASSPATH 環境変数または createJavaVM の classpath 引数 に、EJB スタブ ファイルの格納場所(ディレクトリまたは JAR ファイ ル)を含める必要があります。また、使用するアプリケーション サー バが、クライアントコンピュータ上でクラスまたは JAR ファイルを利 用できるようにし、それらをクラスパスに追加することが必要な場合 もあります。詳細については、668 ページの「開発環境における Java VM クラスパス」を参照してください。 初期コンテキストの設 定 初期コンテキストの設定に使用される文字列は、EJB サーバに依存し ます。次の表に、サンプル文字列値を示します。詳細については、サー バのマニュアルを参照してください。 サーバ EAServer WebLogic WebSphere 例 INITIAL_CONTEXT_FACTORY 値 com.sybase.ejb.InitialContextFactory weblogic.jndi.WLInitialContextFactory com.ibm.websphere.naming.WsnInitialContextFactory 次のスクリプトは、EAServer への接続を示しています。このスクリプ トでは、接続プロパティを設定して、初期コンテキストの作成、サー バのホスト名とポート番号の識別、ユーザ ID とパスワードの識別を行 います。 アプリケーション テクニック 671 コンポーネント メソッドの呼び出し IIOPS IIOPS 接続は、現時点ではサポートされていません。 続いて、このスクリプトでは、EJBConnection オブジェクトのインスタ ンスを作成し、ConnectToServer メソッドを呼び出してサーバへの接続 を確立し、エラーをチェックします。 ejbconnection conn string properties[] properties[1]="javax.naming.Context.INITIAL_CONTEXT_FACTORY= com.sybase.ejb.InitialContextFactory" properties[2]="javax.naming.Context.PROVIDER_URL=iiop://myejbserver:9000" properties[3]="javax.naming.Context.SECURITY_PRINCIPAL=admin" properties[4]="javax.naming.Context.SECURITY_CREDENTIALS=" conn = CREATE ejbconnection TRY conn.connectToServer(properties) CATCH (exception e) MessageBox(" 例外 ", e.getmessage()) END TRY サーバとの接続解除 EJB サーバを使用してアプリケーションを終了したら、サーバとの接続を 解除する必要があります。 conn.disconnectserver() コンポーネント メソッドの呼び出し サーバへの接続が確立され、プロキシ オブジェクトかオブジェクトが 作成された後ではじめて、クライアント アプリケーションは EJB コン ポーネントを使用できます。EJB コンポーネント メソッドを呼び出す には、以下の操作に必要な PowerScript ステートメントを実行する必要 があります。 1 672 EJBConnection の lookup メソッドを使用して、コンポーネントの ホーム インタフェースにアクセスします。 PowerBuilder 第 29 章 EJB クライアントの構築 2 ホーム インタフェース上で create または findByPrimaryKey メソッド を呼び出して、コンポーネントのインスタンスを作成または検索 し、コンポーネントのリモート インタフェースへの参照を取得し ます。 3 リモート インタフェースでビジネス メソッドを呼び出します。 このプロシージャは、pbejbclient110.jar ファイルを使用します。この ファイルは、設計時および実行時に pbjvm110.dll によって自動的に Java VM クラスパスに追加されます。 lookup メソッドの使 い方 lookup メソッドは、ホーム インタフェースのプロキシ名、EJB コンポー ネントの JNDI 名、 EJB コンポーネントの完全修飾ホーム インタフェー ス名の 3 つの文字列引数を受け取ります。 ホーム インタフェース名は、EJB ホーム インタフェースの完全修飾ク ラス名です。たとえば、クラスの Java ネーミング コンテキストからの 相対格納場所が ejbsample である場合、ホーム インタフェース名は ejbsample.HelloEJBHome になります。 次の例では、WebLogic 上の HelloEJB に対する、lookup メソッドの呼び 出しを示します。 HelloEJBHome homeobj homeobj = conn.lookup("HelloEJBHome", "ejbsample.HelloEJB", "ejbsample.HelloEJBHome") Lookup の大文字と小文字の区別 EJB サーバの Lookup では大文字と小文字が区別されます。lookup メ ソッドの引数に指定する文字列の大文字と小文字は、サーバの大文字 と小文字に一致させる必要があります。 EJB のインスタンス の作成や検索 セッション Bean は、クライアントのリクエストに応答して作成されま す。クライアントは、通常の場合、そのクライアント セッションの持 続中はセッション Bean を排他的に使用します。エンティティ Bean は、 データベースに保存される永続情報を表します。クライアントは、ほ かのクライアントと同時にエンティティ Bean を使用します。エンティ ティ Bean は、クライアントの有効期限が終了しても持続するため、エ ンティティ Bean のインスタンスが存在する場合は主キーのクラス名 を使用してこれを検索し、エンティティ Bean のインスタンスが存在し ない場合は新規に作成する必要があります。 アプリケーション テクニック 673 コンポーネント メソッドの呼び出し セッション Bean の場合、プロキシ オブジェクトの create メソッドを使用 して、 EJB のインスタンスを作成します。 create メソッドは、 CreateException と RemoteException を送出します。homeobj 内のホーム インタフェース への参照を取得していることを前提とした場合、すべての EJB サーバ では同じ方法で create が使用されます。 HelloEJB beanobj try beanobj = homeobj.create() catch (remoteexception re) MessageBox(" リモート例外 ", re.getmessage()) catch (createexception ce) MessageBox(" 作成例外 ", ce.getmessage()) end try エンティティ Bean の場合、主キーを提供します。FindByPrimaryKey メ ソッドは、FinderException と RemoteException を送出します。この例で は、キーは関数に引数として渡す特定の顧客 ID です。 try beanobj = homeobj.findByPrimaryKey(customerID) catch (remoteexception re) MessageBox(" リモート例外 ", re.getmessage()) catch (finderexception fe) MessageBox(" 検索例外 ", fe.getmessage()) end try EJB コンポーネント メソッドの呼び出し Bean のインスタンスの作成または検索が完了したら、そのメソッドを 呼び出すことができます。たとえば、次のようになります。 string msg msg = beanobj.displaymessage() Java クラスのインス タンスの作成 Bean に引数として Java クラスを受け取るメソッドがある場合、JavaVM オブジェクトの CreateJavaInstance メソッドを使用して Java クラスのイ ンスタンスを作成します。たとえば、findByPrimaryKey メソッドへの呼び 出し内の主キーが Java クラスである場合は、CreateJavaInstance メソッド を使用してそのクラスを作成し、PowerBuilder プロキシを使用してそ れと通信します。 この例では、create メソッドは Java の Integer 型のクラス引数を受け取 り ま す。PowerBuilder は java_integer と い う プ ロ キ シ を 作 成 し ま す (PowerBuilder integer 型との衝突を避けるために、接頭辞 java_ が必要 です)。CreateJavaInstance への呼び出しがその変数の値を設定し、EJB create メソッドを呼び出せるようにします。 CustomerRemoteHome homeobj CustomerRemote beanobj 674 PowerBuilder 第 29 章 EJB クライアントの構築 java_integer jint_a try homeobj = conn.lookup("CustomerRemoteHome", & "custpkg/Customer", "custpkg.CustomerRemoteHome" ) catch (Exception e) MessageBox( "Lookup 例外 ", e.getMessage() ) return end try try g_jvm.createJavaInstance(jint_a, "java_integer") jint_a.java_integer("8") beanobj = homeobj.create( jint_a, sle_name.text ) catch (RemoteException re) MessageBox(" リモート例外 ", re.getmessage()) return catch (CreateException ce) MessageBox(" 例外作成 ", ce.getmessage()) return catch (Throwable t) MessageBox(" その他例外 ", e.getmessage()) end try MessageBox( "Info", & " このレコードはデータベースの中に " & + "~r~n 正常に保存されました。" ) 戻り値のダウンキャス ト Java コードから、Java プログラミングで使用するためにダウンキャス トが必要な共通 Java オブジェクトが返されると、Java メソッドは常に Java.lang.Object として戻り値を設定します。PowerBuilder EJB クライア ント プロキシでは、java.lang.Object は any データ型にマップされます。 実行時、PowerBuilder は正しい Java オブジェクトを取得し、生成され たマッピング構造体にインデックスを付けて PowerBuilder プロキシ名 を取得します。any 値は、このプロキシ オブジェクトとして設定され ます。返された Java オブジェクトが PowerBuilder 標準データ型にマッ プ可能な場合は、any 値が PowerBuilder 標準データ型として設定されま す。 リモート インタフェースに次のメソッドが含まれるとします。 java.lang.Object account::getPrimaryKey() また、ホーム インタフェースは次のメソッドを含みます。 account accounthome::findByPrimaryKey(java.lang.String) アプリケーション テクニック 675 コンポーネント メソッドの呼び出し 戻り値 java.lang.Object は、実行時に java.lang.String となります。 PowerBuilder は戻り値を PowerBuilder の string データ型に自動的にダ ウンキャストします。 any nid try account beanobj homeobj = conn.lookup("AccountHome", & ejb20-containerManaged-AccountHome, & examples.ejb20.basic.containerManaged.AccountHome) beanobj = homeobj.create("101", 0, "savings") nid = beanobj.getPrimaryKey() accounts = homeobj.findByPrimaryKey(string(nid)) catch (exception e) MessageBox(" 例外 ", e.getmessage()) end try 動的キャスティング EJB メソッドへの呼び出しから返された Java オブジェクトが、必要な メソッドを提供しないプロキシで表される可能性のあるケースが 2 つ 考えられます。 • EJB メソッドの呼び出しから返される Java オブジェクトのクラス が動的に生成される場合、PowerBuilder は Java クラスによって実 装される最初のインタフェースのプロキシを使用する • someclass を実際に返す EJB メソッドのプロトタイプは、someclass が拡張または実装するクラスを返すように定義できる。たとえば、 実際に java.util.ArrayList 型のオブジェクトを返すメソッドは、 java.util.Collection を返すように定義できる。java.util.ArrayList は、 java.util.AbstractList から継承され、この java.util.AbstractList は、 java.util.AbstractCollection から継承され、この java.util.AbstractCollection が、java.util.Collection を実装する。この場合、PowerBuilder は、 java.util.Collection のプロキシを使用する DynamicCast メソッドを使用すると、返されたプロキシ オブジェクト を、必要なインタフェースのプロキシにキャストするか、実行時に返 されるオブジェクトの実際のクラスのプロキシにキャストし、そのオ ブジェクトのメソッドを使用可能にできます。 オブジェクトの実際のクラスを取得するには、GetActualClass メソッド を使用します。また、DynamicCast メソッドは、Java クラスの直接の親 を返す GetSuperClass メソッドや、クラスによって実装されるインタ フェース リストを文字列配列に書き込む GetInterfaces メソッドととも に使用できます。 たとえば、次のようなクラスがある場合、 676 PowerBuilder 第 29 章 EJB クライアントの構築 public class java.util.LinkedList extends java.util.AbstractSequentialList implements java.util.List, java.lang.Cloneable, java.io.Serializable GetActualClass は java.util.LinkedList を返し、GetSuperClass は java.util.AbstractSequentialList を返し、GetInterfaces は 3 を返し、 java.util.List、java.lang.Cloneable、および java.io.Serializable の 3 つの文字 列を、参照される文字列配列に書き込みます。 Java コレクション ク ラス EJB プロキシの生成では、Enumeration、Iterator、Vector などの Java 共 通コレクション クラスが生成されます。PowerBuilder は、これらのコ レクション クラスを、Java クライアントと同じように操作できます。 たとえば、ホーム インタフェースに戻り値 java.util.Enumeration を持つ 次のメソッドが含まれているとします。 Enumeration accounthome::findNullAccounts () 次のコードは、PowerBuilder EJB クライアントが PowerBuilder プロキ シを介して Enumeration クラスを操作する方法を示しています。 Enumeration enum try enum = homeobj.findNullAccounts() if (not enum.hasMoreElements()) then msg = " アカウントは、NULL アカウント型では見つかりません。" end if catch (exception e) MessageBox(" 例外 ", e.getmessage()) end try 例外処理 EJB コンポーネントのメソッドの実行時に発生したエラーは、例外プ ロキシにマップされ、呼び出し側のスクリプトに送出されます。また、 サーバへの接続に失敗したり、コンポーネントが見つけられなかった り作成できなかったりした場合も、pbejbclient110.pbx 内のすべてのク ラスのメソッドは例外を送出します。 EJB プロキシ プロジェクトを構築すると、ホーム インタフェースとリ モート インタフェースのプロキシ、EJB によって参照される Java クラ スのプロキシ、先祖クラスのプロキシ、および EJB とそのサポートす るクラスによって送出される可能性のある例外のプロキシが生成され ます。次の例外プロキシは、システム ツリー内に表示される例外プロ キシの一部です。 アプリケーション テクニック 677 例外処理 プロキシ名 createexception ejbexception finderexception remoteexception removeexception 例外の捕捉 Java オブジェクト名 javax.ejb.CreateException javax.ejb.EJBException javax.ejb.FinderException java.rmi.RemoteException javax.ejb.RemoveException クライアント アプリケーションは、さまざまな方法で通信エラーを処 理できます。たとえば、クライアントがサーバに接続し、オブジェク トのメソッドを呼び出そうとしたのにそのオブジェクトが存在しな かった場合は、サーバとの接続を解除し、別のサーバに接続して操作 を再試行する方法があります。あるいは、クライアントがユーザにメッ セージを表示して、次に起こることを制御する機会をユーザに与える 方法もあります。 クライアントが操作の再開のために新しいサーバに接続している場 合、エラー発生時には、新しいサーバ上でリモート オブジェクトをイ ンスタンス化してから、リモート オブジェクトのメソッドを呼び出す 必要があります。 次の例では、特定の例外の発生時に、スクリプトはメッセージ ボック スを表示するだけです。 //char getChar() 関数が RemoteException を送出します。 try conn.connectToServer(properties) mappinghome = conn.lookup("pbEjbMappingHome", "pbEjbTest/pbEjbMappingBeanSL", "pbejb.pbEjbMappingHome") mapping = mappinghome.create() ret = mapping.getChar() messagebox("EJB からの文字列 ", ret) catch (remoteexception re) messagebox(" リモート例外 ", re.GetMessage()) catch (createexception ce) messagebox(" 作成例外 ", ce.GetMessage()) end try 処理されない例外 678 例外ハンドラがない場合、または既存の例外ハンドラがその例外を処 理しない場合、アプリケーション オブジェクトの SystemError イベン トが実行されます。SystemError イベントにスクリプトが記述されてい ない場合は、アプリケーション エラーが起きて、アプリケーションは 終了します。 PowerBuilder 第 29 章 EJB クライアントの構築 クライアント管理のトランザクション EJB クライアント アプリケーションは、EJBTransaction オブジェクト を使用してサーバ上のトランザクションを制御します。このオブジェ クトには、クライアントにトランザクションを開始、コミット、また はロールバックさせるメソッドがあります。また、クライアントはト ランザクションの状態を取得したり、そのタイムアウト値を変更した り、コミットできないようにトランザクションを変更したりすること もできます。 EJBTransaction メソッドは、javax.transaction.UserTransaction インタ フェースのメソッドに直接マップします。 javax.transaction.UserTransaction インタフェースについての詳細は、Sun Java Web のサイト http://java.sun.com/products/jta を参照してください。 トランザクションの開 始と終了 クライアントは、EJBConnection クラスの getEJBTransaction メソッドを 呼び出して、EJBTransaction クラスのメソッドへのアクセスを取得でき ます。 ejbconnection conn ejbtransaction trans string properties[] conn = create ejbconnection TRY conn.connectToServer(properties) trans = conn.getEJBTransaction() CATCH (exception e) messagebox(" 例外 ", e.getmessage()) END TRY EJBTransaction のインスタンスを正常に取得した場合、その begin メソッ ドを使ってトランザクションを開始し、その commit メソッドまたは rollback メソッドを使用してトランザクションを終了します。 TRY // トランザクションを開始します。 trans.begin() // コンポーネントを作成し、トランザクション内で実行する // メソッドを呼び出します。 ... // トランザクションをコミットします。 trans.commit(); CATCH (exception e) messagebox(" 例外 ", e1.getmessage()) trans.rollback() END TRY アプリケーション テクニック 679 クライアントのデバッグ トランザクションに関 する情報の取得 GetStatus は、トランザクションがアクティブか、ロールバックのマー クが付いているか、prepare フェーズにあるか commit フェーズにある か、またはコミット済みかロールバック済みかを示す Integer 型の値を 返します。 トランザクションのタ イムアウト時間の設定 呼び出し元スレッドで、トランザクションをロールバックするタイム アウト時間を指定できます。次の例では、タイムアウト時間を 3 分 (180 秒)に設定しています。 trans.SetTimeout(180) trans.Begin() クライアントのデバッグ JavaVM クラスの createJavaVM メソッドは、第 2 引数として Boolean 型 の値を受け取ります。この第 2 引数が Ture の場合、クラスのロードな どの実行情報はアプリケーションが保存されているディレクトリの vm.out ファイルに記録されます。 // グローバル変数 :JavaVM g_jvm string classpath boolean isdebug classpath = "d:\tests\ejbsample;" isdebug = true g_jvm.createJavaVM(classpath, isdebug) 680 PowerBuilder 第 7 部 Web アプリケーションの開発 第 7 部では、PowerBuilder で Web アプリケーションを 開発するためのツールとテクニックについて説明します。 第 3 0 章 PowerBuilder での Web アプリ ケーション開発 この章について この章では、PowerBuidler での Web アプリケーション開発に使え る方法について概要を説明します。 内容 項目 Web アプリケーションの作成 .NET Web フォーム アプリケーションとコンポーネント Web サービス JSP ターゲット Web データウィンドウ データウィンドウ Web コントロール ActiveX データウィンドウ プラグイン PowerBuilder ウィンドウ プラグイン PowerBuilder ウィンドウ ActiveX ページ 683 684 684 685 685 687 687 688 689 Web アプリケーションの作成 PowerBuilder には、Web アプリケーション作成のためのいくつか のツールが用意されています。この節では、これらのツールの概 要を説明し、詳細情報の参照場所を示します。 Appeon for PowerBuilder Appeon for PowerBuilder は、既存の PowerBuilder クライアント / サーバ アプリケーションを Web に配布する製品です。詳細につ いては、アシスト のサイト http://www.ashisuto.co.jp/prod/appeon/index.html を参照してください。 アプリケーション テクニック 683 .NET Web フォーム アプリケーションとコンポーネント .NET Web フォーム アプリケーションとコンポーネント PowerBuilder .NET Web フォーム ソリューションは、ASP.NET 技術を 採用しています。それは 3 階層アーキテクチャであり、フロント エン ドとしてブラウザ クライアントを持ち、中間層として IIS サーバ上の PowerBuilder コンポーネントを使用します。データベース層に変更は ありません。 既存のアプリケーションをクライアント サーバ アーキテクチャから 3 階層 Web アーキテクチャへ移す場合、一般的には、アプリケーション コードの変更に多大な労力が必要である一方、Web 環境の制約による 各種の機能制限を許容することが求められます。PowerBuilder .NET Web フォーム ソリューションは、既存のクライアント サーバ アプリ ケーションの Web への配布を非常に簡単に行うこと、新しい Web アプ リケーションを開発するために PowerBuilder のスキルを使用できるよ うにすることを目的としています。 PowerBuilder には、PowerBuilder 非ビジュアル オブジェクトから .NET アセンブリと .NET Web サービス アプリケーションを作成するための ターゲットが含まれています。 詳細については、 『アプリケーションとコンポーネントの .NET への配 布』マニュアルを参照してください。 Web サービス Web サービスは、インターネット テクノロジを活用して分散ソフト ウェア コンポーネントが自動で相互にやりとりするサービスと大ま かに定義されます。そうしたソフトウェア コンポーネントを使用する と、株式市況の取得、インターネットでのカタログの在庫検索、航空 会社とレンタカーの予約サービスの統合などのビジネス ロジックを 実行できます。アプリケーション用のコンポーネントを作成しなくて も、インターネット経由で既存のコンポーネントを使用できます。 PowerBuilder アプリケーションは、インターネット経由でアクセスさ れる Web サービスを利用するクライアントとして機能できます。 SOAP と WSDL を利用すると、1 つのエンティティとしてリモートで 発行された関数の集まりを PowerBuilder アプリケーションに含めるこ とができます。Web サービスは、アプリケーションまたはほかの Web サービスから送信されたリクエストを受信して応答します。JSP ター ゲットで Web サービスを使用することもできます。 684 PowerBuilder 第 30 章 PowerBuilder での Web アプリケーション開発 Web サービスについての詳細は、第 31 章「Web サービス クライアン トの構築」および『JSP ターゲットでの作業』マニュアルを参照してく ださい。 JSP ターゲット JavaServer Pages(JSP)テクノロジを利用すれば、迅速かつ容易な方法 で静的コンテンツと動的コンテンツを持つ Web ページを作成できま す。JSP は、通常 HTML または XML での静的マークアップ、および スクリプト形式の Java コンテンツまたは Java コンポーネントの呼び 出し、あるいはその両方を含むテキストベースの文書です。JSP は Java サーブレット API を拡張したもので、すべての Java API とコンポーネ ントにアクセスできます。 Web ベースのアプリケーションにおいて数多くの方法で JSP を使用で きます。一般に JSP は、J2EE アプリケーション モデルの一部として中 間層の Web サーバで実行し、クライアントからの HTTP リクエストに 応答して、トランザクション サーバの Enterprise JavaBeans(EJB)コ ンポーネントのビジネス メソッドを呼び出します。 PowerBuilder を使用して作成された JSP ページは、JavaServer Pages 仕 様のバージョン 1.2、Java Servlet 仕様のバージョン 2.3、および JDK 1.3 以降をサポートします。PowerBuilder では、JSP 1.2 の形式を使用する カスタム タグ ライブラリもサポートしています。JSP ターゲットを Web アプリケーションとして EAServer、Apache Tomcat、またはコマン ド行配布機能を設定できる任意の JSP 1.2 サーバに配布できます。 JSP ターゲットについての詳細は、『JSP ターゲットでの作業』マニュ アルを参照してください。 Web データウィンドウ Web データウィンドウは、Web アプリケーションのシンクライアント データウィンドウの実装です。Web データウィンドウは、クライアン ト上で PowerBuilder DLL を必要とせずに、PowerBuilder データウィン ドウのデータ操作、提示、およびスクリプト作成機能の大部分を提供 します。 アプリケーション テクニック 685 Web データウィンドウ Web データウィンドウは、以下のような、個別のコンピュータ上で実 行できるいくつかのソフトウェア コンポーネントのサービスを利用 します。 • アプリケーション サーバかトランザクション サーバで実行され る Web データウィンドウ サーバ コンポーネント • 動的ページ サーバ • Web サーバ • Web ブラウザ • データベース サーバ コンポーネントは非ビジュアル ユーザ オブジェクトであり、 データストアを使用して取得と更新の処理を行い、HTML を生成しま す。開発者は、PowerBuilder かカスタム コンポーネントに付属の汎用 コンポーネントを使用できます。 Web データウィンドウの機能を活用するには、いくつかの方法があり ます。 • Web データウィンドウのデザイン タイム コントロール JSP ターゲット では、Web データウィンドウのデザイン タイム コントロールを使 用して、Web データウィンドウ コンポーネントにアクセスする サーバ サイド スクリプトを作成できます。これは、最も簡単に Web データウィンドウを使用できる方法です。 • Web ターゲット オブジェクト モデルのコーディング JSP タ ー ゲ ッ ト では、Web ターゲット オブジェクト モデルを使用して Web デー タウィンドウのコンポーネントにアクセスするためのサーバ サイ ド スクリプトを記述できます。Web ターゲット オブジェクト モデ ルには、Web データウィンドウのコンポーネントのコード作成を 容易にする、定義済みオブジェクトとメソッドのセットがありま す。 • Web データウィンドウのコンポーネント自体のコーディング 直 接 Web データウィンドウのコンポーネントにアクセスするサーバ サイド スクリプトを記述できます。 • 独自の HTML ジェネレータの記述 PowerBuilder で 提 供 さ れ て い る サンプル PBL を基にして、アプリケーションに必要なメソッドを 提供するユーザ独自の HTML ジェネレータを作成できます。 Web データウィンドウについての詳細は、『データウィンドウ プログ ラマーズ ガイド』マニュアルを参照してください。 686 PowerBuilder 第 30 章 PowerBuilder での Web アプリケーション開発 データウィンドウ Web コントロール ActiveX データウィンドウ Web コントロール ActiveX は、Internet Explorer で使 用できる完全対話形式のデータウィンドウ コントロールです。このコ ントロールは、リッチ テキスト提示様式を除く PowerBuilder データ ウィンドウのすべての機能を実装します。 データウィンドウ Web コントロール ActiveX は、検索引数によるデー タ検索とデータ更新をサポートします。開発者は、編集様式、表示書 式、および入力条件則を使用でき、データウィンドウを操作するため の PowerBuilder メソッドの大部分を利用できます。ファイル システム の対話にかかわるいくつかの関数がサポートされていないため、Web ActiveX は、ActiveX コントロールの中では安全にスクリプト実行でき るコントロールとして分類されています。 データウィンドウ Web コントロールには、いくつかのデータウィンド ウ Web コントロールで共有できるデータベース接続を作成するため の、データウィンドウ トランザクション オブジェクト コントロール が含まれています。 Web ActiveX は CAB ファイルとして提供され、これを使ってクライア ント ブラウザはコントロールをインストールして登録します。ユーザ が CAB ファイルを参照する Web ページをダウンロードすると、ブラ ウザは必要であれば CAB ファイルもダウンロードし、そのファイルを アンパックして、コントロールを登録します。 データウィンドウ Web コントロール ActiveX についての詳細は、 『デー タウィンドウ プログラマーズ ガイド』マニュアルを参照してくださ い。 データウィンドウ プラグイン データウィンドウ プラグインは、これまでに生成されて Web サーバに 保存されている Powersoft レポート(PSR)を表示します。PSR ファイ ルがすでに生成されているため、データベース アクセスは必要ありま せん。このプラグインは、読み込み専用アクセスのみをサポートし、 ユーザはレポートの表示、印刷、保存は可能ですが、修正することは できません。 アプリケーション テクニック 687 PowerBuilder ウィンドウ プラグイン プラグインは、Netscape Navigator をはじめとする Netscape プラグイン に対応するブラウザなら、どんなブラウザでも使用できます(Microsoft Internet Explorer 5.5 Service Pack 2 以降のバージョンでは、Netscape プ ラグインをサポートしていません)。クライアント ブラウザに必要な ファイルは、データウィンドウ プラグインの DLL だけです。 詳細については、第 32 章「データウィンドウ プラグインの使い方」を 参照してください。 PowerBuilder ウィンドウ プラグイン PowerBuilder ウィンドウ プラグインは、 クライアント ワークステーショ ンの HTML ページに PowerBuilder ウィンドウを表示する PowerBuilder アプリケーションを実行します。プラグインは、Netscape Navigator を はじめとする Netscape プラグインに対応するブラウザなら、どんなブ ラウザでも使用できます(Microsoft Internet Explorer 5.5 Service Pack 2 以降のバージョンでは、Netscape プラグインをサポートしていませ ん)。プラグインのセキュリティ バージョンを使うと、インターネッ トを介してダウンロードされる PowerBuilder アプリケーションがクラ イアント システムを損傷したり、クライアント ワークステーション上 の情報にアクセスしたりするといったことが防止されます。 アプリケーションがチャイルド ウィンドウから起動される場合は、 ウィンドウ プラグイン内のアプリケーションでほとんどの PowerBuilder 機能を実行できます。アプリケーションは、任意の PowerBuilder ウィ ンドウの実行、情報の表示、入力データの受け付け、データベースの 更新を行います。データベースへのアクセスは、クライアント ワーク ステーション上でクライアントがデータベースに接続することで開始 されます。 プラグインの最大の弱点は、ファット クライアントを必要とすること です。ファット クライアントは、PowerBuilder ランタイム DLL か共有 ライブラリと、PowerBuilder ウィンドウ プラグイン DLL か共有ライブ ラリを必要とするブラウザ クライアントです。 詳細については、第 33 章「PowerBuilder ウィンドウ プラグインの使い 方」を参照してください。 688 PowerBuilder 第 30 章 PowerBuilder での Web アプリケーション開発 PowerBuilder ウィンドウ ActiveX PowerBuilder ウィンドウ ActiveX は、ActiveX をサポートする Web ブラ ウザを使用するときに、HTML ページ内でのグラフィカル インタ フェースを提供します。また、ウィンドウとデータウィンドウ プラグ インの全機能のほかに、JavaScript や VBScript を使って、PowerBuilder のチャイルド ウィンドウのイベントと関数のサブセットにアクセス するための機能を提供します。この中には、ウィンドウ ActiveX コン トロールにあるチャイルド ウィンドウの関数とイベントを呼び出す ためのメソッドが含まれます。 アプリケーションがチャイルド ウィンドウから起動される場合は、 PowerBuilder ウィンドウ ActiveX 内のアプリケーションでほとんどの PowerBuilder 機 能 を 実 行 で き ま す。ア プ リ ケ ー シ ョ ン は、任 意 の PowerBuilder ウィンドウの実行、情報の表示、入力データの受け付け、 データベースの更新を行います。データベースへのアクセスは、クラ イアント ワークステーション上でクライアントがデータベースに接 続することで開始されます。 ウィンドウ プラグインと同様、ウィンドウ ActiveX の最大の弱点は、 ファット クライアントを必要とすることです。ファット クライアント は、PowerBuilder ランタイム DLL と PowerBuilder ウィンドウ ActiveX を必要とするブラウザ クライアントです。 詳細については、第 34 章「PowerBuilder ウィンドウ ActiveX の使い方」 を参照してください。 アプリケーション テクニック 689 PowerBuilder ウィンドウ ActiveX 690 PowerBuilder 第 3 1 章 Web サービス クライアントの構築 この章について この章では、PowerBuilder アプリケーションで Web サービスを使 用する方法について説明します。この章で説明するオブジェクト の関連情報については、 『PowerBuilder エクステンション リファレ ンス』マニュアルおよびオンライン ヘルプを参照してください。 内容 項目 Web サービスについて エクステンション ファイルのオブジェクトのインポート Web サービス プロキシ オブジェクトの生成 SOAP サーバへの接続 Web サービス メソッドの起動 例外処理 UDDI 照会 API の使い方 ページ 691 696 698 705 707 707 708 Web サービスについて Web サービスを使用すると、開発したアプリケーションから呼び 出される一般的なタスクを実行するために、新たにビジネス ロ ジックを作成しなくても、インターネット上かローカル ネット ワーク上の既存のコンポーネントを使用することができます。 Web サービスは、SOAP(Simple Object Access Protocol)が登場し た とき に 生ま れ たも の で す。SOAP は XML(Extensible Markup Language)を利用し、通常は、トランスポートとして HTTP(Hypertext Transfer Protocol)を使用します。SOAP を介して Web サービスを 起動するには、データ型のシリアライズとデシリアライズ、およ び SOAP メッセージの構築と解析が必要です。 アプリケーション テクニック 691 Web サービスについて Web サービスの利点の 1 つとして、WSDL(Web Services Description Language)を使用してサービスをその中に記述できるということがあ ります。WSDL は、XML 文法を使用し、メッセージを交換できる通信 エンドポイントの集まりとして Web サービスを定義します。WSDL サービス定義は、分散システムをドキュメント化し、アプリケーショ ン通信に関連する細部を自動化する方法を示す役割をします。 WSDL フ ァ イ ル に 記 述 さ れ る Web サ ー ビ ス は、UDDI(Universal Description, Discovery, and Integration)Web サイトで登録することがで きます。設計時に PowerBuilder から UDDI レジストリ サイトを検索し、 アプリケーションに必要なサービスを見つけることができます。 SOAP、WSDL、および UDDI により、アプリケーション間のインタ フェースが、異なるプラットフォーム間で標準化されるため、サード パーティのコンポーネントを簡単に使用できるようになります。 PowerBuilder は以下の Web サービス規格をサポートしています。 • SOAP 1.1 以降 • WSDL 1.1 以降 • HTTP または HTTPS PowerScript ターゲットまたは JSP ターゲットから Web サービスにア クセスできます。PowerBuilder で作成した JSP アプリケーションで Web サービスにアクセスする方法の詳細については、 『JSP ターゲットでの 作業』マニュアルの JSP ターゲットに関する章、またはオンライン ヘ ルプの JSP ページのオーサリングに関するトピックを参照してくださ い。 Web サービスの作成 PowerBuilder は、カスタム クラス(非ビジュアル)ユーザ オブジェク トを開発し、EAServer コンポーネントとしてそれらを配布し、Web サー ビスとして公開するツールを提供します。Windows および UNIX オペ レーティング システムで稼働している EAServer ホストにコンポーネ ントを配布することができます。詳細については、第 24 章「EAServer コンポーネントの構築」を参照してください。 692 PowerBuilder 第 31 章 Web サービス クライアントの構築 Web サービス クライアントの構築について PowerBuilder アプリケーションは、インターネット経由でアクセスさ れる Web サービスを利用するクライアントとして機能します。SOAP と WSDL を利用すると、1 つのエンティティとしてリモートで発行さ れた関数のコレクションを PowerBuilder アプリケーションに含めるこ とができます。Web サービスは、アプリケーションまたはほかの Web サービスから送信されたリクエストを受信して応答します。 SOAP を介して Web サービスを起動するには、データ型のシリアライ ズとデシリアライズ、および XML ベースの SOAP メッセージの構築 と解析が必要です。PowerBuilder と一緒にインストールされるエクス テンション ファイルあるいは動的ライブラリのオブジェクトを使用 する場合は、Web サービス クライアント プロキシがこれらの作業を行 います。そのため、SOAP 仕様とスキーマ、XML スキーマ仕様、ある いは WSDL 仕様とスキーマに関する幅広い知識を持つ必要はありま せん。 Web サービス エンジンの選択 PowerBuilder では、SOAP リクエストを作り、Web サービスから返さ れる SOAP メッセージを解析するために .NET Web サービス エンジン と EasySoap Web サービス エンジンのどちらかを選ぶことができます。 .NET Web サービス エンジンの使用 .NET アセンブリの生 成 .NET Web サービスは、最新の Web サービス標準をサポートします。こ のエンジンを使用するためには、開発マシンに wsdl.exe Web サービス ツールが必要になります。このツールは、WSDL ファイルを解析し、 .NET アセンブリ用の C# コードを生成するために必要です。wsdl.exe ファイルは .NET SDK と一緒にインストールされます。開発マシンで は必要ではありませんが、.NET Web サービス エンジンに依存する Web サービスを利用するために開発マシンに .NET Framework が必要です。 Web サービス プロキシ ウィザードで .NET Web サービス エンジンを選 択すると、ウィザードはプロキシ オブジェクトに加えて .NET アセン ブリ(DLL)を生成します。実行時に Web サービスを使用するために は、アプリケーションと一緒にウィザードで生成された DLL を配布す る必要があります。 アプリケーション テクニック 693 Web サービスについて 新しい Web サービス プロキシのためのプロジェクト ペインタで、 .NET Web サービス エンジンを選択することもできます。Web サービ ス プロキシ ジェネレータのプロパティ ダイアログボックスの[Web サービス]タブで[WSDL エンジン]から[.NET]チェックボックス を選択すると、PowerBuilder は[保存]アイコンをクリックした後に アセンブリ DLL を生成しようとします。プロパティ ダイアログボッ クスを使用して、Web サービス プロキシ ウィザードで以前に生成され たプロキシのための Web サービス エンジンを変更することはできま せん。 DLL の命名 [アセンブリ名]テキスト ボックスで Web サービス プロキシ ウィザー ドまたはプロジェクト ペインタによって生成された DLL に名前を付 けることができます。DLL 拡張子を含める必要はありません。ウィ ザ ー ド で 生 成 さ れ た ア セ ン ブ リ の 名 前 は、Web_service.DLL で す。 Web_service は[アセンブリ名]フィールドで指定する名前になります。 名前を指定しない場合は、アセンブリは DLL によって利用される Web サービスの名前を受け取ります。アセンブリは現行のターゲットの ディレクトリに生成されます。 DLL の配布 クライアント実行ファイルを配布するディレクトリに、Web サービス プ ロジェクトに作成した DLL を配布する必要があります。さらに、この ディレクトリに Sybase.PowerBuilder.WebService.Runtime.dll システム アセ ンブリおよび Sybase.PowerBuilder.WebService.RuntimeRemoteLoader.dll シ ステムアセンブリをコピーする必要もあります。 エクステンション オ ブジェクト .NET Web サービス エンジンと EasySoap Web サービス エンジンで、同 じ SOAP 接続と例外処理オブジェクトを使用しても、.NET Web サービ ス エンジンを参照するオブジェクトは異なるエクステンション ファ イルあるいはライブラリを要求します。 SoapConnection オブジェクトで使用可能なメソッドは、使用している エクステンション ファイルやライブラリ、および使用している Web サービスに依存します。.NET Web サービス エンジンのメソッドは、 SOAP クライアント ヘッダにセキュリティ情報を含めることができま す。 詳細については、 「エクステンション ファイルのオブジェクトのイン ポート」を参照してください。 694 PowerBuilder 第 31 章 Web サービス クライアントの構築 EasySoap Web サービス エンジンの使用 .NET SOAP エンジンを使用しない場合、PowerBuilder は EasySoap Web サービス エンジンを使用します。PowerBuilder の以前のリリースでは、 EasySoap Web サービス エンジンのみをサポートしていました。.NET Web サービス エンジンと異なり、EasySoap エンジンは XML タイプの 配列データ型および SOAP メッセージ エンベロープのヘッダ セク ションをサポートしません。EasySoap Web サービス エンジンは、下位 互換性および UNIX マシンに配布されるターゲットの使用のために残 されました。 Web サービス プロキシ ウィザードの先頭ページで、あるいは Web サー ビス プロジェクトのプロパティ シートの[Web サービス]タブで、使 用したい Web サービス エンジンを設定します。新しい Web サービス プロジェクトでは、[.NET]チェック ボックスはデフォルトで設定解 除されます。UNIX マシンに配布する予定の Web サービス アプリケー ションを開発している場合は、チェック ボックスをオンにしないでく ださい。 Web サービスにアクセスするためのファイアウォール設定の指定 設計時に Web サービスを追加し、開発マシンがファイアウォールの後 ろにあるとき、インターネットに接続するためにプロキシ サーバ設定 を指定する必要があります。 表 31-1 は、PowerBuilder システム オプション ダイアログボックスの [ファイアウォール設定]ページで入力できる、設計時のプロキシ サーバ 設定です。ランタイム プロキシ サーバ設定を入力するには、SoapConnection SetProxyServer メソッドまたは SetProxyServerOptions メソッドを使用す る必要があります。 SetProxyServer および SetProxyServerOptions メソッドの詳細については、 オンライン ヘルプの「PowerBuilder エクステンション リファレンス」を 参照してください。 アプリケーション テクニック 695 エクステンション ファイルのオブジェクトのインポート 表 31-1: 設計時のファイアウォール設定 ファイアウォール設 定 ファイアウォール ホ スト ポート ユーザ名 パスワード 説明 Web ページにアクセスするために使用するプロ キシ サーバ名 プロキシ サ ーバに接続するために使用する ポート プロキシ サーバにアクセスするためのユーザ 名 プロキシ サーバにアクセスするユーザのため のパスワード PowerBuilder は、 [ファイアウォール設定]ページの[この設定をシス テムのデフォルトとして使用する]チェック ボックスも選択した場合 にのみ、プロキシ サーバ設定のために入力する値を使用します。Web サービスを利用するために選択したエンジンの種類は、PowerBuilder が設計時にインターネットに接続するために使用する設定にも影響し ます。 .NET Web サービス エンジン 開発マシンはファイアウォールの後ろに あるが、 [この設定をシステムのデフォルトとして使用する]チェック ボックスを選択していない場合、PowerBuilder は Internet Explorer ブラ ウザのインターネット オプション ダイアログボックスで入力した設 定を使用してインターネットに接続しようとします。 [ファイアウォー ル設定]ページでの選択は、開発マシンがファイアウォールの後ろに ない場合には影響しません。 EasySoap Web サービス エンジン [この設定をシステムのデフォルトと して使用する]チェック ボックスを選択していない場合、PowerBuilder は開発マシンはファイアウォールの後ろにないとみなし、Internet Explorer ブラウザのインターネット オプション ダイアログボックスの 設定を使用しようとしません。 [この設定をシステムのデフォルトとし て使用する]チェック ボックスを選択しているが、開発マシンがファ イアウォールの後ろにない場合は、Web サービスの呼び出しは失敗し ます。 エクステンション ファイルのオブジェクトのインポート SOAP を介した Web サービスは、データ型のシリアライズとデシリア ライズおよび XML ベースの SOAP メッセージの解析を要求します。 696 PowerBuilder 第 31 章 Web サービス クライアントの構築 pbwsclient110.pbx ファイルは、SOAP 仕様とスキーマ、XML スキーマ 仕様、あるいは WSDL 仕様とスキーマに関する幅広い知識がなくても これらの作業を行える .NET Web サービス エンジンのためのオブジェ クトを含みます。エクステンション ファイルを PowerBuilder Web サー ビス アプリケーションにインポートした後に、これらのオブジェクト を使用することができます。 EasySoap Web サービス エンジンを使用する場合、pbsoapclient110.pbx ファイルまたは pbwsclient110.pbx ファイルを PowerBuilder アプリケー ションにインポートすることができます。しかし、.NET Web サービス エンジンを使用していなくても、pbwsclient110.pbx ファイルは設計マ シンおよび開発マシンに .NET 2.0 Framework を必要とします。両方の エクステンション ファイルは同じオブジェクトを含み、同様の方法で これらのオブジェクトとメソッドを使用します。 PBD ファイルの使用 PowerBuilder の以前のバージョンでは、エクステンション ファイルを インポートするかわりに、PBD ファイルをアプリケーション ライブラ リに追加する必要がありました。しかし、現在これは必要ではなく、 セットアップ プログラムが PBD ファイル(エクステンション ファイ ルとして、同じ SoapConnection オブジェクトと SoapException オブジェ クトを含んでいます)を Sybase\Shared\PowerBuilder ディレクトリにイ ンストールします。pbwsclient110.pbx または pbsoapclient110.pbx ファイ ルからオブジェクト定義をインポートするかわりに、pbwsclient110.pbd あるいは pbsoapclient110.pbd を使用することができます。 PowerBuilder エクステンション ファイルの定義をアプリケーション ラ イブラリに追加するには、システム ツリーでライブラリを右クリック して、ポップアップ メニューから[PB エクステンションのインポー ト]を選択します。Sybase\Shared\PowerBuilder ディレクトリに移動し て、使用したいエクステンション ファイルを選択します。 PBWSClient110.pbx または PBSoapClient110.pbx ファイルをアプリケー ションにインポートすると、以下のオブジェクトがシステム ツリーに 表示されます。 オブジェクト soapconnection soapexception アプリケーション テクニック 説明 SOAP サーバへの接続に使用される soapconnection から送出された例外の捕捉のために使 用される 697 Web サービス プロキシ オブジェクトの生成 Web サービス クライアント アプリケーションを作成する際に、アプリ ケーションの探索パス内のディレクトリに、クライアント実行ファイ ルとともに使用するエクステンション ファイルを配布する必要があ ります。Web サービス アプリケーションが必要とするエクステンショ ン ファイルを自動的に含めるために、ランタイム パッケージャ ツー ルを使用することができます。 Web サービス プロキシ オブジェクトの生成 Web サービス プロキ シ オブジェクトの作 成 Web サービス プロキシを新しく作成するには、新規作成 ダイアログ ボックスの[プロジェクト]ページから[Web サービス プロキシ ウィ ザード]アイコンを選択します。Web サービス プロキシ ウィザードで プロキシを作成することにより、PowerScript で Web サービスを使用で きるようになります。EasySoap Web サービス エンジンを選択した場 合、各ポートに対して 1 つのプロキシが作成されます。 ウィザードで以下の指定を行います。 • 使用する Web サービス エンジン • アクセスする WSDL ファイル • 選択する WSDL ファイル内のサービス • 使用する 1 つまたは複数のポート(EasySoap エンジンのみ) • ポート名に付ける接頭辞(EasySoap)およびプロキシ名に含める 接頭辞(EasySoap と .NET エンジン) • プロキシの配布先の PowerBuilder ライブラリ 新規作成 ダイアログボックスの[プロジェクト]ページから[Web サービス プロキシ]アイコンを選択することもできます。[Web サー ビス プロキシ]アイコンを選択すると、Web サービスのプロジェクト ペインタが開きます。ここからプロジェクトを作成し、オプションを 指定し、プロキシ ライブラリを構築できます。新規プロジェクトは、 Web サービス(および、EasySoap エンジンでは、プロキシを生成する ポート)を一覧にし、生成されるプロキシ オブジェクトを格納する出 力ライブラリの名前を指定します。 Web サービス プロジェクトの作成にウィザードを使用した場合でも ペインタを使用した場合でも、最後のステップとして、ペインタ バー の[配布]アイコンをクリックするか、メニュー バーから[デザイン| プロジェクトの配布]を選択して、プロキシ オブジェクトを構築します。 698 PowerBuilder 第 31 章 Web サービス クライアントの構築 循環参照 循環参照を含む WSDL ファイルからの Web サービス プロキシの生成 は、PowerBuilder ではサポートしません。このような「循環参照」の 例は、子クラス メンバーとしてそれ自身を含んでいる構造です。 ウィザードでの UDDI ブラウザの使い方 PowerBuilder では、 PowerScript ターゲットと JSP ターゲットの Universal Description, Discovery, and Integration(UDDI)レジストリにアクセスで きます。UDDI サービスは業界全体の取り組みであり、企業間統合の ための標準を提供します。また、Web サービスのデータベースにアク セスするための、標準インタフェースを定義します。 Web サービス プロキシ ウィザードと JSP Web サービス プロキシ ウィ ザードには、UDDI ブラウザが組み込まれています。これらのウィザー ドの[WSDL ファイルの選択]ページ上、または Web サービス プロキ シ プロジェクトのプロパティ ダイアログボックスの[Web サービス] ページ上の[UDDI から検索する]ボタンをクリックすると、UDDI 検 索ページが表示されます。UDDI 検索ページには、表 31-2 に示す検索 フィールドとオプションがあります。 アプリケーション テクニック 699 Web サービス プロキシ オブジェクトの生成 表 31-2: UDDI の検索フィールドとオプション 検索フィールドまたは オプション UDDI プロファイル クエリ URL 検索 カテゴリ 単語の検索 大文字 / 小文字の区別 ソート 最大行数 説明 UDDI オペレータの名前を含む編集可能なドロッ プダウン リスト。UDDI プロファイルには、クエ リ URL を関連付けることができる。このドロップ ダウン リストでは、Microsoft と IBM のパブリッ ク UDDI レジストリの定義済みプロファイルを選 択できる Web サービスを検索する Web サービス レジスト リの URL が表示されるテキスト ボックス。 [UDDI プロファイル]ドロップダウン リストで定義済み のプロファイルを選択した場合、そのプロファイ ルに関連付けられている URL がここに表示され る。クエリ URL を入力して[プロファイルの保 存]ボタンをクリックすることにより、プロファ イルにその URL を関連付けることもできる UDDI の検索で使用するキーワードを入力するた めのテキスト ボックス 「サービス名」 (デフォルト)または「ビジネス名」 を含むドロップダウン リスト チェックボックス オプション。オンにすると、 [検 索]テキストボックスの現在の値が完全一致で検 索される チェックボックス オプション。オンにすると、 [検 索]テキストボックスの現在の値が大文字と小文 字を区別して検索される ラジオボタン オプション。検索結果を昇順または 降順にソートする スピン ボタン オプション。返される検索結果の数 をここに指定した数に制限する UDDI 検索で次に表示されるページは、キーワードをビジネス名と サービス名のどちらで検索するかによって異なります。 700 • ビジネス名検索の場合 [ビジネス名]ページに、検索条件に一致す るビジネス名と説明のリストが表示されます。ビジネス名を選択 して[次へ]をクリックすると、 [サービスの選択]ページにサー ビス名のリストが表示されます。このリストには、各サービスの 説明と WSDL ファイル名も含まれます。 • サービス名検索の場合 [サービスの選択]ページにサービス名のリ ストが表示されます。このリストには、各サービスのビジネス名、 説明、および WSDL ファイル名も含まれます。 PowerBuilder 第 31 章 Web サービス クライアントの構築 [サービスの選択]ページでサービスを選択すると、UDDI の検索が終 了します。ウィザードの残りのページで選択を続けてください。 Web サービス プロキシ オブジェクトのプロパティ ダイアログボック スの[Web サービス]ページには、Web サービス プロキシ ウィザード で選択した WSDL ファイルが表示されます。この WSDL ファイルは、 UDDI 検索ウィザードを使用して変更することもできます。UDDI 検索 ウィザードには、Web サービス プロキシ ウィザードの UDDI の検索 ページと同じ検索オプションと検索結果リストがあります。 生成されたプロキシ 生成されたプロキシはシステム ツリーに表示されます。プロキシ ノー ドを展開すると、メソッドのシグネチャを表示できます。 XML メソッドのエリ アス PowerBuilder は大文字と小文字を区別しませんが、XML、SOAP、C#、 および .NET は大文字と小文字を区別します。そこで、PowerScript コー ドが XML メソッドを正しく呼び出せるように、プロキシの各メソッ ドはエリアスを使用します。alias for の後に、対応する XML メソッ ドまたは SOAP メソッドの名前とシグネチャが大文字小文字を区別し て入ります。 たとえば、次のようになります。 function real getquote(string ticker) alias for getQuote(xsd:string symbol)# return xsd:float StockPrice@urn:xmethods-delayedquotes@SoapAction アプリケーション テクニック 701 Web サービス プロキシ オブジェクトの生成 異なる時間帯の Web サービス アプリケーションが date、time、あるいは datetime データ型を使用する Web サービスを利用する場合、サービス実装が処理し、異なる時間帯 からサービスにアクセスするアプリケーション ユーザに対して異な る値を返すことがあります。これは、通常 Web サービスの設計での問 題で、Web サービスとそれを呼び出すアプリケーション間での精度の 差あるいは変換エラーによるものではありません。 EasySoap Web サー ビス エンジンのデー タ型マッピング Web サービス プロキシ ジェネレータにより、EasySoap Web エンジンを 使用している場合は、XML と PowerBuilder 間で、.NET Web サービス エンジンを使用している場合は、XML、C#、.NET、および PowerBuilder 間でデータ型のマッピングが行われます。XML のデータ 型はすべて World Wide Web Consortium Web のサイト http://www.w3.org/1999/XMLSchema と World Wide Web Consortium Web のサ イト http://www.w3.org/2001/XMLSchema に基づいています。 表 31-3 は、XML と PowerScript 間でのデータ型マッピングを示してい ます。.NET Web サービスを使用する場合は、データ型は C# に変換さ れ、次に .NET データ型に変換されます。 (表 31-4 と 表 31-5 は、.NET Web サービス エンジンで使用されるデータ型マッピングを示してい ます。) 表 31-3: XML と PowerBuilder 間でのデータ型マッピング XML データ型 boolean byte (-128 ~ 127) または short unsignedByte (0 ~ 255) または unsignedShort int unsignedInt long (-9223372036854775808 ~ 9223372036854775807)、 unsignedLong (0 ~ 9223372036854775807)、 integer (-9223372036854775808 ~ 9223372036854775807)、 nonNegativeInteger (0 ~ 9223372036854775807)、 negativeInteger (-1 ~ -9223372036854775808)、 nonPositiveInteger (0 ~ -9223372036854775808)、または positiveInteger (1 ~ 9223372036854775807) decimal (-999999999999999999 ~ 999999999999999999) float double 702 PowerScript データ型 boolean int uint long ulong longlong decimal real double PowerBuilder 第 31 章 Web サービス クライアントの構築 PowerScript XML データ型 データ型 gYear、gYearMonth、gMonthDay、gDay、anyURI、QName、 string NOTATION、string、normalizedSting、token、または token か ら派生するデータ型 normalizedString、token、および派生データ型について normalizedString はキャリッジ リターン、ライン フィード、 あるいはタブ文字を含みません。token は normalizedString に似ていますが、先頭スペースや末尾スペース、あるいは 内部の連続するスペースを含みません。token から派生する デ ー タ 型 は、language、Name、NCName、NMTOKEN、 NMTOKENS、ID、IDREF、IDREFS、ENTITY、ENTITIES を 含みます。 date time dateTime base64、base64Binary、または hexBinary .NET Web サービス エンジンのデータ型 マッピング date time datetime blob .NET Web サービス エンジンを使用する際に、PowerBuilder は WSDL ファイルからの XML を C# コードに変換し、.NET アセンブリ内でそ れをコンパイルします。表 31-4 は、これらの変換のデータ型をマッピ ングを示します。 アプリケーション テクニック 703 Web サービス プロキシ オブジェクトの生成 表 31-4: NET Web サービス エンジンのデータ型マッピング XML データ型 int unsignedInt boolean unsignedByte short unsignedShort long unsignedLong Decimal Float Double C# データ型 int uint bool Byte short ushort long ulong Decimal Float Double System.DateTime Byte [ ] Datetime、Date、および Time hexBinary および hex64Binary String nonNegativeInteger、 negativeInteger、 nonPositiveInteger、 positiveInteger、gYear、 gMonth、gMonthDay、gDay、 duration、anyURI、QName、 NOTATION、normalizedString、 token、language、NMTOKEN、 NMTOKENS、Name、 NCName、ID、IDREF、 IDREFS、ENTITY、 ENTITIES、および String AnyType Object .NET データ型 System.Int32 System.UInt32 System.Boolean System.Byte System.Int16 System.UInt16 System.Int64 System.UInt64 System.Decimal System.Float System.Double System.DateTime System.Byte [ ] System.String System.Object 表 31-5 は、C# データ型と PowerBuilder 間のデータ型マッピングを示 しています。 704 PowerBuilder 第 31 章 Web サービス クライアントの構築 表 31-5: C# と PowerBuilder 間のデータ型マッピング C# データ型 byte sbyte short int long ushort uint ulong float double object char string decimal bool System.DateTime 配列の配列 PowerScript データ型 byte int int long longlong uint ulong longlong real double any uint string decimal boolean datetime PowerBuilder は、XML とは異なり、可変長一次元配列のみサポートし ます。WSDL ファイルの配列が固定長の一次元である場合、PowerBuilder は自動的にこれを可変長配列に変換します。WSDL ファイルの配列が 多次元配列の場合、戻り値の型は無効になり、使用できません。 関数プロトタイプで、PowerBuilder は配列型を PowerBuilder any 型とし て表示します。戻り値を保持する適切な型の配列を宣言することが必 要です。 SOAP サーバへの接続 アクセスする Web サービスをホストする SOAP サーバに接続するに は、SoapConnection オブジェクトを使用します。SoapConnection オブ ジェクトの SetOptions メソッドを使用して、HTTPS 接続のユーザ ID およびパスワードなどのオプションを設定できます。.NET Web サー ビスでは、SetBasicAuthentication、SetCertificateFile 、および UseWindowsAuthentication 等の認証メソッドを使用することもできま す。 アプリケーション テクニック 705 SOAP サーバへの接続 同一アプリケーション内での複数の Web サービスの使用 異なる認証要求を持つ複数の Web サービスに接続する場合は、複数の SoapConnection オブジェクトのインスタンスを作成し、SetOptions メ ソッドあるいは各接続オブジェクトのほかの認証メソッドに適切な値 を設定する必要があります。 CreateInstance メソッドを使用して、Web サービスにアクセスするクラ イアント プロキシ インスタンスを作成します。 SoapConnection オブジェクト メソッドの詳細については、オンライン ヘルプの「PowerBuilder エクステンション リファレンス」を参照して ください。 例 以下のスクリプトでは、EasySoap Web サービス エンジンを使用している SOAP サーバ上の Web サービスへの接続が作成されます。CreateInstance メソッドで定義されるエンドポイントを使用して、接続プロパティが設定 されます。エンドポイントが CreateInstance メソッドで定義されない場 合、プロキシに格納されているデフォルト URL が使用されます。この スクリプトでは、SetSoapLogFile メソッドにより、ログ ファイルが指定 されています。戻り値がメッセージ ボックスに表示されます。 SoapConnection conn // SoapConnection を定義 syb_currencyexchangeport proxy_obj // プロキシを宣言 long rVal, lLog real amount // エンドポイントを定義。プロキシ内のデフォルト エンド // ポイントを使用する場合は、省略できる string str_endpoint str_endpoint = "http://services.xmethods.net:80/soap" conn = create SoapConnection // 接続のインスタンス化 lLog = conn.SetSoapLogFile("C:\mySoapLog.log") // SOAP のデータ交換を記録するトレース ファイルを設定 // 文字列を "" にすると、この機能は無効になる rVal = Conn.CreateInstance(proxy_obj, & "syb_currencyexchangeport", str_endpoint) // プロキシ オブジェクトの作成 try amount = proxy_obj.getrate("us","japan") // サービスの起動 messagebox(" 現在の為替レート ", "1 US ドル "& 706 PowerBuilder 第 31 章 Web サービス クライアントの構築 + " = " + string(amount) + " 日本円 ") catch ( SoapException e ) messagebox (" エラー ", "Web サービスを起動できません。") // エラー処理 end try destroy conn Web サービス メソッドの起動 SoapConnection は、SoapConnection オブジェクト メソッドを使って設 定した接続オプションで Soap_proxy オブジェクトを作成するために使 用されます。Web サービスのプロキシ オブジェクトが作成されると、 クライアント アプリケーションは、その Web サービスにアクセスでき るようになります。Web サービス メソッドを起動するには、プロキシ オブジェクトに以下の情報を含めることが必要です。 • サービスのエンドポイント。WSDL ファイルから取得 • SOAP メソッド呼び出しで使用される名前空間定義 • 構造体定義(必要な場合) • 戻される各構造体配列のインスタンス変数。戻される配列がすべ て any 型であるため • 1 つ以上の SOAP メソッドと、対応するエリアス文字列 例外処理 Web サービスのメソッドの実行時に発生するエラーは、SoapException オブジェクトに変換され、呼び出したスクリプトに送出されます。ま た、PBWSClient110.pbx および PBSoapClient110.pbx 内の SoapConnection オブジェクトのメソッドは、サーバへの接続が失敗し たときや Web サービスが検索されなかったり作成できなかったりし たときなどに、SoapException オブジェクトを送出できます。 アプリケーション テクニック 707 UDDI 照会 API の使い方 例外の捕捉 クライアント アプリケーションは、さまざまな方法で通信エラーを処 理できます。たとえば、クライアントがサーバに接続し、オブジェク トのメソッドを呼び出そうとしたときにそのオブジェクトが存在しな かった場合は、サーバとの接続を解除し、別のサーバに接続して操作 を再試行する方法があります。あるいは、クライアントがユーザにメッ セージを表示して、次に起こることを制御する機会をユーザに与える 方法もあります。 エラー発生時にクライアントが操作の再開のために新しいサーバに接 続している場合、新しいサーバ上でリモート オブジェクトをインスタ ンス化してから、リモート オブジェクトのメソッドを呼び出す必要が あります。 処理されない例外 例外ハンドラがない場合、または既存の例外ハンドラがその例外を処 理しない場合、アプリケーション オブジェクトの SystemError イベン トが実行されます。SystemError イベントにスクリプトが記述されてい ない場合は、アプリケーション エラーが起きて、アプリケーションは 終了します。 UDDI 照会 API の使い方 PowerBuilder のエクステンション クラスである UDDIProxy を使用す ると、アクセスする Web サービスを UDDI レジストリから検索できま す。エクス テンシ ョン クラス とその メソッ ドの詳 細につ いては、 『PowerBuilder エクステンション リファレンス』マニュアルまたはオン ライン ヘルプを参照してください。 コード例 次に、UDDIProxy クラスのすべてのメソッドを使用したコード例を示 します。この例では、同じ検索オプション(大文字と小文字を区別し て検索し、最大 5 行の検索結果を取得する)を使用して、IBM の UDDI レジストリをサービス名(Weather)とビジネス名(IBM)で検索します。 uddiproxy proxy int ret proxy = create uddiproxy ret = proxy.setinquiryurl (“http:/www-3.ibm.com/services/uddi/inquiryapi”) ret = proxy.setoption (false, true, 0, 5) int count, count2 string businessName[], businessDescription[] string businessKey [] string servicename[], servicedescription[] 708 PowerBuilder 第 31 章 Web サービス クライアントの構築 string servicekey [], wsdl [ ] ret = proxy.findService(“Weather”,count,serviceName, & serviceDescription, serviceKey, businessName, wsdl) int i, j FOR i = 1 TO count messagebox(servicename[i], & servicedescription[i]+servicekey[i]+wsdl[i]) NEXT proxy.findbusiness(“IBM”, count, businessName, & businessDescription, businessKey) FOR i = 1 TO count messagebox(businessName[i], & businessDescription[i] + businessKey[i]) proxy.getbusinessdetail (businessKey [i], count2, & servicename, servicedescription, servicekey, wsdl) FOR j = 1 TO count2 messagebox(servicename[j], & servicedescription[j]+servicekey[j]+wsdl[j]) NEXT NEXT destroy proxy UDDI API 呼び出しの トラブルシューティン グ ロギングを有効にすると、UDDIProxy オブジェクトのメソッド呼び出 しが失敗した場合に原因を追跡できます。ロギングを有効にするには、 PowerBuilder の Java サービス クラス パスにコンフィグレーション ファイル log4j.properties を追加する必要があります。次に、UDDI 検索 用のログ コンフィグレーション ファイルの例を示します。 #log4j.debug=true #log all level #log4j.rootCategory=DEBUG, lf5 #only log com.sybase.powerbuilder.uddi log4j.category.com.sybase.powerbuilder.uddi=DEBUG, dest2, lf5 #dest1 #log4j.appender.dest1=org.apache.log4j.ConsoleAppender #log4j.appender.dest1.layout= org.apache.log4j.PatternLayout #log4j.appender.dest1.layout.ConversionPattern= %-5p:%-5r:%-5c:%l:%m%n #dest2 log4j.appender.dest2=org.apache.log4j.FileAppender log4j.appender.dest2.layout= org.apache.log4j.PatternLayout log4j.appender.dest2.layout.ConversionPattern= %-5p:%l:%m%n アプリケーション テクニック 709 UDDI 照会 API の使い方 log4j.appender.dest2.File=c:/mylog.txt #lf5 log4j.appender.lf5= org.apache.log4j.RollingFileAppender log4j.appender.lf5.File=c:/mylog.lf5 log4j.appender.lf5.layout= org.apache.log4j.PatternLayout log4j.appender.lf5.layout.ConversionPattern= [slf5s.start]%d{DATE}[slf5s.DATE]%n\ %p[slf5s.PRIORITY]%n%x[slf5s.NDC] %n%t[slf5s.THREAD]%n\%c[slf5s.CATEGORY] %n%l[slf5s.LOCATION]%n%m[slf5s.MESSAGE]%n%n log4j.appender.lf5.MaxFileSize=500KB 710 PowerBuilder 第 3 2 章 データウィンドウ プラグインの 使い方 この章について この章では、データウィンドウ プラグインを使用して Powersoft レ ポート(PSR)を開発して Web ページに配布する方法について説 明します。 内容 はじめに 項目 データウィンドウ プラグインについて Powersoft レポート(PSR)の保存 HTML ページの作成 Web サーバの設定 ユーザのワークステーションの設定 ページ 711 715 716 718 719 この章では、HTML と URL について、および Web ブラウザが Web サーバからページをどのように取得するかについての知識を有 し、Web サーバにアクセス可能な環境であることを前提にしてい ます。 データウィンドウ プラグインについて データウィンドウ プラグインを使用すると、Netscape プラグイン をサポートするブラウザで表示される Powersoft レポート(PSR) を Web ページに表示できます。 PSR ファイルには、レポートの定義(ソースとオブジェクト)お よび PSR ファイル作成時のデータが含まれます。PSR ファイルを 作成するとその中にデータが保存されるので、PSR ファイルでは データベース接続は必要はありません。ただし、データは静的な ので更新できません。 サポートするブラウザ アプリケーション テクニック データウィンドウ プラグインを使用するには、Netscape プラグイ ンをサポートする Web ブラウザを使う必要があります。たとえば、 Netscape ブラウザ、Microsoft Internet Explorer バージョン 3 ~ 5.5 Service Pack 1 です。 711 データウィンドウ プラグインについて Microsoft Internet Explorer 5.5 Service Pack 2 以 降 の バ ー ジ ョ ン は、 Netscape プラグインをサポートしていません。PowerBuilder Enterprise 版を使う場合、ActiveX のデータウィンドウ Web コントロールを使用 して Internet Explorer に PSR を表示できます。詳細については、『デー タウィンドウ プログラマーズ ガイド』マニュアルを参照してくださ い。 セキュリティ データウィンドウ プラグインにはセキュリティ上の問題はありませ ん。ローカル アプリケーションを実行することもありません。また、 ユーザがレポートをローカルに保存するように明示的に選択しない限 り、ローカル ファイルへの書き込みも行いません。 データウィンドウ プラグインは PSR ファイルしか表示しません。PSR ファイルは読み込み専用です。したがって、セキュリティ バージョン のデータウィンドウ プラグインは不要です。 制約 PSR はリッチテキスト提示様式にはできません。 データウィンドウ プラグインの機能 データウィンドウ プラグインは、レポート ペインタ、データウィンド ウ ペインタ、データウィンドウ コントロール、またはデータストアで プレビューおよび保存されたときのデータと書式を持つ PSR を表示し ます。PSR は、回転文字、色付き文字、影付け、チェックボックス編 集様式やラジオボタン編集様式など、データウィンドウ オブジェクト またはレポート オブジェクトのすべての書式を表示します。 データはレポートであり、データ入力やデータベース アクセスはあり ません。 Web ブラウザのポップアップ メニューを使用して、クライアントはレ ポートをいくつかの形式で印刷または保存できます。レポートをロー カル PSR ファイルとして保存すれば、データの検索、フィルタ、およ びソートのためのツールが揃っている InfoMaker で表示できます。デー タウィンドウ プラグインは Netscape プラグイン API を実装します。 データウィンドウ プラグインを使用するには、この API をサポートす るブラウザが必要です。詳細については、711 ページの「サポートす るブラウザ」を参照してください。 クライアントとサーバ の対話の詳細 712 表 32-1 に、データウィンドウ プラグインを含む HTML ドキュメント をユーザが表示する際に、クライアントとサーバ間で行われる処理に ついて詳しく示します。 PowerBuilder 第 32 章 データウィンドウ プラグインの使い方 表 32-1: データウィンドウ プラグインのクライアント / サーバ間トランザク ション 手順 1 2 3 4 5 6 7 8 クライアントの動作 Web ブラウザがサーバに HTML ドキュメントを要求する サーバの応答 サーバはドキュメントの MIME の種類(text/html)を識別する ヘッダを送信する サーバは HTML ドキュメントを 送信する ブラウザは MIME の種類を受信 し、HTML ドキュメントを受信 する準備をする ブラウザは HTML ドキュメント — を受信し、それを表示する ブラウザは Embed 要素を認識し、 サーバは、PSR の MIME の種類 ページ上にプラグインのための (application/datawindow)を識別 領域を確保し、PSR ファイルを するヘッダを送信する サーバに要求する ブラウザは MIME の種類を受信 サーバは PSR ファイルを送信す る し、PSR ファイルを受信する準 備をする Web ブラウザは PSR ファイルを — 受信する ブラウザはそのプラグイン ディ — レクトリで、MIME の種類 (application/datawindow)に対応 する DLL を検索する — Web ブラウザはプラグイン DLL をロードし、PSR ファイルを表 示する 要件 データウィンドウ プラグインを含むページを参照する各クライアン トでは、ローカル マシンにインストールしたデータウィンドウ プラグ イン DLL が必要です。 名前と位置 データウィンドウ プラグインの名前は、NPDWE110.DLL です。 PowerBuilder は、この DLL を PowerBuilder 11.0\Internet Tools\Plugins ディレクトリにインストールします。 アプリケーション テクニック 713 データウィンドウ プラグインについて データウィンドウ プラグインのインストールと設定 PowerBuilder のインストール時に標準セットアップを選択した場合、 データウィンドウ プラグインはコンピュータにインストールされま せん。プラグインをインストールするには、PowerBuilder のカスタム インストールを実行し、 [コンポーネントの選択]ページで[Web プラ グイン]チェックボックスをオンにします。インストールするプラグ インとコントロールを選択するには、そのページの[変更]ボタンを クリックします。この節では、プラグインのインストール後に行う必 要がある設定作業について説明します。 データウィンドウ プラグインは、PowerBuilder 11.0\Internet Tools\Plugins ディレクトリにインストールされます。Netscape がインストール済み の場合は、PowerBuilder インストール プログラムによってプラグイン のコピーが Web ブラウザの Plugins ディレクトリにインストールされ る場合もあります。 インストール先 ブラウザがインストールされていない場合、またはインストール プロ グラムがブラウザを見つけられなかった場合には、Netscape をインス トールして、プラグインをブラウザの Plugins ディレクトリにコピーす るか移動しなければなりません。Microsoft Internet Explorer の現行バー ジョンは、プラグインをサポートしていません。 データウィンドウ プラグインの開発と配布 実行方法 データウィンドウ プラグインの中に PSR を表示するためには、4 つの 主な作業があります。 ❖ 結果のコンポーネント 714 データウィンドウ プラグインの中に PSR を表示するには 1 PSR ファイルを保存します。 2 データウィンドウ プラグインを埋め込む HTML ページを作成し ます。 3 内容の種類(MIME の種類)を登録し、HTML ページと PSR ファ イルを所定のディレクトリにコピーして、Web サーバを構成しま す。 4 すべてのクライアント ワークステーション上にデータウィンドウ プラグイン DLL をインストールします。 セットアップがすべて終了すると、表 32-2 に示すコンポーネントが サーバおよびクライアント コンピュータに設定されます。 PowerBuilder 第 32 章 データウィンドウ プラグインの使い方 表 32-2: データウィンドウ プラグイン用のサーバとクライアントの環境設定 コンピュータ サーバ クライアント 次の手順 コンポーネント MIME の種類 application/datawindow が拡張子 PSR で登録 されている HTML ページに PSR の Embed 要素がある PSR ファイル ブラウザの Plugins ディレクトリ内のデータウィンドウ プ ラグイン DLL とサポートする DLL この章では、以降、データウィンドウ プラグインに PSR を表示するた めの以下の 4 つの手順について説明します。 • Powersoft レポート(PSR)の保存 • HTML ページの作成 • Web サーバの設定 • ユーザのワークステーションの設定 Powersoft レポート(PSR)の保存 PSR ファイルを作成するには、いくつかの方法があります。 PSR ファイルの作成 ❖ PSR ファイルを作成するには • PowerBuilder データウィンドウ ペインタまたは InfoMaker レポー ト ペインタで、以下の操作を行います。 • [ファイル|名前を付けてファイルを保存]を選択する。ファ イル名の選択 ダイアログボックスに、保存する場所、ファイ ル名、およびファイルの種類として Powersoft レポートを指定 する • [ファイル|名前を付けて行を保存]を選択する。名前を付け て保存 ダイアログボックスに、保存する場所、ファイル名、お よびファイルの種類として Powersoft レポートを指定する PSR のリソース データウィンドウ オブジェクトまたはレポート オブジェクトは、ビッ トマップ オブジェクトとカスタム ポインタを表示できます。これらの 外部リソースを、クライアント ワークステーションで利用できるよう にしなければなりません。サーバから自動ではダウンロードされませ ん。 アプリケーション テクニック 715 HTML ページの作成 外部リソースのパスは、クライアント ワークステーションで有効でな ければなりません。データウィンドウ ペインタかレポート ペインタ で、現行ディレクトリに対する相対パスを指定できます。絶対パスは ユーザのコンピュータに存在しないことがあります。 イントラネット環境では、すべてのユーザがアクセスできるネット ワークドライブに外部リソースを保存できます。Windows 環境では、 ネットワーク パスを使用して、マップされたドライブ名ではなくネッ トワーク ドライブを指定できます。 OLE オブジェクトと カスタム コントロー ル OLE サーバとカスタム コントロールを各クライアント ワークステー ションでインストール、登録する必要があります。 制約 元のデータウィンドウかレポートがリッチテキスト提示様式だった PSR は、データウィンドウ プラグインの中には使えません。 次の手順 PSR ファイルを保存したら、その PSR ファイルを表示する HTML ペー ジを作成しなければなりません。 HTML ページの作成 Embed 要素を使用して、Web ページに Powersoft レポート(PSR)を含 めます。要素の属性によって、レポートに割り当てる領域とレポート ファイル名を指定します。 Embed 要素は次のように指定します。 <EMBED src=April_sales.psr WIDTH=370 HEIGHT=320> Embed 要素の属性 Embed 要素は、プラグインの HTML 仕様の一部です。データウィンド ウ プラグインの場合、標準 HTML 属性だけを指定します。 HTML 属性 HTML 属性で、クライアントにダウンロードするファイル の名前、および Web ページ上でプラグインに確保する領域を、以下の とおり指定します。 716 PowerBuilder 第 32 章 データウィンドウ プラグインの使い方 表 32-3: データウィンドウ プラグインの HTML 属性 HTML 属性 SRC 値 ダウンロードされるオブジェクトを識別する ブラウザは、Embed 要素を処理するときに、サーバに リソースを要求し、コンテンツ タイプを処理する DLL をプラグイン ディレクトリから検索する WIDTH HEIGHT データウィンドウ プラグインの場合、オブジェクトは PSR ファイルである 表示するウィンドウの幅。ピクセル値で指定する 表示するウィンドウの高さ。ピクセル値で指定する サンプル ページ 次に、サンプル ページにデータウィンドウ プラグインを含める HTML コードを示します。Embed 要素を使用して、PSR ファイルを指定して います。 始めの要素 <HTML> ドキュメント ヘッダ <HEAD> <TITLE>On Leave report</TITLE> </HEAD> <BODY> H1 ヘッダ <H1>On Leave report</H1> パラグラフの中の Embed 要素 <P><EMBED src=DWB_att_crossout.psr WIDTH=680 HEIGHT = 350></P> 終わりの要素 </BODY> </HTML> アプリケーション テクニック 717 Web サーバの設定 Web サーバの設定 サーバを設定するには、以下の操作を行います。 MIME の種類の指定 1 MIME の種類の指定 2 サーバへのファイルの配置 Web サーバに所定のソフトウェアを使用して、データウィンドウ プラ グインの MIME の種類を登録します。PowerBuilder 11.0 で使用できる MIME の種類は次のとおりです。 application/datawindow11.0 MIME のファイル拡張子は PSR です。 サーバのマニュアルによっては、MIME の種類ではなく、コンテンツ タイプという用語を使用する場合もあります。 サーバへのファイルの 配置 PSR ファイルと HTML ファイルをサーバ上の所定のディレクトリに コピーします。 表 32-4: サーバ上の PSR ファイルと HTML ファイルの場所 ファイル HTML ページ 場所 HTML ドキュメント ディレクトリかサブ ディレクトリ Embed 要素の SRC 属性で指定される PSR ファイル HTML ドキュメント ディレクトリか、ほか の適切なディレクトリ 実行方法 HTML ページを、ページに リンクする URL で指定され るディレクトリにコピーす る PSR ファイルを Embed 要素 の属性で指定したディレク トリにコピーする URL について HTML ページに指定する URL は、Web サーバで定義さ れる論理パスです。たとえば、PSR のシステム パスは以下のようにな ります。 C:\WEBSITE\HTDOCS\PB\DWB_ATT_CROSSOUT.PSR htdocs がサーバのドキュメント ディレクトリに定義されれば、URL の 論理パスは、次のようにドキュメント ディレクトリに対する相対パス になります。 pb/dwb_att_crossout.psr 718 PowerBuilder 第 32 章 データウィンドウ プラグインの使い方 ユーザのワークステーションの設定 PSR の保存、HTML ページの作成、およびサーバの設定が終了したら、 次はデータウィンドウ プラグインを含むページを表示できるように クライアント ワークステーションを設定する必要があります。 データウィンドウ プラグインを含む Web ページを表示するユーザは、 クライアント ワークステーションでインストールされるソフトウェ アをサポートする必要があります。また、Web サーバにも接続しなけ ればなりません。 必要なコンポーネント データウィンドウ プラグインを含む Web ページを表示するには、各ク ライアント ワークステーションで表 32-5 に示すコンポーネントが必 要です。 表 32-5: データウィンドウ プラグインの表示に必要なクライアント要件 コンポーネント インターネット接 続かイントラネッ ト接続 Netscape プラグイ ンをサポートする Web ブラウザ データウィンドウ プラグイン DLL サポート DLL アプリケーション テクニック 手順 企業内で、またはインターネット サービス プロバイダ から利用できる ブラウザ ベンダから利用できる。以下のようなブラウ ザが必要である • Netscape Navigator バージョン 3.x 以降 • Microsoft Internet Explorer バージョン 3.x ~ 5.5 Service Pack 1。Internet Explorer 5.5 Service Pack 2 以降はプラ グインをサポートしていない この DLL がない場合は、NPDWE110.DLL ファイルを Internet Tools\Plugins ディレクトリからブラウザの Plugins ディレクトリにコピーする この DLL がない場合は、Shared\PowerBuilder ディレク トリからブラウザの Plugins ディレクトリに PBSHR110.DLL ファイルをコピーします。クライアン ト ワークステーションで有効でない場合は、クライア ントの Windows システム ディレクトリに次の Microsoft ランタイム ファイルをインストールします。 MSVCR71.DLL、MSVCP71.DLL、ATL71.DLL 719 ユーザのワークステーションの設定 コンポーネント その他のファイル 手順 元のデータウィンドウ オブジェクトかレポートに、外 部ファイルのビットマップ オブジェクトかカスタム ポ インタが含まれていた場合、外部ファイルをクライアン ト ワークステーションにコピーする必要がある。クラ イアント ワークステーションのパスは、PSR に保存さ れているパスに対応しなければならない 元のデータウィンドウ オブジェクトかレポートに OLE オブジェクトかカスタム コントロールが含まれていた 場合、OLE サーバかカスタム コントロールをクライア ント ワークステーションでインストール、登録する必 要がある。OLE オブジェクトのパスはクライアント ワークステーションで有効でなければならない Web ページと PSR の 表示 PSR をデータウィンドウ プラグインの中に表示しながら、以下の操作 を行えます。 • スクロールバーを使用して PSR のデータを操作する • PSR のソースが編集可能なデータウィンドウ オブジェクトであっ た場合、行とカラムの値を変更する。ただし、データベース接続 がないため、データベースのデータは更新できない • PSR を右クリックして、保存、印刷、およびナビゲートのポップ アップ メニューを表示する Web ページのレポートをローカル PSR ファイルとして保存すれば、そ の PSR ファイルを InfoMaker で開いてデータの検索、フィルタ、およ びソートが行えます。 720 PowerBuilder 第 3 3 章 PowerBuilder ウィンドウ プラグイン の使い方 この章について この章では、Web ページにプラグイン アプリケーションとして表 示される PowerBuilder アプリケーションの開発、テスト、および 配布の方法について説明します。 内容 はじめに アプリケーション テクニック 項目 PowerBuilder ウィンドウ プラグインについて PowerBuilder ウィンドウ プラグインのインストールと設定 セキュリティ PowerBuilder ウィンドウ プラグインの使い方 PowerBuilder ウィンドウ プラグイン アプリケーションの開発 と配布 PowerBuilder アプリケーションの作成 HTML ページの作成 サーバの設定 ユーザのワークステーションの設定 ページ 722 727 728 729 730 738 742 743 この章では、HTML と URL について、および Web ブラウザが Web サーバからページをどのように取得するかについての知識を有 し、Web サーバにアクセス可能な環境であることを前提にしてい ます。 721 PowerBuilder ウィンドウ プラグインについて PowerBuilder ウィンドウ プラグインについて PowerBuilder ウィンドウ プラグインを使用すると、Netscape プラグイ ンをサポートするブラウザで表示される PowerBuilder チャイルド ウィ ンドウを Web ページに表示できます。 Internet Explorer Microsoft Internet Explorer 5.5 Service Pack 2 以 降 の バ ー ジ ョ ン は、 Netscape プラグインをサポートしていません。そのため、それらのブ ラウザでは、PowerBuilder ウィンドウ プラグインを使用して PSR レ ポートを表示することはできません。 722 PowerBuilder 第 33 章 機能 PowerBuilder ウィンドウ プラグインの使い方 PowerBuilder チャイルド ウィンドウには、データウィンドウ、OLE オ ブジェクト、ActiveX(OCX)コントロール、およびツリー コントロー ルなどの使い慣れたコントロールがすべて含まれます。また、チャイ ルド ウィンドウからポップアップ ウィンドウまたはレスポンス ウィ ンドウを開くことも可能です。 ユーザがチャイルド ウィンドウやほかのウィンドウのコントロール と対話すると、スタンドアロン PowerBuilder アプリケーションのコン トロールとまったく同じように、そのイベント スクリプトが実行され ます。プラグイン アプリケーションからデータベースへのアクセス は、クライアントの定義済みデータベース接続を使用してローカルで 実行されます。 アプリケーション内のオブジェクトを、1 つまたは複数の PowerBuilder 動的ライブラリ(PBD: PowerBuilder Dynamic Library)に含めることが できます。 標準バージョンとセ キュリティ バージョ ン PowerBuilder ウィンドウ プラグインには、標準バージョンとセキュリ ティ バージョンの 2 種類があります。 標準 PowerBuilder ウィンドウ プラグイン 標 準 PowerBuilder ウ ィ ン ド ウ プラグインは、PowerBuilder チャイルド ウィンドウを HTML ページ に表示します。標準ウィンドウ プラグインは、NPPBA110.DLL で実装 されます。 セキュリティ PowerBuilder ウィンドウ プラグイン セキュリティPowerBuilder ウィンドウ プラグインは、標準 PowerBuilder ウィンドウ プラグインの セキュリティ バージョンです。セキュリティ バージョンを使用する と、インターネットを介してダウンロードされる PowerBuilder アプリ ケーションがクライアント システムを損傷したり、クライアント ワー クステーション上の情報にアクセスしたりすることが防止されます。 セキュリティ ウィンドウ プラグインは、NPPBS110.DLL で実装されま す。 PowerBuilder ウィンドウ プラグインのセキュリティ バージョンを使用す るときの留意事項については、728 ページの「セキュリティ PowerBuilder ウィンドウ プラグインの使い方」を参照してください。 サポートするブラウザ PowerBuilder ウィンドウ プラグインでは、Netscape Navigator バージョ ン 3.x 以降の、Netscape プラグインをサポートするブラウザを使用す る必要があります。Microsoft Internet Explorer 5.5 Service Pack 2 以降の バージョンは、Netscape プラグインをサポートしていません。 アプリケーション テクニック 723 PowerBuilder ウィンドウ プラグインについて セキュリティ 標準 PowerBuilder ウィンドウ プラグインは、セキュリティ機能を実装 していないアプリケーションなので、ローカルのファイルにアクセス し、ローカルのアプリケーションを実行できます。このような処理は、 制御のない Web 環境では好まれないことが多いですが、アクセスが制 御される企業イントラネットでは許容される場合もあります。 セキュリティが重要視されるサイトの場合は、PowerBuilder ウィンド ウ プラグインのセキュリティ バージョンを使用してアプリケーショ ンを構築してください。 セキュリティ モードで常に動作するイベントがある PowerBuilder 11 では、標準ウィンドウ プログラムを使用していたとし ても、アプリケーションの Open イベントおよびコントロール用のい くつかの Constructor イベントがセキュリティ モードで動作します。ア プリケーションのロジックが、これらのイベントでの安全性に欠ける 動作(ファイルを開いて書き込みを行うなど)を実行する機能に依存 する場合には、イベント メッセージが自分に対して表示されるように してください。このイベント メッセージは、プラグインが標準モード に戻ったときに処理されます。 セキュリティ PowerBuilder ウィンドウ プラグインの詳細については、 728 ページの「セキュリティ PowerBuilder ウィンドウ プラグインの使 い方」を参照してください。 プラグインとなるアプリケーションの種類 HTML フォームでは、限られたユーザ インタフェースを介した対話処 理しかできません。PowerBuilder ウィンドウ プラグインは、HTML を 超える能力を提供します。リッチ ユーザ インタフェース設計で開発さ れたアプリケーション ウィンドウを、Web ページに表示できます。ク ライアント ワークステーションで定義されているデータ ソースにア クセスできます。 例 724 アプリケーションには以下のものがあります。 • マスタ データウィンドウと詳細データウィンドウを持つデータ解 析ウィンドウ • ユーザによる選択を、ツリービュー、リストビュー、およびピク チャ リストボックス コントロールから行うユーザ インタフェー スの設計 • サーバ上のデータを処理するデータ入力フォーム PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 • クライアント定義によるデータベース接続(ネットワークまたは ローカル)を使用してクライアント マシン上のデータを処理する データ入力フォーム • PowerBuilder の OLEControl コントロールを使用して ActiveX コン トロールを表示するウィンドウ PowerBuilder ウィンドウ プラグインの機能 PowerBuilder ウィンドウ プラグインは、Web ページ上にあらかじめ割 り当てられた固定領域内に PowerBuilder のチャイルド ウィンドウを表 示します。ユーザはページ上のコントロールと対話でき、ウィンドウとそ のコントロールの PowerBuilder スクリプトはどの PowerBuilder コード でも実行できます。ユーザが別の Web ページに移ると、PowerBuilder ウィンドウは閉じ、PowerBuilder DLL がメモリからアンロードされま す。 プラグインを HTML ページに含めるには、HTML Embed 要素を使いま す。Embed 要素は PowerBuilder オブジェクトを収めた 1 つまたは複数 の PBD の名前、およびページに表示されるチャイルド ウィンドウ オ ブジェクトの名前を指定します。 PowerBuilder ウィンドウ プラグインは Netscape プラグイン API を実装 し、この API をサポートするブラウザが必要です。詳細は、723 ペー ジの「サポートするブラウザ」を参照してください。 クライアントとサーバ の対話の詳細 表 33-1 に、PowerBuilder ウィンドウ プラグインを含む HTML ドキュ メントが表示される際にクライアントとサーバとの間で行われる処理 について詳しく示します。 表 33-1: ウィンドウ プラグインのクライアント / サーバ間トランザクション 手順 1 クライアントの動作 Web ブラウザがサーバに HTML ドキュメントを要求する 2 ブラウザは MIME の種類を受信 し、HTML ドキュメントを受信 する準備をする ブラウザは HTML ドキュメント を受信し、それを表示する 3 アプリケーション テクニック サーバの応答 サーバはドキュメントの MIME の種類(text/html)を識別する ヘッダを送信する サーバは HTML ドキュメントを 送信する — 725 PowerBuilder ウィンドウ プラグインについて 手順 4 クライアントの動作 ブラウザは Embed 要素を認識し、 ページ上にプラグインのための 領域を確保し、PBD ファイルを サーバに要求する サーバの応答 サーバは、PBD の MIME の種類 を識別するヘッダを送信する。 ヘッダは以下のいずれかである • 標準ウィンドウ プラグイン application/vnd.powerbuilder11.0 • セキュリティ ウィンドウ プラグ イン application/vnd.powerbuilder11.0 -s 5 6 7 8 9 10 11 12 13 14 726 ブラウザは MIME の種類を受信 し、PBD ファイルを受信する準 備をする ブラウザは PBD ファイルを受信 する ブラウザは、自分のプラグイン ディレクトリから MIME タイプ に対応する DLL を探す。手順 4 のサーバの応答を参照 ブラウザはプラグイン DLL を ロードする プラグインが PowerBuilder 配布 DLL を探してロードする Embed 要素に LIBRARY 属性が含 まれる場合、クライアントは指 定された PBD ファイルを要求す る ブラウザは MIME の種類を受信 し、追加 PBD ファイルを受信す る準備をする PowerBuilder は Embed 要素で指 定されたチャイルド ウィンドウ を表示する チャイルド ウィンドウはその Open スクリプトを実行する スクリプトが CommandParm 関数 を呼び出す場合、PowerBuilder は Embed 要素の COMMANDPARM 属性の値をブラウザに問い合わ せる サーバは PBD ファイルを送信す る — — — — サーバは PBD の MIME の種類を 識別するヘッダを送信する。手 順 4 のサーバの応答を参照 サーバは PBD ファイルを送信す る — — — PowerBuilder 第 33 章 要件 PowerBuilder ウィンドウ プラグインの使い方 PowerBuilder ウィンドウ プラグインは、PowerBuilder ランタイム DLL およびプラグイン DLL を使用して、PowerBuilder のフル機能を提供し ます。 PowerBuilder ウィンドウ プラグインを含むページを参照する各クライ アントで、ローカル マシンにインストールされる以下のソフトウェア をサポートする必要があります。 • PowerBuilder ランタイム DLL • Web ブラウザの Plugins ディレクトリに入っている ウィンドウ プ ラグイン DLL PowerBuilder ウィンドウ プラグインは、開発者がクライアント マシン のセットアップを管理するイントラネット アプリケーションで特に 便利です。 サポートされる各プラットフォーム上でのクライアント マシンの設 定の詳細については、743 ページの「ユーザのワークステーションの 設定」を参照してください。 名前 PowerBuilder ウィンドウ プラグイン DLL の名前は、使用しているもの が標準バージョンかセキュリティ バージョンかによって異なります。 表 33-2: PowerBuilder ウィンドウ プラグイン DLL コンポーネント 標準 PowerBuilder ウィンドウ プラグイン セキュリティ PowerBuilder ウィンドウ プラ グイン 名前 NPPBA110.DLL NPPBS110.DLL PowerBuilder ウィンドウ プラグインのインストールと設定 PowerBuilder のインストール時に標準セットアップを選択した場合、 PowerBuilder ウィンドウ プラグインはコンピュータにインストールさ れません。プラグインをインストールするには、PowerBuilder のカス タム インストールを実行し、 [コンポーネントの選択]ページで[Web プラグイン]チェックボックスをオンにします。インストールするプ ラグインとコントロールを選択するには、そのページの[変更]ボタ ンをクリックします。 この節では、プラグインのインストール後に行う必要がある設定作業 について説明します。 アプリケーション テクニック 727 セキュリティ PowerBuilder ウィンドウ プラグインの使い方 インストール先 PowerBuilder ウィンドウ プラグイン DLL は、PowerBuilder11.0\Internet Tools\Plugins ディレクトリにインストールされます。Netscape がイン ストール済みの場合は、PowerBuilder インストール プログラムによっ てプラグインのコピーが Web ブラウザの Plugins ディレクトリにイン ストールされる場合もあります。 ブラウザがインストールされていない場合、またはインストール プロ グラムがブラウザを見つけられなかった場合には、Netscape をインス トールして、プラグインをブラウザの Plugins ディレクトリにコピーす るか移動しなければなりません。 PowerBuilder 配布 DLL PowerBuilder ウィンドウ プラグインは、PowerBuilder ランタイム DLL (PBVM110.DLL、PBDWE110.DLL など)の場所を認識していなければ なりません。セットアップ プログラムはブラウザを検出するとレジス トリに適切な修正を加えますが、セットアップ プログラムがブラウザ を検出できなかった場合には、開発者側で修正を行わなければなりま せん。これには 2 つの方法があります。 • Windows レジストリで、ブラウザの実行ファイルに対するアプリ ケーション パス キーに PowerBuilder ランタイム DLL のディレク トリを追加する • システム パスに PowerBuilder ランタイム DLL のディレクトリを 追加する セキュリティ PowerBuilder ウィンドウ プラグインの使い方 使い方 セキュリティ PowerBuilder ウィンドウ プラグインを使用するアプリ ケーションを開発、配布するには、標準の PowerBuilder ウィンドウ プ ラグインの場合と同じ基本手順(729 ページの「PowerBuilder ウィンド ウ プラグイン アプリケーションの開発と配布」を参照)に従います。 唯一の相違点は、セキュリティ PowerBuilder ウィンドウ プラグインが、 特殊なバージョンの標準のウィンドウ プラグイン DLL を使用することで す。セキュリティ バージョンのウィンドウ プラグインは、NPPBS110.DLL です。 機能上の制約 728 セキュリティ PowerBuilder ウィンドウ プラグインを使用すると、クラ イアント ワークステーションで実行する PowerBuilder アプリケーショ ンの機能がかなり制約され、クライアント システムへの印刷以外のア クセスは拒否されます。このため、セキュリティ ウィンドウ プラグイ ンがすべての状況で有効であるとは限りません。 PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 セキュリティ PowerBuilder ウィンドウ プラグインを使用した場合、表 33-3 に示す動作が制限されます。 表 33-3: セキュリティ ウィンドウ プラグインの制約 動作 外部関数 PowerScript 関数 データベース接続 インターネット アク セス 電子メール OLE ダイナミック データ エクスチェンジ (DDE) 制約 外部関数を呼び出すと実行エラーが発生する 一定の PowerScript 関数を呼び出すと実行エラーが 発生する データベースにアクセスする関数を呼び出すと実 行エラーが発生する セキュリティ PowerBuilder ウィンドウ プラグイン を使用するアプリケーションでは、現行の Web サー バにしかインターネット接続できない PowerScript の Mail 関数を呼び出すと実行エラーが 発生する PowerScript の OLE 関数を呼び出すと実行エラーが 発生する PowerScript の DDE 関数を呼び出すと実行エラーが 発生する PowerBuilder ウィンドウ プラグイン アプリケーション の開発と配布 基本手順 プラグイン アプリケーションの開発には、主な 4 つの作業があります。 ❖ PowerBuilder ウィンドウ プラグイン アプリケーションを作成および配布す るには 1 PowerBuilder アプリケーションを作成、テスト、および構築します。 2 PowerBuilder アプリケーション ウィンドウを埋め込む HTML ペー ジを作成します。 3 内容の種類(MIME の種類)を登録し、アプリケーションの HTML ページと PBD ファイルを所定のディレクトリにコピーして、Web サーバを構成します。 4 すべてのクライアント ワークステーション上で、標準またはセキュ リティ PowerBuilder ウィンドウ プラグイン DLL と PowerBuilder 配 布 DLL をインストールします。 アプリケーション テクニック 729 PowerBuilder アプリケーションの作成 結果のコンポーネント セットアップがすべて終了すると、表 33-4 に示すコンポーネントが サーバおよびクライアント コンピュータに設定されます。 表 33-4: PowerBuilder プラグイン用のサーバとクライアントの環境設定 コンピュータ サーバ クライアント コンポーネント MIME の種類が登録されている 登録の方法については、742 ページの「MIME の種類の指 定」を参照 HTML ページに PBD の Embed 要素がある 1 つまたは複数の PBD にアプリケーション オブジェクト が収められている ブラウザのプラグイン ディレクトリ内の PowerBuilder プラ グイン DLL プラットフォーム用の配布キットを使用してインストール した PowerBuilder 配布 DLL システム パスにリストされた PowerBuilder 配布 DLL の ディレクトリ データベース接続ソフトウェア、OLE サーバ、カスタム コ ントロールなど、プラグイン アプリケーションで必要とな るその他のソフトウェア 次の手順 この章では、以降、PowerBuilder ウィンドウ プラグイン アプリケー ションを開発、配布するための以下の 4 つの手順について説明します。 • PowerBuilder アプリケーションの作成 • HTML ページの作成 • サーバの設定 • ユーザのワークステーションの設定 PowerBuilder アプリケーションの作成 PowerBuilder ウィンドウ プラグイン アプリケーションは、Web ページ に表示されるチャイルド ウィンドウから始まります。ウィンドウで、 コントロールの表示、およびイベントのスクリプトの記述が行えます。 スクリプトからは、ほかのウィンドウを開く、ファイルを読み書きす る、クライアント マシン上のほかのプログラムを実行するなどの操作 が行えます。 730 PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 プラグイン アプリケーションの設計の選択 プラグインとして使用するアプリケーションの設計は、通常開発する PowerBuilder アプリケーションとほとんど変わりませんが、以下の点 について、いくつかの制限事項と留意事項があります。 ウィンドウ管理 • ウィンドウ管理 • オブジェクト • スクリプトと変数 • データ アクセス • 外部ファイル 初期チャイルド ウィンドウ 初期ウィンドウは、ブラウザ フレーム内に 存在するチャイルド ウィンドウでなければなりません。 以下のことが可能です。 • チャイルド ウィンドウでタイトル バーを使用する。ただし、チャ イルド ウィンドウでは、コントロール メニュー、最大化ボタン、 または最小化ボタンは使用しない • チャイルド ウィンドウから、ポップアップ ウィンドウまたはレス ポンス ウィンドウを開く。メイン ウィンドウまたは MDI ウィン ドウは開けない 以下の制限があります。 • チャイルド ウィンドウのメニューを配置する • 初期ウィンドウから別のチャイルド ウィンドウを開く ウィンドウを閉じる クライアントが別の Web ページを参照すると、現 行の Web ページのチャイルド ウィンドウは閉じますが、ほかのウィン ドウはアプリケーションを閉じない限り、開いています。これらのウィ ンドウは、チャイルド ウィンドウの Close イベントまたは CloseQuery イベントで閉じなければなりません。 戻り値を設定して、CloseQuery イベントでチャイルド ウィンドウが閉 じないようにする処理は行わないでください。ブラウザが別のページ に移らないようにしたり、ビューからウィンドウを削除できないよう にしたりすることはできません。ユーザが前のページに戻ったときに、 アプリケーションの別のインスタンスが起動されます。 オブジェクト PBD 内のオブジェクト プラグイン アプリケーションは、PBD の中の すべてのオブジェクトにアクセスします。関数、構造体、ユーザ オブ ジェクトにもアクセスできます。 アプリケーション テクニック 731 PowerBuilder アプリケーションの作成 プラグイン アプリケーションは、SQLCA トラン ザクション オブジェクトやメッセージ オブジェクトなど、PowerBuilder がインスタンスを作成するシステム オブジェクトにアクセスします。 システム オブジェクト Embed 要素のオプションの APPLICATION 属性を使用して、PBD のアプリケーション オブジェク トの名前を指定できます。APPLICATION 属性を使用すると、プラグ イン アプリケーションはアプリケーション オブジェクトの Open イベ ントと Close イベントにアクセスできます。 アプリケーション オブジェクト APPLICATION 属性を指定しないと、以下のようになります。 • プラグイン アプリケーションはアプリケーション オブジェクトに アクセスできなくなり、SystemError や Idle などのイベントが利用 できない。アプリケーション オブジェクトでグローバルに定義さ れている変数と関数を処理できない • アプリケーション オブジェクトのほかのスクリプトは、PowerBuilder でテストを行う際に必要となる。アプリケーション オブジェクト のスクリプトで、アプリケーションのセットアップを行うことが できない APPLICATION 属性の指定については、738 ページの「Embed 要素の属 性」を参照してください。 スクリプトと変数 グローバル変数 Embed 要素の APPLICATION 属性を使用して PBD の アプリケーション オブジェクトを指定すると、プラグイン アプリケー ションはアプリケーションで使うグローバル変数とグローバル関数に アクセスできます。 APPLICATION 属性を指定しないと、プラグイン アプリケーションは グローバル変数を使えません。すべての変数をインスタンス、共有、 またはローカルに定義しなければなりません。 APPLICATION 属性の指定については、738 ページの「Embed 要素の属 性」を参照してください。 初期ウィンドウの参照 PowerBuilder は、初期チャイルド ウィンドウの インスタンスを保持する変数を作成しないので、スクリプトで名前を 使用して初期チャイルド ウィンドウを参照することはできません。逆 に、Open 関数のスクリプトを記述してウィンドウのインスタンスを生 成すれば、そのインスタンスを変数に代入して参照できます。 したがって、以下のスクリプトは、ウィンドウ変数 w_mychild が存在し ないため、実行時エラーになります。 // 以下のスクリプトは、実行時エラーとなります。 w_mychild.title = "The initial window" 732 PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 以下のようにスクリプトを記述すると、エラーを回避できます。 // チャイルド ウィンドウ自体で this.title = "The initial window" // または title = "The initial window" // チャイルド ウィンドウのコントロール内で parent.title = "The initial window" アプリケーションをセットアップするスクリプト DBMS への接続を含め、 アプリケーションのセットアップはすべてチャイルド ウィンドウで 行わなければなりません。最初に実行されなければならないスクリプ ト可能なイベントは、ウィンドウの中のコントロールのコンストラク タです。次に、ウィンドウの Open イベントが実行されます。 Activate イベントはチャイルド ウィンドウでは実行されません。した がって、チャイルド ウィンドウにアプリケーションのセットアップ コードを置かないでください。 データ アクセス アプリケーションから DBMS にアクセスする場合、各クライアントは データ ソースに接続しなければなりません。その接続は、サーバでは なくクライアント マシン上で定義される必要があります。データ ソー スはローカル DBMS かネットワーク DBMS です。 クライアント マシンから DBMS に接続する方法については、『データ ベースとの接続』マニュアルを参照してください。 コントロールの Constructor イベントは、ウィンドウの Open イベント の前に実行されます。ウィンドウの Open イベントで DBMS に接続し た場合、Constructor イベントではデータが得られません。ウィンドウ の Open イベントでコントロールのデータを取得するか、Constructor イ ベントまたはウィンドウの Open イベントからイベントをポストして ください。 外部リソースのパス ファイルに指定するパスは、クライアント ワークステーションで有効 でなければなりません。 アプリケーションで外部ファイルとして画像を使用する場合、その画 像は PowerBuilder オブジェクトに指定されたパスで取得できなければ なりません。外部ファイルを使用するのではなく、画像リソースを PBD に構築することもできます。これについては、736 ページの「動的ラ イブラリの構築」を参照してください。 アプリケーションでローカル ファイルを読み書きする場合、それらの ファイルのパスは各クライアント マシンで有効なものでなければな りません。 アプリケーション テクニック 733 PowerBuilder アプリケーションの作成 パスで、マップされたドライブ名を使用してネットワーク ドライブが 参照されている場合、すべてのクライアントがアプリケーションと同 じドライブ名を使用する必要があります。また、サーバ名をパスで指 定することもできます。 たとえば、o: が \\marketing\drive に割り当てられている場合、以下の パスはどちらも有効です。ただし、ドライブ名は変更の可能性がある ので、サーバ名を指定している 2 番目のパスの方が永続的な利用が可 能です。 O:\pbapps\connect.bmp \\marketing\drive\pbapps\connect.bmp ウィンドウ ペインタでの開始ウィンドウの定義 PowerBuilder で作成するほかのウィンドウと同様に、起動ウィンドウ の作成にもウィンドウ ペインタを使います。 ❖ ❖ 起動ウィンドウ(または専用のウィンドウ)を作成するには 1 PowerBuilder でウィンドウ オブジェクトを新規作成します。 2 プロパティ ビューのウィンドウの[全般]タブで、ウィンドウの 種類を「child!」に設定します。 3 必要であれば、ほかのコントロールを追加します。 4 ウィンドウとコントロールのイベント スクリプトを記述します。 既存のアプリケーションをプラグインとして実行できるように変換するには 1 最初に表示されるウィンドウの種類を「child!」に変更します。 2 Embed 要素の APPLICATION 属性を指定しない場合は、以下の両 方の操作を行います。 • グローバル変数への参照を削除する • アプリケーションのセットアップ コードを、アプリケーショ ンの Open イベントまたは MDI フレーム イベントからチャイ ルド ウィンドウの Open イベントに移動します。 APPLICATION 属性の指定については、738 ページの「Embed 要素 の属性」を参照してください。 3 734 アプリケーションの設計によっては、ほかのウィンドウを開く方 法を設計し直さなければならない場合もあります。 PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 チャイルド ウィンドウにメニューを配置することはできません。チャ イルド ウィンドウはアクティブ ウィンドウとはみなされず、Activate イベントは発生しません。チャイルド ウィンドウにはタイトル バーを 表示でき、最小化、最大化、サイズ変更ができます。プラグイン環境 では、以下のように、チャイルド ウィンドウは Web ページ上の WIDTH 属性と HEIGHT 属性で割り当てられる領域に常に制限されます。 チャイルド ウィンド ウについて • ウィンドウを最大化すると、WIDTH 属性と HEIGHT 属性で割り当 てられた領域内で最大表示される • ウィンドウを最小化すると、ウィンドウのアイコンとタイトルが プラグインに割り当てられた領域の下端に表示される • チャイルド ウィンドウのサイズを変更できる場合は、枠線をドラッ グしてウィンドウを割り当て領域より小さくできる(割り当て領 域より大きくすることはできない) したがって、チャイルド ウィンドウの最小化、最大化、またはサイズ 変更は有効とはいえません。 PowerBuilder でのアプリーションのテスト 作成したアプリケーションをクライアント ブラウザで実行する前に、 PowerBuilder でチャイルド ウィンドウを開くメイン ウィンドウを定義 して、アプリケーションをテストできます。 ❖ PowerBuilder ウィンドウ プラグイン アプリケーションをテストするには 1 種類がメイン(デフォルト)のウィンドウ オブジェクトを新規作 成します。 2 プラグインの起動チャイルド ウィンドウを開く Open イベントの スクリプトを記述します。 Open(w_child) 3 アプリケーション テクニック ウィンドウ ペインタで、ウィンドウ サイズを以下のように設定す ると便利です。 • メイン ウィンドウのサイズは、チャイルド ウィンドウを十分 に表示できるサイズにする • チャイルド ウィンドウを左上隅に配置する。このように設定 するには、プロパティ ビューの[その他]タブの[位置]フィー ルドを使用する 735 PowerBuilder アプリケーションの作成 4 [プレビュー]ボタンをクリックするか、[ファイル|実行 / プレ ビュー]を選択して、テスト ウィンドウを実行します。 PowerBuilder でのデバッグ PowerBuilder デバッガを使用するには、ウィンドウだけを実行するの ではなく、アプリケーションを実行する必要があります。メイン ウィ ンドウを開くスクリプトで、アプリケーション オブジェクトを定義し ます。次に、 [実行]コマンドか[デバッグ]コマンドを使用してアプ リケーションをテストできます。 動的ライブラリの構築 『ユーザーズ ガイド』マニュアルでは、動的ランタイム ライブラリ (PBD)を構築する方法について説明しています。この手順は、プラグ イン アプリケーションの場合と同じです。この節では、プラグイン ア プリケーション用の PBD を構築するために必要な選択項目について 説明します。 Web 環境では、ファイル サイズが重要であることを覚えておいてくだ さい。 PBL 内でのオブジェ クトの編成 PowerBuilder リソー ス(PBR)ファイル の使用 736 アプリケーションを構築する前に、アプリケーションで使用するオブ ジェクトをシステム ツリーまたはライブラリ ペインタで PBL に編成 しておかなければなりません。PBL はプラグイン アプリケーションの PBD のソースになります。最適なライブラリを作成するには、以下の 点に留意します。 • ファイル サイズを最小化するには、アプリケーションで使用する オブジェクトのみを入れる。不要なオブジェクトは削除する • 動的に作成されるオブジェクト(データストアで使用されるデー タウィンドウ オブジェクトなど)またはデータウィンドウのコン トロールに動的に割り当てられるオブジェクトをすべて含める • 先祖オブジェクトを入れる コントロールによっては、画像に外部ファイルを使用する場合もあり ます。たとえば、ピクチャ リストボックス コントロール、ツリービュー コントロール、ピクチャ コントロール、ピクチャボタン コントロー ル、ポインタ、データウィンドウ オブジェクトのビットマップ オブ ジェクトです。プラグイン アプリケーションで外部ファイルの画像を 使用する場合、クライアントで同じ画像が同じシステム パス上にない ことがあります。 PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 クライアント マシンにピクチャをインストールするかわりに、1 つま たは複数の PowerBuilder リソース(PBR: PowerBuilder Resource)ファ イルを使用して、PBD に画像を組み込むことができます。画像を組み 込むと PBD はサイズは大きくなりますが、独立して機能します。 構築する動的ランタイム ライブラリは実行ファイルではないため、 PBR ファイルにデータウィンドウ オブジェクトを含める必要はあり ません。作成後の PBD には、ソース PBL 内のすべての PowerBuilder オブジェクトが含まれます。 ネットワーク上の画像やその他のリソース PBD にファイルを組み込むかわりに、広くアクセスされるネットワー ク ディレクトリにファイルを格納することも可能です。ただし、この 場合、ファイルへのパスは、PowerBuilder オブジェクトでのパスと同 じでなければなりません。つまり、Windows 環境では、各クライアン トが同じドライブ名でネットワーク ドライブをマップしなければな りません。あるいは、サーバ名をパスで指定することもできます。 ❖ PBR ファイルを定義するには 1 〔Shift〕+〔F6〕を押してファイル PowerBuilder エディタを開くか、 ほかのテキスト エディタを開き、拡張子 .PBR の新しいファイル を作成します([テキスト エディタ]アイコンはツールバーに追加 できます)。 2 画像やほかのリソースを、各行に一覧表示します。パスとファイ ル名を、オブジェクトのプロパティ シートかスクリプトで指定さ れるとおり正確に表示します。 ショートカット オブジェクトのプロパティ ビューを表示し、 〔Ctrl〕+〔C〕を使用 して、ファイル名をクリップボードにコピーし、エディタに貼り 付けます。 3 ファイルを保存します。 アプリケーションに複数の PBL が含まれ、各 PBL にそれぞれのリソー スを使用するオブジェクトが含まれている場合は、各 PBL に対して PBR ファイルを作成する必要があります。PBR ファイルは、1 つの PBL 内で使用されるリソースのファイル名をリストします。 PBD の構築 ライブラリ ペインタかプロジェクト ペインタでランタイム ライブラ リ(PBD)を構築します。これについては、『ユーザーズ ガイド』マ ニュアルを参照してください。以下のことに留意してください。 アプリケーション テクニック 737 HTML ページの作成 プラグイン アプリケーションには、マシ ン コード DLL ではなく PBD が必要です。 • マシン コードの選択解除 • PBR ファイルを各 PBD に指定する PBR ファイルにリストしたリ ソースを PBL 内のオブジェクトで使用する場合は、PBR 名を [ソー ス ファイル]テキストボックスに入力します。 PBR ファイルの定義およびランタイム ライブラリ(PBD)の構築方法 については、 『ユーザーズ ガイド』マニュアルで実行ファイルの作成 に関する章を参照してください。 HTML ページの作成 プラグイン アプリケーションの PowerBuilder PBD を作成、構築した ら、次にそれを表示する HTML ページを作成しなければなりません。 PowerBuilder ウィンドウを Web ページに含むには、Embed 要素を使い ます。要素の属性で、ウィンドウに割り当てる領域、PBD の名前、お よび PBD の中のチャイルド ウィンドウの名前を指定します。 Embed 要素は次のように指定します。 <EMBED SRC=plugin_tree.pbd WIDTH=370 HEIGHT=320 WINDOW=w_emp_by_dept> Embed 要素の属性 Embed 要素は、プラグインの HTML 仕様の一部です。HTML でいくつ かの標準属性を定義し、PowerBuilder で追加属性を定義します。 HTML 属性 738 HTML 属性で、クライアントにダウンロードするファイルの名前、お よび Web ページ上でプラグインに確保する領域を、以下のとおり指定 します。 PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 表 33-5: HTML Embed 要素属性 HTML 属性 SRC 値 ダウンロードされるオブジェクトを識別する ブラウザは、Embed 要素を処理するときに、サーバ にリソースを要求し、コンテンツ タイプを処理す る DLL をプラグイン ディレクトリから検索する WIDTH HEIGHT PowerBuilder ウィンドウ プラグインの場合、オブ ジェクトはアプリケーションを起動するチャイル ド ウィンドウを収めた PBD である 表示するウィンドウの幅。ピクセル値で指定する 表示するウィンドウの高さ。ピクセル値で指定する WIDTH 属性と HEIGHT 属性には、チャイルド ウィンドウの幅および 高さの最大値を定義します。チャイルド ウィンドウのサイズを変更で きる場合、指定のサイズより小さくできますが、大きくはできません。 PowerBuilder 属性 Embed 要素の PowerBuilder 属性で、アプリケーションを起動するウィ ンドウ オブジェクト、追加ライブラリ、アプリケーションに渡すパラ メータ、およびアプリケーション オブジェクトの名前を、以下のとお り識別します。 アプリケーション テクニック 739 HTML ページの作成 表 33-6: PowerBuilder Embed 要素属性 PowerBuilder 属性 WINDOW LIBRARY (オプション) 値 PBD 内のチャイルド ウィンドウのクラス名 アプリケーションに必要なオブジェクトを収めた 追加 PBD を指定する URL。PBD の相対 URL では なく絶対 URL を指定しなければならない 複数の LIBRARY 属性を指定できる。アプリケー ションに必要な追加の各 PBD に対して、LIBRARY 属性を指定する。SRC に指定されたファイルの LIBRARY 属性は指定しない COMMANDPARM (オプション) APPLICATION (オプション) LIBRARY 属性を使用した HTML コードの例につ いては、741 ページの「追加属性を持つ Embed 要 素」を参照 ウィンドウに渡す文字列。ウィンドウ内からこの文 字列にアクセスするには、CommandParm 関数を呼 び出す COMMANDPARM 属性を使用した HTML コードの 例については、741 ページの「追加属性を持つ Embed 要素」を参照 PBD 内のアプリケーション オブジェクトの名前 これを使用して、プラグイン アプリケーションはア プリケーション オブジェクトの Open イベントと Close イベント、およびアプリケーションで使うグ ローバル変数とグローバル関数にアクセスできる APPLICATION 属性を使用すると、アプリケーション オブジェクトの Open イベントと Close イベントは デフォルトで実行され、上書きできない。WINDOW 属性で指定されたチャイルド ウィンドウは、アプ リケーション オブジェクトの Open イベントでは 開かない。もし開けば、アプリケーションは異常終 了する APPLICATION 属性を使用した HTML コードの例 については、741 ページの「追加属性を持つ Embed 要素」を参照 サンプル ページ 次の HTML コードは、マスタ データウィンドウ コントロールと詳細デー タウィンドウ コントロールを持つウィンドウを表示する、PowerBuilder ウィンドウ プラグインを含むページを作成します。ここでは、Embed 要素を使用して PowerBuilder ウィンドウ プラグインを指定しています。 740 PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 始めの要素 <HTML> ドキュメント ヘッダ <HEAD> <TITLE>Master-Detail window</TITLE> </HEAD> <BODY> スモール イメージ <IMG SRC="undercon.gif" BORDER=0 HEIGHT=38 WIDTH=40> H1 ヘッダ <H1>Master-detail in a PB window plug-in</H1> 水平ルール <P><HR></P> パラグラフ <P> このウィンドウは、PB デモ データベースにアクセスして部門リス トを表示します。ユーザが部門の行をクリックすると、2 番目のデータ ウィンドウにその部門の従業員が表示されます。</P> パラグラフの中の Embed 要素 <P><EMBED SRC=plugin_tree.pbd WIDTH=370 HEIGHT=320 WINDOW=w_emp_by_dept> </P> サイトのホームページ へのリンク <LI>Back to <A HREF="http://www.mycompany.com/index.html">Home Page</A> </LI> 終わりの要素 </BODY> </HTML> 追加属性を持つ Embed 要素 プラグイン アプリケーションで追加ライブラリ、COMMANDPARM 文 字列、および PBD のアプリケーション オブジェクトにアクセスする ための APPLICATION 属性を使用する場合、Embed 要素を以下のとお り指定します。 <EMBED SRC=plugin_tree.pbd WIDTH=370 HEIGHT=320 WINDOW=w_emp_by_dept LIBRARY=http://www.mycompany.com/pb/extra1.pbd LIBRARY=http://www.mycompany.com/pb/extra2.pbd COMMANDPARM="Eastern region" APPLICATION=plugin_tree> アプリケーション テクニック 741 サーバの設定 サーバの設定 プラグイン アプリケーションを表示するための HTML ページを定義 したら、次に Web サーバを設定します。 MIME の種類の指定 Web サーバに所定のソフトウェアを使用して、PowerBuilder ウィンドウ プラグインの MIME の種類を登録します。表 33-7 に、使用できる MIME の種類を示します。 表 33-7: PowerBuilder ウィンドウ プラグイン MIME タイプ プラグイン 標準 PowerBuilder ウィン ドウ プラグイン セキュリティ PowerBuilder ウィンドウ プラグイン 登録する MIME の種類 application/vnd.powerbuilder11.0 application/vnd.powerbuilder11.0-s MIME のファイル拡張子は PBD です。 サーバのマニュアルによっては、MIME の種類ではなく、内容の種類 という用語を使用する場合もあります。 サーバへのファイルの 配置 PowerBuilder ライブラリと HTML ファイルをサーバ上の所定のディレ クトリにコピーします。 表 33-8: サーバ上の PBD ファイルと HTML ファイルの場所 ファイル HTML ページ 場所 HTML ドキュメント ディレクトリ Embed 要素の SRC 属 性および LIBRARY 属 性で指定される PBD ファイル HTML ドキュメント ディレクトリか、ほか の適切なディレクトリ 実行方法 HTML ページを、ページ にリンクする URL で指定 されるディレクトリにコ ピーする PBD ファイルを Embed 要 素の属性で指定したディ レクトリにコピーする URL について HTML ページに指定する URL は、Web サーバで定義さ れる論理パスです。たとえば、Windows では、PBD のシステム パスは 以下のようになります。 C:\WEBSITE\HTDOCS\PB\PLUGIN_APP.PBD htdocs がサーバのドキュメント ディレクトリに定義されれば、Embed 要素の SRC 属性を指定するとき次の相対パスを使えます。このパス は、ドキュメント ディレクトリに対する相対パスです。 pb/plugin_app.pbd 742 PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 LIBRARY 属性の場合、PBD に相対 URL を指定しないでください。以 下のような絶対 URL を指定しなければなりません。たとえば、次のよ うになります。 http://www.mycompany.com/pb/plugin_app.pbd ユーザのワークステーションの設定 プラグイン アプリケーションの構築、その HTML ページの作成、およ びサーバの設定が終了したら、次はプラグイン アプリケーションを表 示できるようにクライアント ワークステーションを設定する必要が あります。 PowerBuilder ウィンドウ プラグイン アプリケーションを含む Web ページを表示するには、クライアント ワークステーションでインス トールされるソフトウェアをサポートする必要があります。また、Web サーバにも接続しなければなりません。 必要なコンポーネント PowerBuilder ウィンドウ プラグイン アプリケーションを含む Web ペー ジを表示するには、各クライアント ワークステーションで表 33-9 に示 すコンポーネントが必要です。 アプリケーション テクニック 743 ユーザのワークステーションの設定 表 33-9: PowerBuilder ウィンドウ プラグインの表示に必要なクライアント 要件 コンポーネント インターネット接続か イントラネット接続 Netscape プラグインを サポートする Web ブラ ウザ PowerBuilder 配布 DLL 詳細 企業内で、またはインターネット サービス プロバ イダから利用できる ブラウザ ベンダから利用できる。以下のようなブ ラウザが必要である • Netscape Navigator バージョン 3.x 以降 • Microsoft Internet Explorer バージョン 3.x から 5.5 Service Pack 1 まで。Internet Explorer 5.5 Service Pack 2 以降のバージョンはプラグインを サポートしていない PowerBuilder ランタイム DLL をインストールす る。866 ページの「PowerBuilder ランタイム ファイ ル」を参照 PowerBuilder ランタイム DLL は、アプリケーショ ン ディレクトリか、システム パス上のディレクトリ に置く。PowerBuilder ウィンドウ プラグイン DLL は、PowerBuilder ランタイム DLL の場所がわから なければならない。そのためには、PowerBuilder 配 布 DLL のディレクトリをシステム パスに追加す るか、ディレクトリをブラウザのアプリケーショ ン パス キーに追加する(Windows レジストリ) 標準またはセキュリ この DLL がない場合には、NPPBA110.DLL ファイ ティ PowerBuilder ウィ ル(標準)または NPPBS110.DLL ファイル(セキュ ンドウ プラグイン DLL リティ)を Internet Tools\Plugins ディレクトリから ブラウザの Plugins ディレクトリにコピーする その他のファイル 画像ソースを PBD に入れていない場合、ファイル がオブジェクトのプロパティで指定されるパス上 になければ、そのパスにコピーする プラグイン アプリケーションがデータベースに接 続する場合、DBMS のクライアント ソフトウェア をセットアップする。クライアント マシンから DBMS に接続する方法については、 『データベース との接続』マニュアルを参照 Web ページとプラグイン アプリケーションの表示 必要なソフトウェアをインストールしたら、Web ページとプラグイン アプリケーションを表示できます。 ユーザが Web ページの URL を指定すると、以下のことが行われます。 744 PowerBuilder 第 33 章 PowerBuilder ウィンドウ プラグインの使い方 • PowerBuilder ウィンドウに割り当てられた領域に、ページ上のテキ ストが表示される • クライアントがサーバから PBD をダウンロードする • ブラウザが Web ページ内にチャイルド ウィンドウを表示する • ウィンドウの中のコントロールと対話し、イベントのスクリプト を実行する • ユーザがページから離れると、ウィンドウが閉じ、PowerBuilder DLL がメモリからアンロードされる アプリケーション テクニック 745 ユーザのワークステーションの設定 746 PowerBuilder 第 3 4 章 PowerBuilder ウィンドウ ActiveX の使い方 この章について この章では、PowerBuilder ウィンドウ ActiveX の使い方について説 明します。 内容 項目 PowerBuilder ウィンドウ ActiveX について PowerBuilder アプリケーションの作成 HTML ページの作成 PowerBuilder ウィンドウ ActiveX のイベント サーバの設定 ユーザのワークステーションの設定 ページ 747 752 759 773 774 774 PowerBuilder ウィンドウ ActiveX について PowerBuilder ウィンドウ ActiveX を使用すると、ActiveX をサポー トするブラウザに表示される Web ページに、PowerBuilder のチャ イルド ウィンドウを表示できます。 機能 PowerBuilder ウィンドウには、データウィンドウ、OLE オブジェ クト、OCX(ActiveX)コントロール、およびツリービュー コント ロールなど、通常使用しているすべてのコントロールを表示でき ます。また、チャイルド ウィンドウからポップアップ ウィンドウ またはレスポンス ウィンドウを開くことも可能です。 ユーザがウィンドウ内のコントロールを操作すると、スタンドア ロンの PowerBuilder アプリケーションの場合と同様、そのコント ロールのイベント スクリプトが実行されます。また、HTML ペー ジ内に VBScript や JavaScript を記述することにより、PowerBuilder 関数を呼び出して PowerBuilder イベントに応答する処理を実行で きます。 アプリケーション テクニック 747 PowerBuilder ウィンドウ ActiveX について PowerBuilder ウィンドウ ActiveX アプリケーションからのデータベー ス アクセスは、クライアントのローカル定義データベース接続を使用 して行われます。 アプリケーション内のオブジェクトを、1 つまたは複数の PowerBuilder 動的ライブラリ(PBD: PowerBuilder Dynamic Library)に含めることが できます。 サポートするブラウザ PowerBuilder ウィンドウ ActiveX を利用するには、ActiveX をサポート する、Microsoft Internet Explore などのブラウザが必要です。 PowerBuilder ウィンドウ ActiveX で動作するアプリケーションの種類 HTML フォームでは、限られたユーザ インタフェースを介した対話処 理しかできません。PowerBuilder ウィンドウ ActiveX は、HTML を超 える能力を提供します。リッチ ユーザ インタフェース設計で開発され たアプリケーション ウィンドウを、Web ページに表示できます。クラ イアント ワークステーションで定義されているデータ ソースにアク セスできます。 例 748 アプリケーションには以下のものがあります。 • マスタ データウィンドウと詳細データウィンドウを持つデータ解 析ウィンドウ • ユーザによる選択を、ツリービュー、リストビュー、およびピク チャ リストボックス コントロールから行うユーザ インタフェー スの設計 • サーバ上のデータを処理するデータ入力フォーム • クライアント定義によるデータベース接続(ネットワークまたは ローカル)を使用してクライアント マシン上のデータを処理する データ入力フォーム • PowerBuilder の OLEControl コントロールを使用して ActiveX コン トロールを表示するウィンドウ PowerBuilder 第 34 章 PowerBuilder ウィンドウ ActiveX の使い方 PowerBuilder ウィンドウ ActiveX の機能 PowerBuilder ウィンドウ ActiveX は、Web ページ上にあらかじめ割り 当てられた固定領域内に PowerBuilder のチャイルド ウィンドウを表示 します。ユーザはページ上のコントロールと対話でき、ウィンドウと そのコントロールの PowerBuilder スクリプトはどの PowerBuilder コー ドでも実行できます。ユーザが別の Web ページに移ると、PowerBuilder ウィンドウは閉じ、PowerBuilder DLL がメモリからアンロードされま す。 PowerBuilder ウィンドウ ActiveX は、HTML Object 要素を使用して HTML ページに貼り付けられます。HTML Object 要素は、PowerBuilder オブ ジェクト、HTML ページに表示されるチャイルド ウィンドウの名前、 および PowerBuilder アプリケーション オブジェクト(オプション)を 含んだ 1 つまたは複数の PBD を指定します。 セキュリティ セキュリティが設定されていないアプリケーションでは、ローカル ファイルへのアクセスおよびローカル アプリケーションの実行が可 能です。このような処理は、制御のない Web 環境では好まれないこと が多いですが、アクセスが制御される企業イントラネットでは許容さ れる場合もあります。PowerBuilder ウィンドウ ActiveX には、セキュ リティ付き(PBRXS110.OCX)とセキュリティなし(PBRX110.OCX) の 2 種類があります。セキュリティ付きの場合は厳しい制約があり、 クライアント ワークステーションへのアクセスが認められていませ ん。 セキュリティ モードで常に動作するイベントがある PowerBuilder では、標準バージョンのウィンドウ ActiveX を使用して いたとしても、アプリケーションの「Open イベント」およびコント ロール用のいくつかの「Constructor イベント」がセキュリティ モード で動作します。アプリケーションのロジックが、書き込み用のファイ ル オープンなど、これらのイベントでの非セキュリティ活動を実行す る能力に依存する場合には、イベント メッセージをアプリケーション やコントロールに対してポストするようにしてください。このイベン ト メッセージは、ウィンドウ ActiveX が標準モードに戻ったときに処 理されます。 要件 PowerBuilder ウィンドウ ActiveX は、ActiveX そのものと PowerBuilder 仮想マシンを使用して、PowerBuilder のあらゆる機能を提供します。 各クライアントが PowerBuilder ウィンドウ ActiveX の貼り付けられた ページを参照するには、以下の支援ソフトウェアがローカル マシンに インストールされている必要があります。 アプリケーション テクニック 749 PowerBuilder ウィンドウ ActiveX について • PowerBuilder 仮想マシン(PBVM110.DLL とサポート ファイル) • PowerBuilder ウィンドウ ActiveX PowerBuilder ウィンドウ ActiveX は、開発者がクライアント マシンの セットアップを管理するイントラネット アプリケーションで特に便 利です。 PowerBuilder ウィンドウ ActiveX のインストールと設定 PowerBuilder のインストール時に標準セットアップを選択した場合、 PowerBuilder ウィンドウ ActiveX コントロールはコンピュータにイン ストールされません。ActiveX コントロールをインストールするには、 PowerBuilder のカスタム インストールを実行し、 [コンポーネントの選 択]ページで[Web プラグイン]チェックボックスをオンにします。 インストールするプラグインとコントロールを選択するには、その ページの[変更]ボタンをクリックします。 この節では、ウィンドウ ActiveX のインストール後に行う必要がある 設定作業について説明します。 インストール先 PowerBuilder ウィンドウ ActiveX ファイル(セキュリティ付きおよび セキュリティなしの両バージョン)は、\Sybase\Shared\PowerBuilder ディレクトリにインストールされます。 ActiveX の登録 PowerBuilder ウィンドウ ActiveX で開発を行うには、マシンに ActiveX を登録しなければなりません。PowerBuilder オブジェクト ブラウザを 使用すると、登録状況をチェックできます。オブジェクト ブラウザを 開いて、 [OLE]タブを選択し、OLE カスタム コントロール項目を展開 します。ActiveX が登録されていれば、ツリー ビューの中に PowerBuilder Window Control または PowerBuilder Secure Window Control として表示 されます。クラス情報ノードを展開すると、現在登録されているコン トロールのバージョンを確認できます。 ActiveX をマシンに登録していない場合には、PowerBuilder 内から登録 するか、MS-DOS の regsvr32 コマンドを使用して登録できます。 750 PowerBuilder 第 34 章 ❖ PowerBuilder ウィンドウ ActiveX の使い方 PowerBuilder 内から ActiveX を登録するには 1 PowerBuilder から新規または既存のアプリケーションを開きます。 次に、新規または既存のウィンドウを開きます。 2 メニューから[挿入|コントロール| OLE]を選択します。 オブジェクトの挿入 ダイアログボックスが表示されます。 3 [コントロールの挿入]タブを選択して、 [登録]ボタンをクリッ クします。 参照 ダイアログボックスが表示されます。 4 System ディレクトリ内の OCX の保存場所に移動し、 PBRX110.OCX か PBRXS110.OCX のどちらかを選択して、[開く] をクリックします。 OCX がうまく登録されないと、エラー メッセージが表示されます。 ❖ MS-DOS の regsvr32 コマンドを使用して ActiveX を登録するには • 引数として OCX のフル パスを指定して、MS-DOS の regsvr32.exe コマンドを実行します。たとえば、次のようにスクリプトを記述 します。 regsvr32.exe C:\Windows\System32\pbrx110.ocx PowerBuilder ウィンドウ ActiveX アプリケーションの開発と配布 PowerBuilder ウィンドウ ActiveX アプリケーションの開発には、主な 4 つの作業があります。 ❖ PowerBuilder ウィンドウ ActiveX アプリケーションの作成および配布を行 うには 1 PowerBuilder アプリケーションを作成、テスト、および構築します。 2 PowerBuilder アプリケーション ウィンドウなどを貼り付ける HTML ページを作成します。 3 アプリケーションで使用する HTML ページと PBD ファイルを適 切なディレクトリにコピーして、Web サーバの設定を行います。 4 すべてのクライアント アプリケーション上で、PowerBuilder ウィ ンドウ ActiveX コントロールと PowerBuilder ランタイム DLL をイ ンストールします。 アプリケーション テクニック 751 PowerBuilder アプリケーションの作成 結果のコンポーネント セットアップがすべて終了すると、表 34-1 に示すコンポーネントが サーバおよびクライアント コンピュータに設定されます。 表 34-1: PowerBuilder ウィンドウ ActiveX アプリケーション用のサーバお よびクライアントの環境設定 コンピュータ サーバ クライアント コンポーネント ウィンドウまたはレポートの Object 要素を貼り付けた HTML ページと PBD ファイル インストールおよび登録された PowerBuilder ウィンドウ ActiveX(オプション) チャイルド ウィンドウとほかの PowerBuilder オブジェク トを含んだ 1 つまたは複数の PBD ファイル インストールおよび登録された PowerBuilder ウィンドウ ActiveX 第 41 章「アプリケーションとコンポーネントの配布」で 記述されているようにインストールした PowerBuilder ラ インタイム DLL システム パスに記述された PowerBuilder ランタイム DLL のディレクトリ Microsoft DLL: MFC42.DLL MSVCRT.DLL URL.DLL URLMON.DLL データベース接続ソフトウェア、OLE サーバ、ActiveX コ ントロールなど、PowerBuilder ウィンドウ ActiveX アプリ ケーションで必要なその他のアプリケーション PowerBuilder アプリケーションの作成 PowerBuilder ウィンドウ ActiveX アプリケーションは、Web ページに 表示されるチャイルド ウィンドウから起動します。ウィンドウ内に は、コントロールを配置してイベント スクリプトを記述できます。ス クリプトからは、ほかのウィンドウを開く、ファイルを読み書きする、 クライアント マシン上のほかのプログラムを実行するなどの操作が 行えます。 752 PowerBuilder 第 34 章 PowerBuilder ウィンドウ ActiveX の使い方 アプリケーションのデザイン PowerBuilder ウィンドウ ActiveX 用に設計するアプリケーションは、通 常開発する PowerBuilder アプリケーションとほとんど変わりません が、いくつかの制限事項と留意事項があります。この節では、以下の 項目について説明します。 ウィンドウ管理 • ウィンドウ管理 • スクリプトと変数 • データ アクセス • 外部ファイル 初期チャイルド ウィンドウ 初期ウィンドウは、ブラウザ フレーム内に 存在するチャイルド ウィンドウでなければなりません。 以下の制限があります。 • チャイルド ウィンドウのメニューを配置する • 初期ウィンドウから別のチャイルド ウィンドウを開く 以下のことが可能です。 • チャイルド ウィンドウでタイトル バーを使用する。ただし、チャ イルド ウィンドウでは、コントロール メニュー、最大化ボタン、 または最小化ボタンは使用しない • チャイルド ウィンドウから、ポップアップ ウィンドウまたはレス ポンス ウィンドウを開く。メイン ウィンドウまたは MDI ウィン ドウは開けない ウィンドウを閉じる クライアントが別の Web ページを参照すると、現 行の Web ページのチャイルド ウィンドウは閉じますが、ほかのウィンド ウはアプリケーションから閉じない限り、開いています。これらのウィン ドウは、チャイルド ウィンドウの Close イベントまたは CloseQuery イベ ントで閉じなければなりません。 戻り値を設定して、CloseQuery イベントでチャイルド ウィンドウが閉 じないようにする処理は行わないでください。ブラウザが別のページ に移らないようにしたり、ビューからウィンドウを削除できないよう にしたりすることはできません。ユーザが前のページに戻ったときに、 アプリケーションの別のインスタンスが起動されます。 オブジェクト PBD 内のオブジェクト PowerBuilder ウ ィ ン ド ウ ActiveX ア プ リ ケ ー ションは、PBD の中のオブジェクトすべてにアクセスできます。関数、 構造体、ユーザ オブジェクトにもアクセスできます。 アプリケーション テクニック 753 PowerBuilder アプリケーションの作成 PowerBuilder ウ ィ ン ド ウ ActiveX ア プ リ ケ ー ションは、SQLCA Transaction オブジェクトや Message オブジェクトな ど、PowerBuilder がインスタンスを生成するシステム オブジェクトに アクセスできます。 システム オブジェクト PowerBuilder ウィンドウ ActiveX アプ リケーションは、アプリケーション オブジェクトのプロパティである グローバル変数にアクセスできます。 アプリケーション オブジェクト PowerBuilder では、開発中は現行のアプリケーション オブジェクトが 必要ですが、アプリケーションで使用されるのは Open イベントとグ ローバル変数だけです。アプリケーション オブジェクトのほかのスク リプトは、PowerBuilder でテストを行う際に必要となります。 スクリプトと変数 アプリケーションをセットアップするスクリプト HTML で PBAPPLICATION パラメータを指定すると、PowerBuilder ウィンドウ ActiveX はチャイ ルド ウィンドウを開く前に、アプリケーションの Open イベントを発 生させます。このイベントを利用して、データベース接続の構築およ びグローバル変数の初期化を行うことができます。 HTML で開くウィンドウを指定する アプリケーションの Open イベントでウィンドウを開かないでください。 HTML で PBAPPLICATION パラメータを指定しないと、DBMS への接 続などアプリケーションのセットアップをすべてチャイルド ウィン ドウ内で行わなければなりません。スクリプトが記述可能なイベント で、最初に発生するのはウィンドウのコントロールの Constructor イベ ントで、次に発生するのは、そのウィンドウの Open イベントです。 Activate イベントは、チャイルド ウィンドウに対しては発生しません。 したがって、そこでアプリケーションのセットアップを行わないでく ださい。 グローバル変数 PowerBuilder ウィンドウ ActiveX アプリケーション は、グローバル変数にアクセスできます。 初期ウィンドウの参照 PowerBuilder は、初期チャイルド ウィンドウの インスタンスを保持する変数を作成しないので、スクリプトで名前を 使用して初期チャイルド ウィンドウを参照することはできません。逆 に、Open 関数のスクリプトを記述してウィンドウのインスタンスを生 成すれば、そのインスタンスを変数に代入して参照できます。 したがって、以下のスクリプトは、ウィンドウ変数 w_mychild が存在し ないため、実行時エラーになります。 // 以下のスクリプトは、実行時エラーとなります。 754 PowerBuilder 第 34 章 PowerBuilder ウィンドウ ActiveX の使い方 w_mychild.title = "The initial window" 次のスクリプトはエラーになりません。 // チャイルド ウィンドウ自体で this.title = "The initial window" // または title = "The initial window" // チャイルド ウィンドウのコントロール内で parent.title = "The initial window" データ アクセス アプリケーションから DBMS にアクセスする場合、各クライアントは データ ソースに接続しなければなりません。その接続は、サーバでは なくクライアント マシン上で定義される必要があります。データ ソー スは、ローカルまたはネットワーク DBMS のどちらでもかまいませ ん。 クライアント マシンから DBMS に接続する方法については、『データ ベースとの接続』マニュアルを参照してください。 ウ ィ ン ド ウ の Open イ ベ ン ト が 発 生 す る 前 に、コ ン ト ロ ー ル の Constructor イベントが発生します。つまり、ウィンドウの Open イベン トで DBMS に接続した場合、Constructor イベントはデータを取得でき ません。ウィンドウの Open イベントでコントロールのデータを取得 するか、Constructor イベントまたはウィンドウの Open イベントからイ ベントをポストしてください。 外部リソースのパス ファイルに指定するパスは、クライアント ワークステーションで有効 でなければなりません。 アプリケーションで外部ファイルとして画像を使用する場合、その画 像は PowerBuilder オブジェクトに指定されたパスで取得できなければ なりません。外部ファイルを使用するかわりに、PBD に画像リソース を組み込むことも可能です。 アプリケーションでローカル ファイルを読み書きする場合、それらの ファイルのパスは各クライアント マシンで有効なものでなければな りません。 Windows 環境で、ネットワーク ドライブを参照するパスに、割り当て られたネットワーク ドライブのドライブ名を使用すると、すべてのク ライアントでそれと同じドライブ名を使わなければなりません。また、 サーバ名をパスで指定することもできます。 たとえば、o: が \\marketing\drive に割り当てられている場合、以下の パスはどちらも有効です。ただし、ドライブ名は変更の可能性がある ので、サーバ名を指定している 2 番目のパスの方が有効です。 アプリケーション テクニック 755 PowerBuilder アプリケーションの作成 O:\pbapps\connect.bmp \\marketing\drive\pbapps\connect.bmp ウィンドウ ペインタでの開始ウィンドウの定義 PowerBuilder 内のアプリケーション用の開始ウィンドウを作成します。 ❖ ❖ アプリケーションの開始ウィンドウを作成するには 1 PowerBuilder でウィンドウ オブジェクトを新規作成します。 2 プロパティ ビューのウィンドウの[全般]タブで、ウィンドウの 種類を「child!」に設定します。 3 必要な場合は、ほかのコントロールを追加します。 4 ウィンドウとコントロールのイベント スクリプトを記述します。 既存のアプリケーションを PowerBuilder ウィンドウ ActiveX として実行で きるように変換するには 1 開いているウィンドウの種類を「child!」に変更します。 2 アプリケーションのセットアップ コードを、アプリケーションの Open イベントまたは MDI フレーム イベントからチャイルド ウィ ンドウの Open イベントに移動します。 アプリケーションの設計によっては、ほかのウィンドウを開く方法を 設計し直さなければならない場合もあります。 チャイルド ウィンド ウについて 756 チャイルド ウィンドウにメニューを配置することはできません。チャ イルド ウィンドウはアクティブ ウィンドウとはみなされず、Activate イベントは発生しません。チャイルド ウィンドウには、タイトル バー を設定できます。また、最小化、最大化、およびサイズ変更も可能で す。ただし、PowerBuilder ウィンドウ ActiveX 環境では、チャイルド ウィンドウは、Web ページ上に指定された WIDTH 属性と HEIGHT 属 性によって割り当てられる領域内に表示されます。したがって、以下 のように制限されます。 • ウィンドウを最大化すると、WIDTH 属性と HEIGHT 属性で割り当 てられた領域内で最大表示される • ウィンドウを最小化すると、ウィンドウのアイコンとタイトルが ActiveX コントロールに割り当てられた領域の下端に表示される • チャイルド ウィンドウのサイズを変更できる場合は、枠線をドラッ グしてウィンドウを割り当て領域より小さくできる(割り当て領 域より大きくすることはできない) PowerBuilder 第 34 章 PowerBuilder ウィンドウ ActiveX の使い方 したがって、チャイルド ウィンドウの最小化、最大化、またはサイズ 変更は有効とはいえません。 PowerBuilder でのアプリーションのテスト 作成したアプリケーションをクライアント ブラウザで実行する前に、 PowerBuilder でチャイルド ウィンドウを開くメイン ウィンドウを定義 して、アプリケーションをテストできます。 ❖ PowerBuilder ウィンドウ ActiveX アプリケーションをテストするには 1 PowerBuilder の中で、種類がメイン(デフォルト)のウィンドウ オブ ジェクトを新規作成します。 2 チャイルド ウィンドウを開くスクリプトを Open イベントに記述 します。 Open(w_child) 3 ウィンドウ ペインタで、ウィンドウ サイズを以下のように設定す ると便利です。 • メイン ウィンドウのサイズは、チャイルド ウィンドウを十分 に表示できるサイズにする • チャイルド ウィンドウを左上隅に配置する。この設定は、プ ロパティ シートの[位置]タブで行う 4 [実行]アイコンをクリックして、テスト ウィンドウを実行します。 PowerBuilder でのデバッグ PowerBuilder デバッガを使用するには、ウィンドウだけを実行するの ではなく、アプリケーションを実行する必要があります。メイン ウィ ンドウを開くスクリプトで、アプリケーション オブジェクトを定義し ます。その後、 [実行]または[デバッグ]コマンドを使用してアプリ ケーションをテストします。 PBL 内でのオブジェ クトの編成 Web 環境では、ファイルのサイズが重要です。クライアントはアプリ ケーションを実行する場合、そのアプリケーションをごく最近実行し たばかりでキュッシュされているとき以外は、実行のたびにアプリ ケーションをダウンロードします。 アプリケーション テクニック 757 PowerBuilder アプリケーションの作成 アプリケーションを構築する前に、ライブラリ ペインタを使用して、 アプリケーションで使用する、PBL 内のオブジェクトを整理します。 PBL は、PowerBuilder ウィンドウ ActiveX アプリケーションの PBD の ソースになります。ファイル サイズを最小限に抑えるには、アプリ ケーションで使用するオブジェクトだけを入れ、不要なオブジェクト は削除します。以下のことを行う必要があります。 • データストアで使用されるデータウィンドウ オブジェクトなど、 動的に作成されるオブジェクト、またはデータウィンドウ コント ロールおよびプロキシ オブジェクトに動的に割り当てられるオブ ジェクトをすべて入れる • 先祖オブジェクトを入れる コントロールによっては、画像に外部ファイルを使用する場合もあり ます。たとえば、ピクチャ リストボックス コントロール、ツリービュー コントロール、ピクチャ コントロール、ピクチャボタン コントロー ル、ポインタ、データウィンドウ オブジェクトのビットマップ オブ ジェクトです。プラグイン アプリケーションで外部ファイルの画像を 使用する場合、クライアントで同じ画像が同じシステム パス上にない ことがあります。 PowerBuilder リソー ス(PBR)ファイル の使用 クライアント マシンにピクチャをインストールするかわりに、1 つま たは複数の PowerBuilder リソース(PBR: PowerBuilder Resource)ファ イルを使用して、PBD に画像を組み込むことができます。画像を組み 込むと PBD はサイズは大きくなりますが、独立して機能します。 作成するのは実行ファイルではなく PBD なので、リソース ファイル にデータウィンドウ オブジェクトを含める必要はありません。作成後 の PBD には、ソース PBL 内のすべての PowerBuilder オブジェクトが 含まれます。 ネットワーク上の画像やそのほかのリソース PBD にファイルを組み込むかわりに、広くアクセスされるネットワー ク ディレクトリにファイルを格納することも可能です。ただし、この 場合、ファイルへのパスは、PowerBuilder オブジェクトでのパスと同 じでなければなりません。つまり、Windows 環境では、各クライアン トは、ネットワーク ドライブが割り当てられた同じドライブ名を使用 しなければなりません。パスにサーバ名を指定することも可能です。 ❖ PBR ファイルを定義するには 1 〔Shift〕+〔F6〕を押してファイル エディタを開くか、ほかのテキス ト エディタを開き、拡張子 .PBR の新しいファイルを作成します。 758 PowerBuilder 第 34 章 2 PowerBuilder ウィンドウ ActiveX の使い方 画像やほかのリソースを、各行に一覧表示します。オブジェクト のプロパティ ビューまたはスクリプトに表示される同じ形式でパ スとファイル名を記述します。 ショートカット オブジェクトのプロパティ ビューを表示し、 [編集|コピー] (Windows では〔Ctrl〕+〔C〕)を使用して、ファイル名をクリップ ボードにコピーします。次に、このファイル名をエディタに貼り 付けます。 3 ファイルを保存します。 アプリケーションに複数の PBL が含まれ、各 PBL にそれぞれのリソー スを使用するオブジェクトが含まれている場合は、各 PBL に対して PBR ファイルを作成する必要があります。PBR ファイルは、1 つの PBL 内で使用されるリソースのファイル名をリストします。 PBD の構築 システム ツリー、プロジェクト ペインタ、またはライブラリ ペイン タを使用して、動的ライブラリ(PBD)を構築します。構築する手順 は次のとおりです。 • マシン コードの選択解除 PowerBuilder ウィンドウ ActiveX アプリ ケーションには、マシン コード DLL ではなく PBD が必要です。 • PBR ファイルを各 PBD に指定する PBR ファイルにリストしたリ ソースを PBL 内のオブジェクトで使用する場合は、PBR 名を[ソー ス ファイル]テキストボックスに入力します。 PBR ファイルの定義および動的ライブラリ(PBD)の構築方法につい ては、『ユーザーズ ガイド』マニュアルで実行ファイルの作成に関す る章を参照してください。 HTML ページの作成 PowerBuilder ウィンドウ ActiveX アプリケーションの PowerBuilder PBD を作成および構築したら、次はそれを表示する HTML ページを作成す る必要があります。 アプリケーション テクニック 759 HTML ページの作成 Web ページに PowerBuilder ウィンドウを貼り付けるには、Object 要素 を使います。要素属性には、PowerBuilder ウィンドウ ActiveX のクラ ス ID、ウィンドウに割り当てる領域、PBD 名、PBD 内のチャイルド ウィンドウ名、ライブラリ リスト、および PowerBuilder のバージョン を指定します。 Object 要素のサンプルを以下に示します。 <OBJECT NAME="PBRX1" WIDTH=225 HEIGHT=83 CLASSID="CLSID:BBBB1304-BBBB-1000-8000-080009AC61A9"> <PARAM NAME="_Version" VALUE="65536"></PARAM> <PARAM NAME="_ExtentX" VALUE="5962"></PARAM> <PARAM NAME="_ExtentY" VALUE="2164"></PARAM> <PARAM NAME="_StockProps" VALUE="0"></PARAM> <PARAM NAME="PBWindow" VALUE="w_helloworld"></PARAM> <PARAM NAME="LibList" VALUE="http://www.company.com/rknnt.pbd;"></PARAM> <PARAM NAME="PBApplication" VALUE="hello"></PARAM> <PARAM NAME="PBVersion" VALUE="100"></PARAM> </OBJECT> Object 要素の属性 Object 要素は、HTML で ActiveX コントロールを指定するときに一緒に 指定します。これによって、いくつかの標準属性を定義し、PowerBuilder で追加属性を定義します。 HTML 属性 760 HTML 属性では、クラス ID、名前、および Web ページ上で PowerBuilder ウィンドウ ActiveX に割り当てる領域を指定します。 PowerBuilder 第 34 章 PowerBuilder ウィンドウ ActiveX の使い方 表 34-2: Object 要素の HTML 属性 HTML 属性 NAME CLASSID 値 スクリプトで参照される場合またはフォームの一部と して発行される場合のオブジェクト名 登録される ActiveX コントロールのクラス ID 構文は次のとおりです。 CLSID:class_id CODEBASE WIDTH HEIGHT 登録済みの ActiveX コントロールのクラス ID 値を検 索する場合には、PowerBuilder オブジェクト ブラウザ の[OLE]タブを使用できる。OLE カスタム コント ロール項目を展開し、次に PowerBuilder Window Control 項目または PowerBuilder Secure Window Control 項目を 展開する。クラス ID は、クラス情報分岐の GUID 項目 の値になる クライアント マシンに PowerBuilder ウィンドウ ActiveX がない場合にダウンロードする OCX または CAB ファイルの場所を識別する URL クライアント マシンには PowerBuilder 仮想マシンが必 要。また、システム パス上にそのほか必要な DLL が 存在しなければならない 表示するウィンドウの幅。ピクセル値で指定する 表示するウィンドウの高さ。ピクセル値で指定する WIDTH 属性と HEIGHT 属性には、チャイルド ウィンドウの幅および 高さの最大値を定義します。チャイルド ウィンドウのサイズを変更で きる場合、指定のサイズより小さくできますが、大きくはできません。 Param 要素 PowerBuilder ウィンドウ ActiveX のプロパティを指定するには、Param 要素などを設定します。Param 要素によって、アプリケーションを起 動するウィンドウ オブジェクト、アプリケーション オブジェクト、追 加ライブラリ、および PowerBuilder ウィンドウ ActiveX に渡す追加パ ラメータを識別できます。表 34-3 に、PowerBuilder 固有の Param 要素 を示します。 アプリケーション テクニック 761 HTML ページの作成 表 34-3: PowerBuilder ウィンドウ ActiveX の Param 構成要素 プロパティ PBWINDOW LIBLIST PBAPPLICATION (オプション) PBVERSION DISPLAYRUNTIME MESSAGES (オプション) COMMANDPARM (オプション) 値 PBD 内のチャイルド ウィンドウのクラス名 アプリケーションで必要な PowerBuilder 動的ライブ ラリ(PBD ファイル)のリスト。複数指定する場合 はセミコロンで区切る PowerBuilder アプリケーション オブジェクト PowerBuilder DLL のバージョン(例:110) Boolean 型の値。実行時エラーを表示するかどうかを 指定する ウィンドウに渡す文字列。ウィンドウ内からこの文 字列にアクセスするには、CommandParm 関数を呼び 出す Object 要素の記述 コーディング時のエラーを最小限に抑えるには、JSP ターゲットの HTML エディタ、ActiveX Control Pad、Front Page などの ActiveX 対応 の HTML エディタを使用して Object 要素やパラメータを記述します。 762 PowerBuilder 第 34 章 PowerBuilder ウィンドウ ActiveX の使い方 基本ページ 次のサンプル ページには、PowerBuilder ウィンドウ ActiveX が貼り付 けてあります。 以下に示すのは、このページを作成するための HTML コードです。 Object 要素を使用して、PowerBuilder ウィンドウ ActiveX を指定してい ることに注目してください。 <HTML> <HEAD> <TITLE>Employee List</TITLE> </HEAD> <BODY> <H1>PowerBuilder window ActiveX</H1> <P> <OBJECT ID="PBRX1" NAME="PBRX1" WIDTH=357 HEIGHT=269 CLASSID="CLSID:BBBB1304-BBBB-1000-8000-080009AC61A9"> <PARAM NAME="_Version" VALUE="65536"> <PARAM NAME="_ExtentX" VALUE="9440"> <PARAM NAME="_ExtentY" VALUE="7112"> アプリケーション テクニック 763 HTML ページの作成 <PARAM NAME="_StockProps" VALUE="0"> <PARAM NAME="PBWindow" VALUE="w_emplist"> <PARAM NAME="LibList" VALUE="http://www.company.com/rknnt.pbd;"> <PARAM NAME="PBApplication" VALUE="rknnt"> <PARAM NAME="PBVersion" VALUE="110"> </OBJECT> </BODY> </HTML> クライアント側のスクリプト HTML ページに JavaScript または VBScript を追加することにより、 PowerBuilder ウィンドウ ActiveX 内に表示されるウィンドウと対話で きます。以下のことを行うことができます。 • ウィンドウ内で発生するイベントに応答するためのイベント ハン ドラを記述する • PowerScript 関数を呼び出して、ポインタ情報の取得、印刷、再描 画の設定、およびタイマー設定を行う • InvokePBFunction 関数を呼び出して、ユーザ定義ウィンドウ関数を 起動する • TriggerPBEvent 関数を呼び出して、ウィンドウでユーザ イベントを 発生させる ActiveX のプロパティ、イベント、および関数の表示 ウィンドウ ActiveX をマシンに登録しているときには、PowerBuilder オ ブジェクト ブラウザの[OLE]タブを使用して、ウィンドウ ActiveX のプロパティ、イベント、および関数のリストを見ることができます。 イベント ハンドラの 記述 HTML ページには、PowerBuilder ウィンドウ ActiveX を制御するため に、JavaScript または VBScript イベント ハンドラを記述できます。 コーディング例の前提条件 次のコード例は、HTML ページに Form という名前の buttonForm が含 まれていることを想定したものです。このフォームには、複数の入力 要素として、passedFlags、passedXPos、および passedYPos が含まれます。 764 PowerBuilder 第 34 章 ❖ PowerBuilder ウィンドウ ActiveX の使い方 PowerBuilder ウィンドウ ActiveX を制御する JavaScript イベント ハンド ラを記述するには 1 PowerBuilder ウィンドウ ActiveX を HTML ページに挿入して、必 要なすべてのプロパティを指定します。 <OBJECT NAME="PBRX1" WIDTH=225 HEIGHT=83 CLASSID="CLSID:BBBB1304-BBBB-1000-8000080009AC61A9"> <PARAM NAME="_Version" VALUE="65536"> <PARAM NAME="_ExtentX" VALUE="5962"> <PARAM NAME="_ExtentY" VALUE="2164"> <PARAM NAME="_StockProps" VALUE="0"> <PARAM NAME="PBWindow" VALUE="w_helloworld"> <PARAM NAME="LibList" VALUE="http://www.company.com/rknnt.pbd;"> <PARAM NAME="PBApplication" VALUE="rknnt"> <PARAM NAME="PBVersion" VALUE="110"> </OBJECT> 2 HTML ページのヘッダに、イベントが発生したときに呼び出され る関数を記述します。 次の関数サンプルは、Clicked イベントの引数の表示のみを実行し ます。 function wasClicked(flags, xpos, ypos) { document.buttonForm.passedFlags.value = flags; document.buttonForm.passedXPos.value = xpos; document.buttonForm.passedYPos.value = ypos; } 3 HTML ページの本体に、イベントが発生したときに関数を呼び出 すイベント ハンドラを記述します。 <SCRIPT LANGUAGE="JavaScript" FOR="PBRX1" Event="Clicked(flags, xpos, ypos)"> <!-wasClicked(flags, xpos, ypos); --> </SCRIPT> コーディング スタイル 次に示すように、イベント ハンドラ内にすべてのコードを記述し て、関数呼び出しを省略することも可能です。 アプリケーション テクニック 765 HTML ページの作成 ❖ PowerBuilder ウィンドウ ActiveX を制御する VBScript イベント ハンドラ を記述するには 1 PowerBuilder ウィンドウ ActiveX を HTML ページに挿入して、必 要なすべてのプロパティを指定します。 <OBJECT NAME="PBRX1" WIDTH=225 HEIGHT=83 CLASSID="CLSID:BBBB1304-BBBB-1000-8000080009AC61A9"> <PARAM NAME="_Version" VALUE="65536"> <PARAM NAME="_ExtentX" VALUE="5962"> <PARAM NAME="_ExtentY" VALUE="2164"> <PARAM NAME="_StockProps" VALUE="0"> <PARAM NAME="PBWindow" VALUE="w_helloworld"> <PARAM NAME="LibList" VALUE="http://www.company.com/rknnt.pbd;"> <PARAM NAME="PBApplication" VALUE="rknnt"> <PARAM NAME="PBVersion" VALUE="110"> </OBJECT> 2 HTML ページの本体に、イベントを処理するイベント ハンドラを 記述します。 次の関数サンプルは、Clicked イベントの引数の表示のみを実行し ます。 <SCRIPT LANGUAGE="VBScript"> <!-Sub PBRX1_Clicked(flags, xpos, ypos) document.buttonForm.passedFlags.value = flags document.buttonForm.passedXPos.value = xpos document.buttonForm.passedYPos.value = ypos end sub --> </SCRIPT> PowerScript 関数の呼 び出し PowerBuilder ウィンドウ ActiveX では、ActiveX コントロールに表示さ れるウィンドウ上で、以下の PowerScript 関数を呼び出すことができま す。 • PointerX ウィンドウの左端からポインタまでの距離を戻す • PointerY ウィンドウの上端からポインタまでの距離を戻す • Print ウィンドウを印刷する • SetRedraw 変更が加えられるたびにウィンドウを自動的に再描 画するかどうかを切り替える • Timer ウィンドウの Timer イベントを、指定した間隔で繰り返し 発生させる 766 PowerBuilder 第 34 章 PowerBuilder ウィンドウ ActiveX の使い方 これらの関数の詳細については、『PowerScript リファレンス』マニュ アルを参照してください。 すべての ActiveX コントロールと同様、 PowerBuilder ウィンドウ ActiveX では、AboutBox 関数を呼び出してコントロールについての情報を参照 できます。 コーディング例の前提条件 次のコード例は、PowerBuilder ウィンドウの Timer イベントによって 呼び出されるスクリプトをすでに作成していることを想定したもので す。 ❖ JavaScript を使用して PowerScript 関数を呼び出すには 1 PowerScript 関数を呼び出す関数を記述します。 次の例では、PowerScript の Timer 関数を呼び出します。 <SCRIPT LANGUAGE="JavaScript"> <!-var cumSeconds = 0; function setPBTimer( f ) { var li_return var li_interval li_interval = parseInt(f.timerInterval.value); li_return = PBRX1.Timer(li_interval); if (li_return != 1) { alert(" タイマーの設定に失敗しました "); } } //--> /SCRIPT 2 その関数を呼び出す関数、アンカー、またはボタンのスクリプト を記述します。 次の例では、フォーム上のボタンを使用して、手順 1 で定義した、 タイマー間隔をリセットする関数を呼び出します。 <FORM NAME="clockForm"> <P>Timer Interval: <INPUT TYPE=Text NAME="timerInterval" Size="5"> <P><INPUT TYPE=BUTTON VALUE="Set Timer" ONCLICK="setPBTimer(this.form)"> </FORM> アプリケーション テクニック 767 HTML ページの作成 ❖ VBScript を使用して PowerScript 関数を呼び出すには 1 PowerScript 関数を呼び出す関数を記述します。次の例では、 PowerScript の Timer 関数を呼び出します。 <SCRIPT LANGUAGE="VBScript"> <!-dim cumSeconds cumSeconds = 0 Sub pbSetTime() dim li_return dim li_interval li_interval = clockForm.timerInterval.value li_return = pbrx1.Timer(li_interval) if li_return 1 THEN msgBox " タイマーの設定に失敗しました " end if end sub //--> </SCRIPT> 2 その関数を呼び出す関数、アンカー、またはボタンのスクリプト を記述します。 次の例では、フォーム上のボタンを使用して、手順 1 で定義した、 タイマー間隔をリセットする関数を呼び出します。 <FORM NAME="clockForm"> <P>Timer Interval: <INPUT TYPE=Text NAME="timerInterval" Size="5"> <HR> <P>Mirror of PB Time: <INPUT TYPE=Text NAME="pbTime" Size="8"> <HR> <P>INPUT TYPE=BUTTON VALUE="Set Timer" onClick="call pbSetTime()"> </FORM> ユーザ定義関数の呼び 出し PowerBuilder ウィンドウ ActiveX には、InvokePBFunction 関数がありま す。この関数は、ユーザ定義ウィンドウ関数を呼び出します。 VBScript と JavaScript の違い ユーザ定義関数に引数がある場合、JavaScript では、SetArgElement 関数 を使用して引数を指定しなければなりません。つまり、InvokePBFunction 関数で明示的に引数を指定することはできません。 768 PowerBuilder 第 34 章 ❖ PowerBuilder ウィンドウ ActiveX の使い方 ユーザ定義関数を呼び出す JavaScript を記述するには 1 必要な場合は、ウィンドウ関数を定義します。 次の例は、PowerBuilder ウィンドウの中で、パラメータとして文字 列を受け取る関数 of_arg をすでに定義していることを想定したも のです。 2 InvokePBFunction 関数を呼び出す JavaScript 関数を記述し、実際に 呼び出すユーザ定義関数を指定します。 次の例では、引数を初期化し、ウィンドウ関数 of_arg を呼び出し ます。 function invokeFunc(f) { var retcd; var rc; var numargs; var theFunc; var theArg; retcd = 0; numargs = 1; theArg = f.textToPB.value; PBRX1.SetArgElement(1, theArg); theFunc = "of_arg"; retcd = PBRX1.InvokePBFunction(theFunc, numargs); rc = parseInt(PBRX1.GetLastReturn()); if (rc != 1) { alert(" エラー。空の文字列 "); } PBRX1.ResetArgElements(); } 3 JavaScript 関数を呼び出す関数、アンカー、またはフォーム ボタン を記述します。たとえば、次のようになります。 <FORM> <P> このテキストを PowerBuilder にコピーします。 <INPUT TYPE=Text NAME="textToPB" SIZE="20"> <P><INPUT TYPE=BUTTON VALUE="Invoke Func" ONCLICK="invokeFunc(this.Form)"> </FORM> JavaScript での引数の定義 JavaScript で記述する場合、関数とイベントの引数は、SetArgElement 関 数を呼び出して定義します。 アプリケーション テクニック 769 HTML ページの作成 ❖ ユーザ定義関数を呼び出す VBScript を記述するには 1 必要な場合は、ウィンドウ関数を定義します。 次の例は、PowerBuilder ウィンドウの中で、パラメータとして文字 列を受け取る関数 of_arg をすでに定義していることを想定したも のです。 2 InvokePBFunction 関数を呼び出す VBScript 関数を記述し、実際に呼 び出すユーザ定義関数を指定します。 次の例では、引数を初期化し、ウィンドウ関数 of_arg を呼び出し ます。 Sub invokeFunction() Dim retcd Dim myForm Dim args(1) Dim rc Dim numargs Dim theFunc Dim rcfromfunc retcd = 0 numargs = 1 rc = 0 theFunc = "of_arg" Set myForm = Document.buttonForm args(0) = buttonForm.textToPB.value retcd = PBRX1.InvokePBFunction(theFunc, numargs, args) rc = PBRX1.GetLastReturn() if rc 1 then msgbox " エラー。空の文字列 " end if PBRX1.ResetArgElements() end sub 3 関数、アンカー、またはクリックして VBScript 関数を呼び出す フォーム ボタンのスクリプトを記述します。たとえば、次のよう になります。 <FORM NAME="buttonForm"> <P><INPUT TYPE=Text NAME="textToPB" SIZE="20"> <P><INPUT TYPE=BUTTON VALUE="Invoke Function" ONCLICK="call invokeFunction()"> /FORM </FORM> 770 PowerBuilder 第 34 章 PowerBuilder ウィンドウ ActiveX の使い方 PowerBuilder ウィンドウ ActiveX には、TriggerPBEvent 関数があります。 この関数は、ウィンドウ上でユーザ イベントを発生させます。 ユーザ イベントの呼 び出し ❖ ユーザ イベントを発生させる JavaScript を記述するには 1 必要な場合は、ウィンドウのユーザ イベントを定義します。 次の例は、PowerBuilder ウィンドウの中で、引数として文字列を受 け取るユーザ イベント ue_arg をすでに定義していることを想定し たものです。 2 ユーザ イベントを呼び出す関数を記述します。次の例では、引数 を初期化し、ユーザ イベント ue_arg を呼び出します。 function triggerEvent(f) { var retcd; var rc; var numargs; var theEvent; var theArg; retcd = 0; numargs = 1; theArg = f.textToPB.value; PBRX1.SetArgElement(1, theArg); theEvent = "ue_arg"; retcd = PBRX1.TriggerPBEvent(theEvent, numargs); rc = parseInt(PBRX1.GetLastReturn()); if (rc != 1) { alert(" エラー。空の文字列 "); } PBRX1.ResetArgElements(); } 3 TriggerPBEvent 関数を呼び出す関数、アンカー、またはフォーム ボ タンのスクリプトを記述します。たとえば、次のようになります。 <FORM> <P><INPUT TYPE=Text NAME="textToPB" SIZE="20"> <P><INPUT TYPE=BUTTON VALUE="Trigger Event" ONCLICK="triggerEvent(this.Form)"> </FORM> ❖ ユーザ イベントを発生させる VBScript を記述するには 1 必要な場合は、ウィンドウのユーザ イベントを定義します。 次の例は、PowerBuilder ウィンドウの中で、引数として文字列を受 け取るユーザ イベント ue_arg をすでに定義していることを想定し たものです。 アプリケーション テクニック 771 HTML ページの作成 2 ユーザ イベントを呼び出す関数を記述します。次の例では、引数 を初期化し、ユーザ イベント ue_arg を呼び出します。 Sub TrigEvent( ) Dim retcd Dim myForm Dim args(1) Dim rc Dim numargs Dim theEvent retcd = 0 numargs = 1 rc = 0 theEvent = "ue_arg" Set myForm = Document.buttonForm args(0) = buttonForm.textToPB.value retcd = PBRX1.TriggerPBEvent(theEvent, numargs, args) rc = PBRX1.GetLastReturn() if rc 1 then msgbox " エラー。空の文字列 " end if PBRX1.ResetArgElements() end sub 3 関数、アンカー、またはクリックして VBScript 関数を呼び出す フォーム ボタンのスクリプトを記述します。たとえば、次のよう になります。 <FORM NAME="buttonForm"> <P><INPUT TYPE=Text NAME="textToPB" SIZE="20"> <P><INPUT TYPE=BUTTON VALUE="Trigger Event" ONCLICK="call TrigEvent()"> </FORM> 772 PowerBuilder 第 34 章 PowerBuilder ウィンドウ ActiveX の使い方 PowerBuilder ウィンドウ ActiveX のイベント PowerBuilder ウィンドウ ActiveX は、チャイルド ウィンドウ内で発生 するいくつかのイベントに応答できます。これらのイベントは、アウ トバウンド イベントです。まず、PowerBuilder ウィンドウ内で発生し、 次に PowerBuilder ウィンドウ ActiveX 内で発生します。これらのイベ ントに応答する JavaScript または VB Script コードを追加できます。表 34-4 にこれらのイベントを示します。 表 34-4: PowerBuilder ウィンドウ ActiveX のイベント イベント Activate Clicked 発生する状況 ウィンドウがアクティブになる直前に発生する 有効化された表示可能オブジェクトが配置されていない、 ウィンドウ内の領域をユーザがクリックしたときに発生す る Close ウィンドウが閉じられるときに発生する Deactivate ウィンドウが非アクティブになったときに発生する DoubleClicked 有効化された表示可能オブジェクトが配置されていない、 ウィンドウ内の領域をユーザがダブルクリックしたときに 発生する Hide ウィンドウが非表示になる直前に発生する Key ユーザがキーを押したときに挿入ポイントがライン エ ディットになければ発生する MouseDown 有効化された表示可能オブジェクトが配置されていない、 ウィンドウ内の領域でユーザがマウスの左ボタンを押した ときに発生する PBMouseMove ウィンドウ内でポインタが移動したときに発生する PBMouseUp 有効化された表示可能オブジェクトが配置されていない、 ウィンドウ内の領域でユーザがマウスの左ボタンを放した ときに発生する RButtonDown 有効化された表示可能オブジェクトが配置されていない、 ウィンドウ内の領域でユーザがマウスの右ボタンを押した ときに発生する Resize ユーザまたはスクリプトによって、ウィンドウが開かれた とき、またはウィンドウのサイズが変更されたときに発生 する Show スクリプトがウィンドウに対して Show 関数を実行したと き、ウィンドウが表示される直前に発生する SystemKey 挿入ポイントがライン エディットにないときに、ユーザが 〔Alt〕または〔Alt〕+ 別のキーを押すと発生する Timer Timer 関数が呼び出されてから指定の秒数が経過したとき に発生する アプリケーション テクニック 773 サーバの設定 サーバの設定 サーバのセットアップでは、サーバ上にファイルを配置します。 サーバの適切なディレクトリに、PowerBuilder ライブラリ、PowerBuilder ウィンドウ ActiveX モジュール、および HTML ファイルをコピーする 必要があります。 表 34-5: サーバ上の PBD ファイルと HTML ファイルの場所 ファイル HTML ページ Param 要素の LibList 属 性で指定した PBD ファ イル PowerBuilder ウィンド ウ ActiveX モジュール 場所 HTML ドキュメント ディレクトリ。HTML ペー ジを、ページにリンクする URL で指定される ディレクトリにコピーする Web サーバ アプリケーションのアプリケーショ ン パスまたはシステム パスに指定されたディレ クトリ HTML ドキュメントのディレクトリ、または Object 要素の CODEBASE 属性に指定されたその 他のディレクトリ ユーザのワークステーションの設定 ユーザが PowerBuilder ウィンドウ ActiveX などの貼り付けられた Web ページを表示するには、クライアント ワークステーションへの支援ソ フトウェアのインストールと、Web サーバへの接続が必要です。 表 34-6: PowerBuilder ウィンドウ ActiveX を表示するためのクライアント 要件 コンポーネント インターネット接続か イントラネット接続 ActiveX をサポートす る Web ブラウザ 774 詳細 企業内で、またはインターネット サービス プロバ イダから利用できる ブラウザ ベンダから入手できる。Microsoft Internet Explorer など PowerBuilder 第 34 章 コンポーネント PowerBuilder ランタイ ム DLL PowerBuilder ウィンド ウ ActiveX モジュール その他のファイル PowerBuilder ウィンドウ ActiveX の使い方 詳細 ランタイム ファイルをインストールする。866 ペー ジの「PowerBuilder ランタイム ファイル」を参照 PowerBuilder ランタイム DLL は、アプリケーショ ン ディレクトリか、システム パス上のディレクト リに置く。PowerBuilder ウィンドウ ActiveX は、 PowerBuilder 仮想マシンおよびその他必要なラン タイム DLL にアクセスできなければならない。こ のため、PowerBuilder ランタイム DLL 用のディレ クトリをシステム パスに追加するか、ランタイム DLL を Windows\System32 ディレクトリに配置す る PBRX110.OCX ファイルをクライアント ワークス テーションにコピーして登録する。または、Object 要素に CODEBASE 属性を追加する。これにより、 ページがロードされたときに、ブラウザはこの ファイルをダウンロードし、登録する 画像ソースを PBD に入れていない場合、ファイル がオブジェクトのプロパティで指定されるパス上 になければ、そのパスにコピーする PowerBuilder ウィンドウ ActiveX アプリケーション でデータベースに接続する場合は、DBMS に合わ せてクライアント ソフトウェアをセットアップす る。クライアント マシンから DBMS に接続する方 法については、『データベースとの接続』マニュア ルを参照 Web ページと PowerBuilder ウィンドウ ActiveX アプリケーションの 表示 必要なソフトウェアをインストールすると、ユーザは PowerBuilder ウィンドウ ActiveX アプリケーションが貼り付けられた Web ページを 表示できます。 ユーザが Web ページの URL を指定すると、以下のことが行われます。 • PowerBuilder ウィンドウに割り当てられた領域に、ページ上のテキ ストが表示される • クライアントがサーバから PBD をダウンロードする • ブラウザが Web ページ内にチャイルド ウィンドウを表示する アプリケーション テクニック 775 ユーザのワークステーションの設定 776 • ウィンドウの中のコントロールと対話し、イベントのスクリプト を実行する • ユーザが別のページに移ると、ウィンドウが閉じ、PowerBuilder DLL や共有ライブラリがメモリからアンロードされる PowerBuilder 第 8 部 全般的なテクニック 第 8 部では、日本語仕様、印刷処理、アクセシビリティ 要件、および Windows のレジストリを扱うテクニックに ついて説明します。InfoMaker で使用する様式とアクショ ンの作成についても説明します。 第 3 5 章 アプリケーションの国際化 この章について この章では、複数の言語向けのアプリケーションを開発および配 布するときに発生する問題についていくつか説明します。 内容 項目 国際化アプリケーションの開発 Unicode の使い方 ユーザ インタフェースの国際化 ページ 779 780 786 国際化アプリケーションの開発 複 数 の 言 語 で 配 布 す る ア プ リ ケ ー シ ョ ン を 開 発 す る と き は、 PowerBuilder に組み込まれている Unicode サポートを利用できま す。また、開発プロセスの 2 つのフェーズにも注目する必要があ ります。 アプリケーション テクニック • 1 つ目は国際化のフェーズです。ここでは、アプリケーション のコードの作成を始める前にデザインの問題を考慮します。 • 2 つ目はローカライゼーションのフェーズです。このフェーズ は、国際化アプリケーションの開発フェーズが完了したとき から始まり、アプリケーションの翻訳と配布の処理を行いま す。 779 Unicode の使い方 Unicode の使い方 Unicode は、世界のほとんどの言語のテキストを表示できる文字エン コーディング スキームです。PowerBuilder は、Unicode 文字をサポー トしています。したがって、アプリケーションの同一ページに複数の 言語の文字を表示したり、さまざまな国に向けた配布に適した柔軟な ユーザ インタフェースを作成したり、複数の言語のデータを処理した りすることができます。 Unicode について Unicode が開発されるまでは、多数の異なるエンコーディング システ ムがあり、その多くが互いに競合していました。たとえば、エンコー ディング システムが異なるために、同じ数字が別の文字で表示される ことがありました。Unicode は、サポートされているすべての記述言語 で、それぞれの文字に対して固有の番号を提供します。複数のスクリ プトで記述できる言語の場合、Unicode は、サポートされているそれぞ れのスクリプトの個々の文字に固有の番号を提供します。 サポートされている言語およびスクリプトについての詳細は、Unicode Web のサイト http://www.unicode.org/onlinedat/languages-scripts.html を参照 してください。 エンコーディング形式 780 Unicode のエンコーディング形式には、UTF-8、UTF-16、UTF-32 の 3 つがあります。本来、UTF は、Unicode Transformation Format の略でし た。この略語は、現在では、前述のエンコーディング形式の名前とし て使用されています。いずれの形式も、文字セット定義から、データ を表す実際のコード単位およびエンコーディング スキーム(特定のバ イトのシリアル化を含むエンコーディング形式)にマップします。 • UTF-8 は、1 ~ 4 バイトの符号なしのバイト シーケンスを使用し て、個々の Unicode 文字を表します。 • UTF-16 は、文字のスカラ値の範囲に応じて 1 つまたは 2 つの符号 なしの 16 ビット コード単位を使用して、個々の Unicode 文字を表 します。 • UTF-32 は、単一の符号なしの 32 ビット コード単位を使用して、 個々の Unicode 文字を表します。 PowerBuilder 第 35 章 エンコーディング ス キーム アプリケーションの国際化 エンコーディング スキームは、エンコーディング形式内のバイトをシ リアル化する方法を指定します。PowerBuilder で、ファイルの操作、 Blob データと文字列の変換、データウィンドウの保存を行うときは、 ANSI エンコーディング、または 3 つの Unicode エンコーディング ス キームのいずれかを使用するように選択できます。 • UTF-8 は、UTF-8 コード単位のシーケンスを、そのコード単位シー ケンス自体とまったく同じ順序でシリアル化します。 • UTF-16BE は、UTF-16 コード単位のシーケンスを、バイト シーケ ンスとしてビッグ エンディアン形式でシリアル化します。 • UTF-16LE は、UTF-16 コード単位のシーケンスを、バイト シーケ ンスとしてリトル エンディアン形式でシリアル化します。 UTF-8 は、Web リクエストおよび応答でよく使用されます。ビッグ エ ンディアン形式では、バイト シーケンス内の最上位の値が最初の格納 アドレスに格納されます。これは、通常、UNIX システムで使用され ます。リトル エンディアン形式では、シーケンス内の最下位の値が最 初に格納されます。これは Windows で使用されます。 PowerBuilder での Unicode サポート PowerBuilder は、内部的に UTF-16LE エンコーディングを使用します。 PBL のソース コードは、UTF-16LE でエンコーディングされています。 アプリケーションで入力されたテキストは、自動的に Unicode に変換 されます。String 型と Character PowerScript データ型は、Unicode データ だけを保持します。これらのデータ型に割り当てられた ANSI または DBCS 文字は、すべて内部で Unicode エンコーディングに変換されま す。 Unicode データベース のサポート ほとんどの PowerBuilder データベース インタフェースは、ANSI と Unicode の両方のデータベースをサポートしています。 Unicode デ ー タ ベ ー ス は、文 字 セ ッ ト が UTF-8 や UTF-16 な ど の Unicode 形式に設定されているデータベースです。データベース内のす べてのデータは、Unicode 形式であり、データベースに保存されるデー タはすべて明示的または暗黙的に Unicode データに変換されなければ なりません。 アプリケーション テクニック 781 Unicode の使い方 文字セットとして ANSI(または DBCS)を使用するデータベースは、 Unicode データを保存するための特別なデータ型を使用できます。これ らのデータ型は、NChar、NVarChar、および NVarChar2 です。これら のいずれかのデータ型のカラムは Unicode データを保存することがで きますが、そのタイプのカラムに保存されるデータは、明示的に Unicode に変換されなければなりません。 個々のインタフェースについての詳細は、 『データベースとの接続』マ ニュアルを参照してください。 文字列関数 Fill、Len、Mid、Pos などの PowerBuilder の文字列関数は、パラメータま たは戻り値としてバイトではなく文字数を受け取り、すべての環境で 同じ結果を返します。これらの関数には、"W" 付きの関数(FillW など) があります。これらは、"W" が付かない関数と同じ結果を返すので、 現時点では下位互換性のためにだけ残されており将来のバージョンで 削除される予定です。これらの関数の一部には、ANSI 対応の関数(FillA な ど)も あ り ま す。こ の "A" 付 き の 関 数 は、以 前 の バ ー ジ ョ ン の PowerBuilder で、文字数の代わりにバイトを返す文字列関数を使用し ていた DBCS 環境のユーザ向けに下位互換性のために提供されていま す。 GetEnvironment 関数を使用して、環境で使用される文字セットを指定で きます。 environment env getenvironment(env) choose case env.charset case charsetdbcs! // DBCS 処理 ... case charsetunicode! // Unicode 処理 ... case charsetansi! // ANSI 処理 ... case else // その他の処理 ... end choose 782 PowerBuilder 第 35 章 カタログ データ型の エンコーディング アプリケーションの国際化 Blob、BlobEdit、FileEncoding、FileOpen、SaveAs、および String などの関 数には、オプションの encoding パラメータがあります。これらの関数 では、ANSI、UTF-8、UTF-16LE、および UTF-16BE エンコーディング で Blob およびファイルを操作できます。このパラメータを指定しない 場合の SaveAs および FileOpen デフォルト エンコーディングは ANSI です。そのほかの関数のデフォルトは UTF-16LE です。 次の例は、FileOpen を使用してさまざまな種類のファイルを開く方法 を示します。 // ANSI ファイルを読み込みます。 Integer li_FileNum String s_rec li_FileNum = FileOpen("Employee.txt") // または // li_FileNum = FileOpen("Emplyee.txt", & // LineMode!, Read!) FileRead(li_FileNum, s_rec) // Unicode ファイルを読み込みます。 Integer li_FileNum String s_rec li_FileNum = FileOpen("EmployeeU.txt", LineMode!, & Read!, EncodingUTF16LE!) FileRead(li_FileNum, s_rec) // バイナリ ファイルを読み込みます。 Integer li_FileNum blob bal_rec li_FileNum = FileOpen("Employee.imp", Stream Mode!, & Read!) FileRead(li_FileNum, bal_rec) 初期設定ファイル SetProfileString 関数は、Windows システムでは ANSI または UTF16-LE エンコーディングで、また UNIX システムでは ANSI または UTF16-BE エンコーディングで、初期設定ファイルに書き込むことができます。 ProfileInt および ProfileString PowerScript 関数、およびデータウィンドウ 式関数は、これらのエンコーディング スキームのファイルを読み込む ことができます。 ソースのエクスポート とインポート ライブラリ エントリのエクスポート ダイアログボックスでは、エクス ポートされるファイルのエンコーディング タイプを選択できます。選 択肢は ANSI/DBCS(PowerBuilder 9 以前のバージョンにファイルをイ ンポートできます)、HEXASCII、UTF8、または Unicode LE です。 アプリケーション テクニック 783 Unicode の使い方 HEXASCII エクスポート形式は、ソース制御ファイルに使用されます。 Unicode 文字列は、エクスポートされるファイルでは 16 進数 /ASCII 文 字列で表されます。その種の文字列を含んでいるファイルとして識別 す る た め に、ヘ ッ ダ ー の 最 初 に HA と い う 文 字 が 付 い て い ま す。 HEXASCII ファイルを PowerBuilder 9 以前のバージョンにインポート することはできません。 PowerBuilder 9 以前のバージョンからエクスポートされるファイルを インポートする場合、オブジェクトが PBL に追加される前に、ファイ ル内のソース コードが Unicode に変換されます。 外部関数 ANSI 文字列を返す外部関数や、ANSI 文字列引数を持つ外部関数を呼 び出すときは、外部関数宣言で ALIAS 句を使用し、関数名に ;ansi を 追加する必要があります。たとえば、次のようになります。 FUNCTION int MessageBox(int handle, string content, string title, int showtype) LIBRARY "user32.dll" ALIAS FOR "MessageBoxA;ansi" 次の宣言は、Unicode 文字列を使用する “w” 付きの関数用です。 FUNCTION int MessageBox(int handle, string content, string title, int showtype) LIBRARY "user32.dll" ALIAS FOR "MessageBoxW" PowerBuilder 9 以前のバージョンからアプリケーションを移行する場 合、PowerBuilder は、ANSI 文字列を使用する関数宣言を適切な構文に 自動的に置き換えます。 複数の言語をサポート するためのフォントの 設定 システム オプション ダイアログボックスおよびデザイン オプション ダイアログボックスのデフォルト フォントは MS P ゴシックです。 システム オプション ダイアログボックスのフォントを Tahoma に設定 すると、ウィザードのウィンドウ ペインタ、ユーザ オブジェクト ペ インタ、メニュー ペインタのレイアウト ビューおよびプロパティ ビューで、複数の言語を正しく表示できます。 デザイン オプション ダイアログボックスの[エディタ フォント]ペー ジのフォントが Tahoma に設定されていない場合、スクリプト ビュー、 テキスト エディタ、ソース エディタ、データベース ペインタの ISQL セッション ビュー、およびデバッグ ウィンドウで、複数の言語を表示 することはできません。 784 PowerBuilder 第 35 章 アプリケーションの国際化 スクリプト ビュー、テキスト エディタ、ソース エディタ、データベー ス ペインタの ISQL ビューのデザイン オプション ダイアログボックス の[プリンタ フォント]タブ ページで、印刷用に別のフォントを選択 することができます。プリンタのフォントが Tahoma に設定されてお り、Tahoma フォントがプリンタにインストールされていない場合、 PowerBuilder は、多言語文字を検出したときにフォント セット全体を プリンタにダウンロードします。多言語文字を印刷する必要がある場 合は、プリンタにインストールされているプリンタ フォントを指定し ます。 データウィンドウ オブジェクトで複数の言語をサポートするには、す べてのカラムとテキスト コントロールのフォントを Tahoma に設定し ます。 印刷関数のデフォルト フォントはシステム フォントです。PrintDefineFont 関数および PrintSetFont 関数を使用して、ユーザのプリンタで利用で き、複数言語をサポートするフォントを指定します。 PBNI PowerBuilder ネイティブ インタフェースは Unicode ベースです。PBNI エクステンションは、C++ 開発環境で _UNICODE プリプロセッサ擬似 命令を使用してコンパイルする必要があります。 Unicode 環境での正常な動作を保証するため、エクステンションのコード では、char、char*、および const char* の代わりに、TCHAR、LPTSTR、ま たは LPCTSTR を使用する必要があります。または、MultiByteToWideChar 関数を使用して、文字列を Unicode 文字列にマップします。アプリケー ションで Unicode を有効にする方法についての詳細は、使用している C++ 開発環境のマニュアルを参照してください。 Web サービスでの Unicode の有効化 PowerScript ターゲットでは、Web サービス クライアント アプリケー ションによってインスタンス化される PBNI エクステンション クラス は、すべての内部処理で Unicode を使用します。ただし、コンポーネ ント メソッドの呼び出しは、EasySoap による処理のために ANSI に変 換されます。これらの呼び出しから返されるデータは、Unicode に変換 されます。 JSP ターゲットでは、オーサリング ツール (HTML エディタ)が Unicode を使用できるので、1 つのページに複数の言語のテキストを挿入でき ます。エディタに入力したテキストは UTF-8 エンコーディングで保存 されます。ただし、ほかのエンコーディング スキームの JSP ファイル をエディタにインポートすることもできます。これらのエンコーディ ングのテキストは、自動的に UTF-8 に変換されます。 アプリケーション テクニック 785 ユーザ インタフェースの国際化 XML 文字列のエン コーディング XML パーサは、windows-1253 のように 8 ビット文字コードを使用する 文字列を解析することができません。たとえば、次の宣言を持つ文字 列は解析できません。 string ls_xml ls_xml += '<?xml version="1.0" encoding="windows1253"?>' UTF16-LE などの Unicode エンコーディング値を使用してください。 ユーザ インタフェースの国際化 国際的に配布するアプリケーションを作成するときに、ユーザ インタ フェースのデザインで考慮すべき点は 2 つあります。 物理的デザイン • ユーザ インタフェースの物理的なデザイン • アプリケーションの対象者の文化的基準 ユーザ インタフェースの物理的なデザインには、次のものを含める必 要があります。 • メニュー項目のテキスト、リスト、ラベルが翻訳されたときに文 字列が長くなっても収めることができる柔軟なウィンドウおよび オブジェクト たとえば、元が英語のウィンドウからウィンドウを継承し、ロー カライズする配布用に言語を変更できます。通常は、メニュー項 目、リスト、またはラベルのサイズを英語の文字列の長さの 1.3 倍 にしておけば、ほとんどの言語のテキストを収めることができま す。 • 文化的意識 RightToLeft バージョンの Windows で簡単に使用できるウィンドウ ユーザ インタフェースの文化的なデザインには、対象者にとって許容 できることとできないこと、または意味があることを認識することが 要求されます。 たとえば、手のひらを表示する手のアイコンは、ある文化では「停止」 を意味しますが、別の文化では、 「拒否」を示します。同様に、黄色は ある文化では「注意」を意味しますが、別の文化では「幸福と繁栄」 を意味します。 786 PowerBuilder 第 3 6 章 利用しやすいアプリケーションの作成 この章について この章では、障害のあるユーザにも利用しやすいアプリケーショ ンを作成するためのガイドラインと要件についての情報を提供し ます。また、利用しやすいアプリケーションの作成を支援するた めに PowerBuilder が提供する機能について説明し、追加情報の入 手先も示します。 内容 項目 アクセシビリティの課題についての理解 ソフトウェアおよび Web アプリケーションのアクセシビリ ティ要件 PowerBuilder を使用した利用しやすいソフトウェア アプリ ケーションの作成 VPAT について 製品のアクセシビリティのテスト ページ 787 790 792 796 796 アクセシビリティの課題についての理解 障害のある人にも利用しやすいソフトウェア アプリケーションお よび Web ページを設計および開発する場合は、一般に 4 種類の障 害について考慮する必要があります。 アプリケーション テクニック • 視覚障害 • 聴覚障害 • 運動障害 • 認知障害または学習障害 787 アクセシビリティの課題についての理解 視覚障害 目の不自由なアプリケーション ユーザには、視覚に問題のないユーザ が利用できるすべてのグラフィック イメージおよびビデオに対応す る同等物をテキストの形式で用意する必要があります。このテキスト は、グラフィック形式で提供されている情報と概念の上で同等の内容 を伝える必要があります。それにより、ユーザは、画面読み上げソフ トウェアや点字リーダなどの補助技術を使用して情報を完全に利用で きます。すべてのユーザ インタフェース(UI)要素には、テキストま たはメニュー形式の同等物が必要です。また、目の不自由なユーザは、 視覚に問題のないユーザがマウスで行うような入力をキーボードから 行う必要があります。 色覚に障害のあるユーザに対応するには、色を情報伝達の唯一の手段 として使用するのを避ける必要があります。色で伝える情報を補完す る手段として、グラフやその他のイメージで色以外に塗りつぶしパ ターンを使用するのも 1 つの方法です。色だけで警告またはその他の 内容を提示する代わりに、音声通知を使用することもできます。 ハイ コントラストのサポートを有効にすると、色覚障害のあるユーザ や弱視ユーザが、デフォルトのシステム カラーおよびフォントを調整 して、ウィンドウまたは Web ページの領域を区別しやすくすることが できます。弱視のユーザは、ハードウェアまたはソフトウェアの拡大 鏡を使用して、ディスプレイ上のピクセルを拡大します。また、代替 テキストを使用して、イメージに表示される情報の一部を取得します。 聴覚障害 耳の聞こえないユーザや難聴のユーザには、音声情報を視覚的に表現 する必要があります。たとえば、音声による警告の代わりに、視覚的 な通知をアプリケーションで提供しなければならない場合がありま す。テキストを点滅させるのも 1 つの方法ですが、点滅速度は一定の 範囲内にする必要があります。これは、発作性疾患のあるユーザに問 題が発生するのを避けるためです。オーディオ トラックは、トランス スクリプトを必要とします。また、場合によってはビデオにクローズ ド キャプションが必要です。 聴覚障害を支援する技術には、音声情報をテキストまたは手話に変換 できる音声認識製品があります。同様に重要なのは、コンピュータと 電話を接続し、入力された ASCII テキスト出力をボー(Baudot)コー ドに変換する TTY/TDD モデムです。ボー コードは、聴覚障害者が電 話での会話に通常使用しているものです。 788 PowerBuilder 第 36 章 利用しやすいアプリケーションの作成 運動障害 運動機能が限られているユーザにとって、ハードウェアおよびメディ アを扱うのはしばしば困難ですが、一般に、最大の課題となるのは入 力です。運動障害のあるユーザは、その障害に応じて、場合によって は音声認識を使用したり、電子スイッチ、トラック ボール、または ジョイ スティックによってオンスクリーン キーボードを使用したり する必要があります。また、入力のペースが遅い可能性があるので、 タイマーおよび応答時間を調整できるようにしなければなりません。 インテリジェント機能が組み込まれているシステムでは、要求される 入力の数を減らすためのキューを提供できます。Windows アプリケー ションの場合、フィルタキー機能を利用して、キー リピートの間隔を 長くすることができます。また、Windows の固定キー機能を使用する と、〔Ctrl〕+〔Alt〕+〔Delete〕などの複数のキー ストロークをキー シーケンスとして入力できます。 認知障害 難読症、視覚または音声情報の処理に関する障害、テキスト入力に関 する障害、および短期記憶における障害は、すべてのソフトウェアお よび Web アプリケーションの内容に対するユーザのアクセスに影響 を与える可能性があります。明確でシンプルな言語を使用したり、一 貫性のあるデザインを採用したり、同じ情報をさまざまな形式(オー ディオとビデオの両方など)で提供したりすることは、いずれも認知 障害のあるユーザが情報にアクセスするのを助けます。また、応答時 間を調整できることは、通常より理解に時間のかかるユーザにとって 重要です。コンテンツを画面読み上げソフトウェアで利用できるよう にして視覚表現を補強するのも、認知障害のユーザの理解を助ける方 法の 1 つです。 一般的なアドバイス Web 表示では、フォント サイズなどのテキスト機能を直接操作するの ではなく、要素を使用してすべてをマークアップすることが重要です。 テキスト要素の機能を、視覚的な表示にだけ頼って示すのは避けてく ださい。要素をマークアップすると、画面読み上げソフトウェアなど の支援技術によって、見出しなどのテキスト要素をその機能ごとに通 知することができます。 適切なアクセシビリティを備えたデザインは、障害のあるユーザだけ でなく、すべてのユーザにとって使いやすいものです。一貫したイン タフェース デザイン、わかりやすい言語表現、簡単なナビゲーション、 同一情報のさまざまな形式での提供により、アプリケーションを誰に とっても使いやすくすることができます。 詳細情報 Web サイトを利用しやすくするための情報については、World Wide Web Consortium Web の サイ ト http://www.w3.org/ お よ び Utah State University WebAim Web のサイト http://www.webaim.org を参照してください。 アプリケーション テクニック 789 ソフトウェアおよび Web アプリケーションのアクセシビリティ要件 ユーザがさまざまなブラウザを調整して識別しやすくする方法、およ び視覚障害に対処する一般的な方法については、Lighthouse International Web のサイト http://www.lighthouse.org/ を参照してください。 ソフトウェアおよび Web アプリケーションのアクセシビ リティ要件 障害を持つユーザにも利用しやすいアプリケーションの作成を目指す 組織が従う必要のある複数の規制やガイドラインは、製品を販売また は使用する国ごとに少し異なります。 リハビリテーション法 :508 条 1998 年に制定された 508 条は、米国リハビリテーション法を修正した ものです。508 条は、米国政府機関が開発、調達、維持、使用するす べての電子情報技術は、障害のある一般市民にも利用しやすいもので なければならないことを求めています。米国の州の多くは、これらの 要件を同様に採択しています。米国連邦政府や多くの州政府にソフト ウェア アプリケーションを納入する組織は、アクセシビリティ支援 ツールを使用または販売する企業と同様に、これらの規制を守って、 自社製品が調達条件を満たすようにしなければなりません。 WCAG 1.0 508 条のガイドラインは、World Wide Web コンソーシアムが 1999 年 3 月に発行したアクセシビリティ ガイドラインを基にしています。これ は、Web Content Accessibility Guidelines (WCAG) version 1.0 として知ら れています。WCAG 1.0 は、現在、ほとんどのアクセシビリティ ガイ ドラインや、多数の国で政府によって施行されている標準の共通の土 台となっています。これらのガイドラインには、3 つの優先度があり ます。優先度 1 は、Web コンテンツへのアクセスに必須の機能を扱い ます。優先度 2 は、Web サイトを一般に、そして特にアクセシビリティ ツールを使う人にとって、使いやすく、またわかりやすくするための 方法を定義しています。優先度 3 は、最新の技術を使用する高度なユー ザビリティ機能について記述しています。 508 条には、優先度 1 の WCAG 勧告のほとんどと、優先度 2 および 3 の一部が含まれています。その他に、WCAG には含まれていない他の 要件もいくつか含まれています。WCAG は、組織が優先度 1 および 2 のガイドラインを満たすように努力することを推奨しています。 790 PowerBuilder 第 36 章 利用しやすいアプリケーションの作成 フランスの法令 フランス政府も、障害のある人向けの Web アクセシビリティを要求す る法令を制定し、その準拠のために AccessiWeb を呼ばれる基準を発行 しています。AccessiWeb には、Bronze、Silver、Gold の 3 つのレベル があります。これは、WCAG の 3 つの優先度レベルにほぼ対応してい ますが、AccessiWeb は、優先度 2 および 3 の多くの要件をより高い優 先度に上げており、WCAG 勧告の一部よりも詳細な内容を含んでいま す。 イギリスの法令 イギリスでは、イギリス住民を対象とする Web サイトは、障害のある 人にとって利用しやすいものでなければならないとする障害者差別禁 止法( Disability Discrimination Act )という法令が通過しています。イ ギリスの法の施行は、現行では WCAG 1.0 優先度 1 および 2 のガイド ラインに基づいています。 その他の国 その他の多くの国は、政府の Web サイトや一般的に使用される Web サ イトが障害のある人にとって利用しやすいものであることを要求する 法を制定しています。これらの国の中は、WCAG 1.0 の優先度 1 およ び 2 に準拠することを明示的に要求している国もありますが、優先度 1 の準拠だけを要求している国も少数あります。法的な要件のないそ の他の多数の国では、実際には WCAG が使用されています。 WCAG 2.0 WCAG 標準は、広く受け入れられる Web アクセシビリティの国際的な ガイドラインとなるように、現在も更新が行われています。WCAG 2.0 では、一般的な概念に焦点を当てて、Web サイトが障害のあるユーザ にとって利用しやすいものであるために保持しなければならない特性 を詳しく説明しています。技術的な要件については、別の文書で規定 されています。これは、一般的な概念を更新しなくても、技術的な変 更だけを簡単に更新できるようにするためです。 詳細情報 ソフトウェア アプリケーションおよび Web サイトについての米国連 邦政府のアクセシビリティ要件については、Electronic and Information Technology のサイト http://www.access-board.gov/sec508/guide/ および Electronic and Information Technology Accessibility Standards のサイト http://www.access-board.gov/sec508/508standards.htm を参照してください。 Web アクセシビリティについて広く受け入れられている国際的な推奨 事項については、WCAG guidelines のサイト http://www.w3.org/TR/WCAG10/ を参照してください。開発中の新しいガイドラインについては、WCAG 2.0 guidelines のサイト http://www.w3.org/TR/WCAG20/ を参照してくださ い。 フランス政府が採択している Web アクセシビリティの基準について は、AccessiWeb criteria のサイト http://www.accessiweb.org/fr/Label_Accessibilite/criteres_accessiweb/92_access iweb_lineaire/ を参照してください。 アプリケーション テクニック 791 PowerBuilder を使用した利用しやすいソフトウェア アプリケーションの作成 PowerBuilder を使用した利用しやすいソフトウェア アプ リケーションの作成 MSAA 標準 PowerBuilder は、Windows および Web アプリケーションにアクセシビ リティ機能を組み込むために必要なインフラストラクチャおよびプロ パティを提供します。この機能を使用すると、アプリケーションを Microsoft Active Accessibility(MSAA)バージョン 2 に一般的に準拠さ せることができます。MSAA は、Windows 標準で、アクセシビリティ 支援ツールがユーザ インタフェース要素についての情報を取得する 方法、およびプログラムがアクセシビリティ支援ツールに情報を公開 する方法を定義します。 PowerBuilder の標準コントロールは、次の表に示すように、必要な Microsoft Active Accessibility のプロパティをすべてサポートしています。 表 36-1: MSAA プロパティと PowerBuilder サポート Microsoft Active Accessibility プロパティ サポートする PowerBuilder のプロパティ Name objectname.AccessibleName Role State Location Parent ChildCount Keyboard Shortcut DefaultAction Value 一部のコントロールは、Text プロパティまたは Title プロパティで Name 設定をサポートします。 すべてのコントロールで、Name は、 AccessibleName プロパティを通じてカスタマイズ できます。 objectname.AccessibleRole AccessibleRole プロパティを通じてカスタマイズ できます。 デフォルトの Active Accessibility をサポートする デフォルトの Active Accessibility をサポートする デフォルトの Active Accessibility をサポートする デフォルトの Active Accessibility をサポートする Text プロパティの "&" アクセス キーに対して、 デフォルトの Active Accessibility をサポートする また、そのコントロールに適用できる場合は PowerBuilder Accelerator プロパティを設定 デフォルトの Active Accessibility をサポートする (たとえば、チェック ボックスにはチェックがな いときのデフォルトのアクションがあります) デフォルトの Active Accessibility をサポートする (たとえば、チェック ボックスはオンのときの値 を持ちます) 792 PowerBuilder 第 36 章 Microsoft Active Accessibility プロパティ Children ビジュアル コント ロール 利用しやすいアプリケーションの作成 サポートする PowerBuilder のプロパティ デフォルトの Active Accessibility をサポートする Focus Selection Description (たとえば、リスト ボックス内の項目) デフォルトの Active Accessibility をサポートする デフォルトの Active Accessibility をサポートする objectname.AccessibleDescription Help HelpTopic AccessibleDescription プロパティを通じてカスタ マイズできます。 未サポート 未サポート DragObject から継承される PowerBuilder のビジュアル コントロールの 場合、PowerBuilder ドット表記またはペインタのプロパティ ビューの [その他]ページを使用して、各コントロールの IAccessible Name、Role、 および Description プロパティを操作できます。また、テキスト プロパ ティおよびアクセラレータ プロパティでアンパサンドがサポートさ れている箇所では、PowerBuilder プロパティを使用して、IAccessible プ ロパティの KeyboardShortcut を操作することもできます。その他の IAccessible プロパティは、Active Accessibility のデフォルト サポートを 使用して自動的に設定されます(たとえば、場所は、実行時に画面上 の Windows コントロールの絶対座標で自動的に更新されます)。 次の表は、DragObject から継承される PowerBuilder ビジュアル コント ロールと、そのデフォルトのアクセシブル ロール(AccessibleRole)の リストです。 表 36-2: PowerBuilder ビジュアル コントロールとそのデフォルト ロール AccessibleRole カタログ データ PowerBuilder ビジュアル コントロール (列挙体)値 animationrole! アニメーション checkbuttonrole! チェックボックス pushbuttonrole! コマンドボタン clientrole! データウィンドウ comboboxrole! ドロップダウン リストボックス ドロップダウン ピクチャ リストボックス comboboxrole! textrole! エディットマスク diagramrole! グラフ groupingrole! グループボックス progressbarrole! 水平プログレスバー、垂直プログレス バー アプリケーション テクニック 793 PowerBuilder を使用した利用しやすいソフトウェア アプリケーションの作成 AccessibleRole カタログ データ PowerBuilder ビジュアル コントロール (列挙体)値 scrollbarrole! 水平スクロールバー、垂直スクロール バー sliderrole! 水平トラックバー、垂直トラックバー listrole! リストボックス listrole! リストビュー clientrole! 月表示カレンダ textrole! マルチライン エディット graphicrole! ピクチャ pushbuttonrole! ピクチャボタン linkrole! ピクチャ ハイパーリンク listrole! ピクチャ リストボックス radiobuttonrole! ラジオボタン clientrole! リッチテキスト エディット textrole! シングルライン エディット linkrole! スタティック ハイパーリンク statictextrole! スタティック テキスト clientrole! タブ コントロール clientrole! タブ ページ outlinerole! ツリービュー OLEControl コントロールは、デフォルトで pushbuttonrole! に設定され ます。内容に応じてこのロールを設定する必要があります。 データウィンドウ コ ントロール PowerBuilder は、データウィンドウ カスタム コントロールとその子に ついて MSAA 標準を実装します。 AccessibleName プロパティと AccessibleDescription プロパティは文字 列値を取ります。AccessibleRole プロパティは、AccessibleRole カタロ グ データ型変数の値を取ります。 データウィンドウでのアクセシビリティ サポートには、いくつか制限 があります。 • 794 ナビゲーション関数 accNavigate では、Spatial Nabigation(画面上の 場所を起点にしたキーボードによるナビゲーション)はサポート されていません。キーボード ナビゲーションが論理タブのシーケ ンスに従う論理的なナビゲーションは、詳細区域のカラムについ てのみサポートされています。タブ値が 0 に設定されているカラ ムはユーザによる更新ができないので、キーボードからはアクセ スできません。 PowerBuilder 第 36 章 利用しやすいアプリケーションの作成 • ラベル、段組み、OLE 2.0、およびリッチテキスト データウィンド ウ スタイルはサポートされていません。 • データウィンドウでの OLE オブジェクト、OLE データベース カ ラム、ネスティッド レポートのサポートは限られています。 PowerBuilder では、コントロールのコンテンツのアクセシビリティを 提供することはできません。これは、コントロールのベンダが提供す る必要があります。 例 次のステートメントは、ウィンドウ内のコマンド ボタンの IAccessible プロパティを設定します。 cb_1.accessiblename = " 削除 " cb_1.accessibledescription = " 選択したテキストを削除します " cb_1.accessiblerole = pushbuttonrole! 次のステートメントは、データウィンドウ オブジェクトのボタンの AccessibleName プロパティを設定します。 dw_1.Object.b_1.accessiblename = " 更新 " 次のステートメントは、データウィンドウ オブジェクトの AccessibleRole プロパティを 43(PushButtonRole! に関連付けられている数)に設定し、 プロパティを文字列変数に返します。 string ls_data dw_1.Object.b_1.AccessibleRole = 43 ls_data = dw_1.Describe("b_1.AccessibleRole") 配布 アクセシブル アプリケーションを配布する場合には、pbacc110.dll ファ イルを必ず配布する必要があります。 詳細情報 詳細については、Microsoft の Accessibility Web のサイト http://www.microsoft.com/japan/enable および MSDN library のサイト http://msdn.microsoft.com/library/default.asp?url=/nhp/default.asp?contentid=28 000544 を参照してください。また、WebAim Web のサイト http://www.webaim.org も参照してください。 アプリケーション テクニック 795 VPAT について VPAT について 自主的製品アクセシビリティ テンプレート(VPAT)は、米国連邦政府 の調達用に提供される製品がアクセシビリティ要件に準拠しているか を連邦政府職員が事前に評価するのに役立つように設計されたリスト です。VPAT は、さまざまなタイプの製品についてアクセシビリティ要 件に準拠するための基準を示します。また、自社製品が VPAT の基準 を満たしているかについて、企業がチェックしたりコメントを追加し たりできるカラムがあります。 VPAT は、ソフトウェア アプリケーションとオペレーティング システ ム、Web ベースのインターネット情報とアプリケーション、およびそ の他のタイプの製品で利用できます。VPAT に記入する必要がない場合 でも、自社製品のタイプについてのテンプレートを参照することで、 ソフトウェアおよび Web アプリケーションに対する 508 条の要件を明 確に理解することができます。 詳細情報 さまざまな VPAT を確認するには、Information Technology Industry Council Web のサイト http://www.itic.org/policy/vpat.html を参照してください。 IT 製品の全 VPAT のサンプルを確認するには、Sybase accessibility のサ イト http://www.sybase.com/accessibility を参照してください。 製品のアクセシビリティのテスト MSAA 2.0 ソフトウェア開発キット(SDK)には、アプリケーション が MSAA に準拠していることを確認するためのツールが複数含まれ ています。たとえば、AccExplorer、Accessible Event Watcher、Object Inspector などがあります。これらのツールは、Microsoft Web のサイト http://msdn.microsoft.com/library/default.asp?url=/downloads/list/accessibility.as p から利用できます。 障害のあるユーザにとってのアプリケーションの動作を直接テストす るには、さまざまな方法を使用できます。たとえば、テキストのみの ブラウザを使用したり、キーボードだけを使って入力したり、JAWS、 Window-Eyes、Hal、または Supernova などの画面読み上げソフトウェ アを使ってアプリケーションを使用したりすることができます。 Web サイトが 508 条および WCAG 1.0 に準拠しているかどうかをテス トするために使用できる商用アプリケーションもいくつかあります。 796 PowerBuilder 第 36 章 詳細情報 利用しやすいアプリケーションの作成 WCAG 1.0 の準拠についてテストするためのチェックリストについて は、W3C Web のサイト http://www.w3.org/TR/1999/WAI-WEBCONTENT19990505/full-checklist を参照してください。W3C Web サイトにも、ア クセシビリティをテストするためのリストと評価ツールがあります。 アプリケーション テクニック 797 製品のアクセシビリティのテスト 798 PowerBuilder 第 3 7 章 印刷 この章について この章では、PowerScript の組み込み関数を使用して、リストやレ ポートを印刷する方法について説明します。 内容 項目 印刷関数 印刷の基礎 ページ 799 801 801 802 803 804 ジョブの印刷 タブの使い方 印刷ジョブの停止 高度な印刷技法 印刷関数 PowerScript 言語では、帳票やレポートの作成のための組み込み関数 を用意しています。わずか 3 つの関数(PrintOpen、Print、PrintClose) を用いるだけで、使用プリンタのデフォルトのフォントで表(タ ブラ)形式のレポートを印刷できます。ほかの関数を用いると、複 数のテキストフォント、文字サイズ、スタイルが使用できるだけ でなく、罫線やピクチャを用いた帳票やレポートが作成できます。 表 37-1 は印刷用の関数のリストです。 表 37-1: PowerScript 印刷関数 関数 Print PrintBitMap PrintCancel PrintClose PrintDatawindow アプリケーション テクニック 説明 Print 関数には 5 種類の構文がある。タブを 1 個指 定できる構文が 3 つ、タブを 2 個指定できる構文が 1 つある 指定されたビットマップを印刷する 指定された印刷ジョブを取り消す 印刷ジョブの現行ページをプリンタ(またはスプー ラ)に送り、印刷ジョブを終了する 指定されたデータウィンドウを印刷ジョブとして 印刷する 799 印刷関数 関数 PrintDefineFont PrintGetPrinter PrintGetPrinters PrintLine PrintOpen PrintOval PrintPage PrintRect PrintRoundRect PrintScreen PrintSend PrintSetFont PrintSetPrinter PrintSetSpacing PrintSetup PrintSetupPrinter PrintText PrintWidth PrintX PrintY 説明 印刷ジョブに使用できる 8 種類のフォントから 1 つのフォントを定義する 現在のプリンタ名を取得する 使用可能なプリンタのリストを取得する 指定の太さの線を指定された位置に印刷する 印刷ジョブを開始し、その印刷ジョブに印刷ジョブ 番号を割り当てる 指定サイズの楕円(または円)を指定された位置に 印刷する 現行ページを印刷し、新しいページを設定する 指定サイズの長方形を指定された位置に印刷する 指定サイズ丸長方形を指定された位置に印刷する 画面のイメージを印刷ジョブの一環として印刷す る 指定された文字列をプリンタに直接送信する 現行フォントに、現行ジョブの定義済みフォントの 1 つを設定する 次に呼び出される印刷関数のためにプリンタを使 用するよう設定する。この関数は開いているジョブ には影響しない 行間隔を決定する係数を設定する プリンタの設定 ダイアログボックスを呼び出し、 エンド ユーザが行う設定をプリンタ ドライバに対 して保存する プリンタの設定 ダイアログボックスを表示する 指定テキスト文字列を指定された位置に印刷する 現行印刷ジョブの現行フォントで、指定された文字 列の長さ(単位 : 1/1000 インチ)を返す 印刷カーソルの X 値を返す 印刷カーソルの Y 値を返す 印刷関数についての詳細は、 『PowerScript リファレンス』マニュアル を参照してください。 800 PowerBuilder 第 37 章 印刷 印刷の基礎 印刷処理は、すべて印刷領域に基づいて定義されます。印刷領域とは、 物理的な印刷ページから余白を除いた領域のことです。たとえば、ペー ジのサイズが 8.5 × 11 インチで、上下左右の余白がすべて 1/2 インチ の場合には、印刷領域は 7.5 × 10 インチとなります。 測定単位 印刷領域の測定単位は 1/1000 インチです。たとえば、印刷領域が 7.5 × 10 インチの場合、その四隅の座標は以下のようになります。 左上隅の座標は 0,0 右上隅の座標は 7500,0 左下隅の座標は 0,10000 右下隅の座標は 7500,10000 印刷カーソル 印刷処理の際、PowerBuilder は、印刷カーソルを使用して印刷位置を 制御します。印刷カーソルは、印刷が開始される左上隅の座標を保持 します。PowerBuilder は、PrintBitmap 関数、PrintLine 関数、PrintRectangle 関数、PrintRoundRect 関数以外の印刷処理の後で、印刷カーソルを(必 要であればタブ位置も)更新します。複雑なレポートの作成時にテキ スト、オブジェクト、罫線、およびピクチャの位置を指定するには、 各印刷関数の呼び出し時にカーソル位置を指定します。 ジョブの印刷 印刷ジョブを開始するには、まず最初に PrintOpen 関数を呼び出す必要 があります。PrintOpen 関数は、新しいページをメモリ上に定義し、す べての印刷がプリンタのデフォルト フォントで行われるように指定 して、整数値を返します。この整数値は、ほかのすべての関数呼び出 しで印刷ジョブの識別に用いられるジョブ番号です。 PrintOpen 関数の後に 1 つまたは複数のほかの印刷関数を呼び出し、最 後に PrintClose 関数(または PrintCancel 関数)を呼び出してジョブを終 了します。通常、PrintOpen 関数と PrintClose 関数の間には、タブ付きま たはタブなしで文字列を印刷する単純な印刷関数、あるいはレポート に罫線、オブジェクト、ピクチャーなどを加える複雑な印刷関数が呼 び出されます。 アプリケーション テクニック 801 タブの使い方 タイトルの印刷方法 各ページの上部にタイトルを印刷するときには、印刷される行数をカ ウントし、一定の行数(たとえば 50)になったら PrintPage 関数を呼び 出し、カウンタをリセットしてタイトルを印刷するようにします。 以下の例は、単純な印刷リクエストです。 Int PrintJobNumber // 印刷ジョブを開始し、PrintJobNumber に // PrintOpen の戻り値の整数を設定します。 PrintJobNumber = PrintOpen() // Atlanta の文字列を印刷します。 Print(PrintJobNumber,"Atlanta") // 印刷ジョブを閉じます。 PrintClose(PrintJobNumber) タブの使い方 Print 関数には、いくつかの構文があります。前出の例の構文では、印 刷領域の左端から文字列が印刷され、次に新しい行が印刷されます。 Print 関数のほかの構文で、タブを用いて印刷処理の前または後、ある いは前後で印刷カーソルの位置を指定できます。 タブ値の指定 タブ値は、1/1000 インチの単位で、印刷領域の左端からの相対位置に よって指定します。タブ値が Print 関数の呼び出し文字列の前にあり、 その文字列の後にはない場合、PowerBuilder はタブを設定し、印刷し て、新 し い 行 を 開 始 し ま す。タ ブ 値 が 文 字 列 の 後 に あ る 場 合、 PowerBuilder は印刷後にタブを設定し、新しい行を開始せずに次のス テートメントを待ちます。 以下の例では、Job は整数の印刷ジョブ番号です。 以下のステートメントは、印刷領域の左端から 1 インチの位置にタブ を設定し、Atlanta と印刷して、新しい行を開始します。 Print(Job,1000,"Atlanta") 以下のステートメントは、現行印刷位置に Boston と印刷し、印刷領域 の左端から 3 インチの位置にタブを設定して、その次のステートメン トを待ちます。 Print(Job,"Boston",3000) 802 PowerBuilder 第 37 章 印刷 以下のステートメントは、印刷領域の左端から 1 インチの位置にタブ を設定し、Boston と印刷し、印刷領域の左端から 3 インチの位置にタ ブを設定して、その次のステートメントを待ちます。 Print(Job,1000,"Boston",3000) タブと印刷カーソル PowerBuilder がタブを設定するときには、印刷カーソルの X 座標に印 刷カーソル値(指定された値と現行カーソル位置との大きい方の値) を設定します。したがって、指定された値が印刷カーソルの現行 X 座 標より小さい場合には、カーソルは移動しません。 以下に示す最初の Print 文は、印刷領域の左端から 1 インチの位置にタ ブを設定し、Sybase と印刷しますが、次のタブには移動しません(印 刷領域の左端から 0.5 インチは、現行カーソル位置より左側にあるた めです)。タブは最後の引数として指定されたので、タブを無視して も、最初の Print 文は新しい行を開始しません。2 番目の Print 文は、 Sybase の e の直後に Inc. を印刷し(つまり Sybase Inc.) 、新しい行を開始 します。 Print(Job,1000,"Sybase",500) Print(Job," Inc.") 印刷ジョブの停止 印刷ジョブを中断するには、以下の 2 つの方法があります。通常では、 印刷ジョブの終わりに PrintClose 関数を呼び出してジョブを終了しま す。もう 1 つは、PrintoCancel 関数を呼び出してジョブを取り消す方法 です。 PrintClose 関数の使い 方 PrintClose 関数は、現行ページをプリンタまたはプリント スプーラに送 PrintCancel 関数の使 い方 PrintCancel 関数は、印刷ジョブを終了し、印刷されずに残った出力を すべて破棄します。PrintCancel 関数は、処理が終了する前にエンド ユー ザに対して印刷を取り消す手段を提供します。通常この関数は、グロー バル変数を定義して、印刷ジョブの処理中にその変数の値を定期的に チェックすることによって呼び出されます。 り、印刷ジョブを終了して、印刷を開始したウィンドウをアクティブ 状態にします。PrintClose 関数呼び出しを実行した後では、そのジョブ 番号を参照する関数呼び出しがすべて無効となります。 StopPrint が Boolean 型のグローバル変数であるものとします。以下の ステートメントは、StopPrint グローバル変数をチェックし、StopPrint 変数の値が TRUE になったらジョブを取り消します。 アプリケーション テクニック 803 高度な印刷技法 IntJobNbr JobNbr = PrintOpen() // グローバル変数の初期値を設定します。 StopPrint = FALSE // 印刷処理を行います。 Do While ... . . . // グローバル変数をテストします。 // 値が TRUE の場合、印刷ジョブをキャンセルします。 // スクリプトの実行を止めます。 If StopPrint then PrintCancel(JobNbr) Return End If Loop 高度な印刷技法 PowerBuilder で複雑なレポートを作成するときには、これまでに紹介 した以外の関数も必要となりますが、比較的簡単に作成できます。 PowerScript 関数を使用して、ジョブに対するフォントの定義、フォン ト間隔と行間隔の指定、ページ上へのオブジェクトの配置、テキスト やオブジェクトを配置する正確な位置の指定を行うことができます。 フォントの定義と設定 これまでの例では、プリンタのデフォルト フォントを使用しました が、各印刷ジョブにつき最大 8 つのフォントを定義することや、その ジョブの実行中にフォントを切り替えることが可能です。 さらに、印刷ジョブの実行中は、必要に応じて何度でもフォントの再 定義ができます。このため、使用プリンタで使用可能なフォントをす べて、印刷ジョブにおいて使用できます。ただし、フォントを再定義 するとパフォーマンスが多少低下するので、PrintOpen 関数を呼び出し た時点でフォントを定義し、印刷ジョブの実行中にフォントを変更し ないようにしてください。 フォントを定義するには、Integer 型変数に PrintDefineFont 関数が返した 値を設定し、次に PrintSetFont 関数を使用してフォントを変更します。 804 PowerBuilder 第 37 章 印刷 JobNum は整数の印刷ジョブ番号で、現行プリンタは Helv という フ ォ ン ト を 持 っ て い る も の と し ま す。以 下 の ス テ ー ト メ ン ト は、 Helv18BU(Helv フォント、18 ポイントの太字、下線付き)を定義して います。定義は、JobNum のフォント 2 に保存されています。社名は フォント 2 で印刷されます。 例 IntJob, Helv18BU JobNum = PrintOpen() Helv18BU = PrintDefineFont(JobNum,2,"Helv",250,700, & Variable!,Swiss!,FALSE,TRUE) PrintSetFont(JobNum,2) Print(JobNum,"Sybase, Inc.") PrintDefineFont 関数と PrintSetFont 関数についての詳細は、 『PowerScript リファレンス』マニュアルを参照してください。 行間隔の設定 Print 関数を使用すると、行間隔は自動的に設定されます。たとえば、 18 ポイントのフォントで印刷して新しい行を開始すると、印刷カーソ ルの Y 座標に文字の高さの 1.2 倍が加えられます。 この行間隔係数 1.2 は、固定されているわけではありません。行間隔 は、PrintSetSpacing 関数を使用して設定できます。 以下のステートメントを実行すると、行と行が密着した 1 行間隔 で印刷されます(フォントやプリンタによっては、最も低い文字の最 下部と最も高い文字の最上部が接触する可能性があります)。 例 PrintSetSpacing(JobNum,1) 以下のステートメントは、1.5 行間隔で印刷します。 PrintSetSpacing(JobNum,1.5) 以下のステートメントは、2 行間隔で印刷します。 PrintSetSpacing(JobNum,2) 描画オブジェクトの印 刷 印刷ジョブでは、以下の描画オブジェクトが使用できます。 • 直線 • 長方形 • 丸長方形 • 楕円 • ピクチャ アプリケーション テクニック 805 高度な印刷技法 印刷ジョブで描画オブジェクトを配置するときには、まず最初に描画 オブジェクトを配置し、次にテキストを加えます。たとえば、印刷領 域内に長方形を描き、次にその長方形の内部に罫線とテキストを加え ます。オブジェクトは輪郭線だけのように見えますが、実際には塗り つぶされています(空白が入っています)。したがって、オブジェクト をテキストや別のオブジェクトの上に重ねて配置すると、そのテキス トや別のオブジェクトは覆い隠されてしまいます。 注意 :PowerBuilder は、すべてのテキストやオブジェクトが印刷領域内 に配置されているかどうかを確認しません。印刷領域内にあるものを 印刷するだけです。 例 以下のステートメントは、1 × 3 インチの長方形を描き、次にその 長方形の内部に会社の住所を印刷します。長方形はページの上端の中 央に描かれます。 IntJob JobNum = PrintOpen() PrintRect(JobNum,2500,0,3000,1000,40) Print(JobNum,2525,"") Print(JobNum,2525,"25 Mountain Road") Print(JobNum,2525,"Milton, MA 02186") PrintClose(JobNum) 806 PowerBuilder 第 3 8 章 初期設定ファイルと Windows レジ ストリの管理 この章について この章では、PowerBuilder アプリケーションの環境設定とデフォ ルト設定を管理する方法について解説します。 内容 項目 環境設定とデフォルト設定について 初期設定ファイルでの情報の管理 Windows レジストリでの情報の管理 ページ 807 808 809 環境設定とデフォルト設定について PowerBuilder アプリケーションは、セッションをまたがってエン ド ユーザの環境設定とデフォルト設定を保存できます。たとえば、 アプリケーションはそのアプリケーションの表示と動作の形態を 管理する設定や、データベースに接続するためにデフォルトのパ ラメータを格納する設定を保持しています。PowerBuilder アプリ ケーションは、初期設定ファイルや Windows レジストリでこのよ うな情報を管理できます。 データベース接続パラメー タ トランザクション オブジェクトの値は、通常の場合、外部ファイ ルから値を取得して設定する必要があります。たとえば、アプリ ケーションを開発しているときは PowerBuilder 初期設定ファイル から、またアプリケーションを配布するときはアプリケーション 固有の初期設定ファイルから値を設定できます。 初期設定ファイル内のデータベース接続パラメータについての詳 細は、182 ページの「外部ファイルからの値の読み込み」を参照し てください。 Windows レジストリにデータベース接続パラメータを登録したり 取得したりする方法については、809 ページの「Windows レジス トリでの情報の管理」を参照してください。 アプリケーション テクニック 807 初期設定ファイルでの情報の管理 ツールバーの設定 PowerBuilder では、ツールバーの設定に関する情報の取得や修正を行 うための関数が用意されています。これらの関数を使用して、現行の ツールバーの設定情報の保存と復元ができます。 詳細については、80 ページの「ツールバー設定の保存と復元」を参照 してください。 保存可能なほかの設定 データベース接続パラメータとツールバーの設定情報のほかに、アプ リケーション特有の設定情報を保存できます。たとえば、色、フォン トの表示設定やエンド ユーザの環境設定情報などを保持できます。 初期設定ファイルでの情報の管理 初期設定ファイルにア クセスする関数 PowerBuilder には、初期設定ファイルを使用してアプリケーション設 定を管理するための関数が用意されています。 表 38-1: PowerBuilder 初期設定ファイル関数 関数 ProfileInt ProfileString SetProfileString 説明 プロファイル ファイルの設定値を Integer 型で取得する プロファイル ファイルの設定値を String 型で取得する プロファイル ファイルに値を書き込む これらの関数についての詳細は、 『PowerScript リファレンス』マニュ アルを参照してください。 レジストリでの ProfileString 関数の使い方については、808 ページの「初 期設定ファイルにアクセスする関数」を参照してください。 APP.INI の書式 以下の例では、APP.INI という名前のプロファイルで、アプリケーショ ンの情報を管理しています。このファイルは、アプリケーションの表 示形態を管理するための環境設定の情報が記述されています。ファイ ルには、4 つのカラー設定が記述された [Preferences] セクションがあり ます。 [Preferences] WindowColor=Silver BorderColor=Red BackColor=Black TextColor=White 808 PowerBuilder 第 38 章 以下のスクリプトでは、APP.INI ファイルのカラー設定を取得します。 値の取得 wincolor brdcolor bckcolor txtcolor 初期設定ファイルと Windows レジストリの管理 = = = = ProfileString("app.ini", ProfileString("app.ini", ProfileString("app.ini", ProfileString("app.ini", 値の設定 "Preferences", "Preferences", "Preferences", "Preferences", "WindowColor", "") "BorderColor", "") "BackColor", "") "TextColor", "") 以下のスクリプトでは、APP.INI ファイルにカラー設定を保存します。 SetProfileString("app.ini", SetProfileString("app.ini", SetProfileString("app.ini", SetProfileString("app.ini", "Preferences", "Preferences", "Preferences", "Preferences", "WindowColor", wincolor) "BorderColor", brdcolor) "BackColor", bckcolor) "TextColor", txtcolor) Windows レジストリでの情報の管理 レジストリにアクセス する関数 PowerBuilder には、Windows レジストリを使用してアプリケーション 設定を管理するための関数が用意されています。 表 38-2: PowerBuilder レジストリ設定関数 関数 RegistryDelete RegistryGet RegistryKeys RegistrySet RegistryValues 説明 Windows レジストリのキーまたはキーの値を削除する Windows レジストリから値のデータを取得する Windows レジストリのキーの 1 つ下位レベルにあるサブ キーのリストを取得する Windows レジストリに、キー、値の名前、値のデータを設 定する。キーまたは値の名前が存在しない場合は、新しい キーまたは値の名前を作成する キーに関連付けられた値の名前のリストを取得する これらの関数についての詳細は、『PowerScript リファレンス』マニュ アルを参照してください 。 初期設定ファイルを無 効にする ProfileString 関数を使用すると、初期設定ファイルからではなく、レジ ストリから情報を取得できます。次の位置に INIFILEMAPPING という 名の新しいキーを作成します。 HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion WIN.INI ファイルを無効にするには、WIN.INI という名の INIFILEMAPPING に次の値を持つサブキーを作成します。 #usr:software\microsoft\windows\currentversion\extensions アプリケーション テクニック 809 Windows レジストリでの情報の管理 この後の例では、データベース接続パラメータの情報を管理するため にレジストリを使用します。接続パラメータは、レジストリの HKEY_CURRENT_USER\Software キーの下の MyCo\MyApp\database サブキーで管理されています。 レジストリからの値の 取得 以下のスクリプトは、デフォルトのトランザクション オブジェクトの 値をレジストリから取得します。 RegistryGet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "dbms", sqlca.DBMS) RegistryGet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "database", sqlca.database) RegistryGet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "userid", sqlca.userid) RegistryGet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "dbpass", sqlca.dbpass) RegistryGet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "logid", sqlca.logid) RegistryGet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "logpass", sqlca.logpass) RegistryGet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", “"servername", sqlca.servername) RegistryGet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "dbparm", sqlca.dbparm) レジストリへの値の登 録 & & & & & & & 以下のスクリプトは、トランザクション オブジェクトの値をレジスト リに登録します。 RegistrySet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "dbms", sqlca.DBMS) RegistrySet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "database", sqlca.database) RegistrySet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "userid", sqlca.userid) RegistrySet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "dbpass", sqlca.dbpass) RegistrySet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "logid", sqlca.logid) RegistrySet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "logpass", sqlca.logpass) RegistrySet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "servername", sqlca.servername) RegistrySet("HKEY_CURRENT_USER\Software\MyCo\MyApp\database", "dbparm", sqlca.dbparm) 810 & & & & & & & & & PowerBuilder 第 3 9 章 InfoMaker の様式とアクションの作成 この章について この章では、PowerBuilder で様式を作成して InfoMaker ユーザに提 供する方法について説明します。 内容 項目 フォーム様式について フォーム様式でのデータウィンドウ コントロールの命名 フォーム様式の作成および使用 既存の様式の修正 最初からの様式の作成 様式の完成 様式の使い方 ページ 811 815 816 816 819 820 824 フォーム様式について InfoMaker には、ユーザが洗練されたフォームを作成できるよう に、組み込みフォーム様式があります。PowerBuilder を使用する と、開発者は独自のフォーム様式を作成して、InfoMaker ユーザに 提供できます。このようなカスタム フォーム様式を使うと、フォー ム内で特定の標準を使うように指定して、InfoMaker ユーザに対し て機能を追加できます。たとえば、以下のように指定できます。 • 各フォーム内の開発者の組織のロゴ表示 適当な位置にロゴを配置したカスタム フォーム様式を作成で きる • 組み込みフォーム様式で提供されるツールバーの再構成 組み込みフォーム様式を修正してカスタム フォーム様式とし て保存できる アプリケーション テクニック • フォーム内でのドラッグ アンド ドロップ • フォーム内でのピクチャボタン、編集コントロール、および そのほかのコントロールの配置 811 フォーム様式について PowerBuilder ウィンドウ内でできることは、ほとんどすべてカスタム フォーム様式内でもできます。 フォーム様式 フォーム様式が構成さ れる方法 InfoMaker のユーザはデータを管理するのにフォームを使用します。 フォーム内でデータを表示、追加、削除、および更新できます。各 フォームはフォーム様式を基礎としており、以下の項目を指定します。 • たとえば、フリーフォーム、グリッド、またはマスタ / 詳細提示様 式などデータを提示する方法 • フォームを実行するときに使用可能なメニューとツールバー • そのフォーム内でユーザがコマンドボタンにアタッチできるアク ション PowerBuilder でフォーム様式を作成します。フォーム様式は次の 2 つ のもので構成されています。 • ウィンドウ • メニュー 図 39-1: PowerBuilder フォーム様式 ウィンドウについて ウィンドウはフォームの土台の役割を果たしま す。ウィンドウには特別な名前をもつ 1 つまたは複数のデータウィン ドウ コントロールがあります。フォーム様式の中心となるのはこの データウィンドウ コントロールです。ユーザはこの特別なデータウィ ンドウ コントロールを通じて、データをフォーム内で表示または変更 します。 この章では、この特別なデータウィンドウ コントロールをセントラル データウィンドウ コントロールと呼ぶことにします。セントラル デー タウィンドウ コントロールには、サポートされている名前のセットか ら名前を付けなければなりません。 セントラル データウィンドウに加えて、ウィンドウには PowerBuilder 上のウィンドウ内に配置できるコマンドボタン、ラジオボタン、ユー ザ オブジェクト、およびピクチャなどすべてのコントロールを配置で きます。 メニューについて フォームを実行する場合、メニューから項目を取り 除けます。メニューをメニュー ペインタで作成して、そのフォーム様 式が基礎としているウィンドウにそのメニューを関連付けます。 812 PowerBuilder 第 39 章 InfoMaker の様式とアクションの作成 メニューを作成する場合、フォームが実行されているときにツール バーに表示するメニュー項目を指定できます。このツールバーは PowerBuilder ツールバーと同じように動作します。 フォーム様式には、フォーム内でコマンドボタン にアタッチできたり、スクリプト内で呼び出させたりするアクション があります。 アクションについて フォーム様式のウィンドウ内で定義する各パブリック ウィンドウ関 数を、そのフォーム様式のユーザはアクションとして使用できます。 例 たとえば、組み込み様式であるフリーフォームは以下のもので構成さ れています。 • w_pbstyle_freeform ウィンドウ • m_pbstyle_freeform メニュー w_pbstyle_freeform について w_pbstyle_freeform ウィンドウには dw_freeform という名前のデータウィンドウ コントロールがあります。 その他のコントロールはありません。 PowerBuilder ウィンドウは、以下のようにウィンドウレベルの関数を 多く定義しています。 フリーフォーム フォーム様式のユーザは、これらのウィンドウ関数を それぞれ、InfoMaker 内でアクションとして使用できます。 アプリケーション テクニック 813 フォーム様式について m_pbstyle_freeform メニューでは、フリー フォーム様式を基礎とするフォームの実行時に、メニュー項目および ツールバー項目が使用できます。 m_pbstyle_freeform について たとえば、m_pbstyle_freeform には、 [検索条件の指定]項目が[行]メ ニューにあり、この項目はツールバーにも表示されます。 InfoMaker ユーザがフォームを実行するとき、フォーム内で行を検索す るのに使用する選択条件を入力するために、 [検索条件の指定]を選択 できます。 814 PowerBuilder 第 39 章 InfoMaker の様式とアクションの作成 フォーム様式でのデータウィンドウ コントロールの命名 フォーム様式には、組み込み InfoMaker フォーム様式のいずれかのデー タウィンドウ コントロールを基礎とする 1 つまたは複数のセントラル データウィンドウ コントロールが含まれています。 これらのデータウィンドウ コントロールの動作を理解する一番良い 方法は、InfoMaker 内で各組み込み様式を使用してフォームを作成する ことです。そして、フォーム様式を作成するとき、組み込み様式の中 からフォーム様式内で表示したい提示様式の型に一致するものを選択 します。 たとえば、基本フリーフォームをデータ入力フォームとするためには、 w_pbstyle_freeform にあるデータウィンドウ コントロールの dw_freeform を基礎としてフォームを作成します。 フォーム様式を作成するときは、セントラル データウィンドウ コント ロールに以下の名前の内 1 つを割り当てなければなりません。 • dw_freeform • dw_grid • dw_master_12many • dw_detail_12many • dw_master_many21 • dw_detail_many21 有効な組み合わせ . フォーム様式内では、表 39-1 の 4 つのデータウィン ドウの組み合わせの内 1 つを使用しなければなりません。 表 39-1: PowerBuilder データウィンドウ コントロール 使用するデータウィンドウ コントロール名 dw_freeform のみ dw_grid および dw_freeform dw_master_12many および dw_detail_12many dw_master_many21 および dw_detail_many21 アプリケーション テクニック 基礎となる組み込み様式 フリーフォーム提示様式 グリッド提示様式 dw_grid はセントラル データウィンドウ コン トロール。dw_freeform は結果集合を共有して バックグラウンドで動作し、フォーム内のどこ でもユーザは計算フィールドを配置できる マスタ詳細 /1 対多 マスタ詳細 / 多対 1 815 フォーム様式の作成および使用 フォーム様式の作成および使用 ❖ フォーム様式を作成および使用するには 1 次のどちらかを実行します。 • 既存のフォーム様式からウィンドウとメニューをコピーする • 新規にウィンドウを作成して、サポートされている名前を持つ 1 つか 2 つのデータウィンドウ コントロールをその中に配置 する 2 ウィンドウがフォーム様式の基礎としての役割を果たしているこ とを示す特別なコメントをつけて保存します。 3 ウィンドウにコントロールを追加したり、メニューを修正したり、 アクションとして動作するウィンドウ関数を定義したりなどし て、フォーム様式を拡張します。 4 フォーム様式の中で使用するすべてのオブジェクト(ウィンドウ、 ユーザ オブジェクト、およびメニューなど)を、InfoMaker ユーザ に対して様式ライブラリとして定義するライブラリにコピーしま す。 5 InfoMaker ユーザに対する探索パスを様式ライブラリに追加します。 InfoMaker ユーザが新たにフォームを作成する場合は、開発者の定 義したフォーム様式が新規フォーム ダイアログボックスに表示さ れます。ユーザは開発者が作成した様式を基礎としてフォームを 作成できます。 この章の後の箇所では、これらの操作手順について説明します。 既存の様式の修正 フォーム様式を作成する一番簡単な方法は、既存のフォーム様式をコ ピーして、作業することです。構造を調べて多少の変更を加えると、 短時間でフォーム様式の働きを理解できます。 ❖ 既存のフォーム様式の修正を始めるには 1 816 PowerBuilder 上でライブラリ ペインタを開きます。 PowerBuilder 第 39 章 2 InfoMaker の様式とアクションの作成 フォーム様式の土台としての役割を果たすウィンドウとメニュー を開発者のアプリケーションのライブラリ探索パスにあるライブ ラリにコピーします。 組み込みフォーム様式から始める 組み込みのフォーム様式の基礎としての役割を果たすウィンドウ とメニューは、IMSTYLE110.PBL にあります。このファイルは InfoMaker に同梱されて、InfoMaker 11.0 ディレクトリにインストー ルされます。この PBL のコピーを作成して、独自のフォーム様式 の基礎として使用することができます。 3 4 ウィンドウ ペインタ上でウィンドウを開き、メニュー バーから [ファイル|名前を付けて保存]を選択して新しい名前でウィンド ウを保存します。 そのウィンドウに新しい名前を付けます。 名前は自由に設定できますが、フォーム様式を定義するウィンド ウ名は、InfoMaker ユーザが使用するすべての様式ライブラリに 渡って固有の名前をつける必要があります。 5 ウィンドウに対して特別なコメントを定義します(方法について は、818 ページの「様式の基礎としてのウィンドウの識別」を参照 してください)。 6 [OK]をクリックしてウィンドウを保存します。 7 メニュー ペインタ上でメニューを開き、メニュー バーから[ファ イル|名前を付けて保存]を選択してメニューを新しい名前で保 存します。 8 新しい名前と任意のコメントを付け、 [OK]をクリックしてメ ニューを保存します。 メニューに対してはコメントを付ける必要はありませんが、作成 しているフォーム様式内で使用するときと同様に識別できるよう にしたほうがよいでしょう。 9 アプリケーション テクニック フォーム様式を拡張します(方法については、820 ページの「様式 の完成」を参照してください)。 817 既存の様式の修正 様式の基礎としてのウィンドウの識別 InfoMaker に、ライブラリ内のウィンドウがフォーム様式の基礎として の役割を果たしていることを認識させるには、次のテキスト Style: で 始まるコメントをそのウィンドウに対して指定しなければなりませ ん。 Style: 様式を説明するテキスト Style: に続くテキストは InfoMaker の新規フォーム ダイアログボック ス内のフォーム様式のアイコンの下に表示されます。 たとえば、コメント「Style: 企業データ管理」付きの w_pbstyle_freeform ウィンドウを様式ライブラリに保存する場合には、InfoMaker ユーザが 新しいフォームを作成するときに、次のような画面が表示されます。 最初にウィンドウを保存するときとライブラリ ペインタ上のどちら の場合もコメントを指定できます。 詳細については、PowerBuilder の『ユーザーズ ガイド』マニュアルを 参照してください。 818 PowerBuilder 第 39 章 InfoMaker の様式とアクションの作成 最初からの様式の作成 フォームの動作を一度理解すると、最初からフォームを作成できるよ うになります。 ❖ フォーム様式を最初から作成するには 1 新しいウィンドウを作成します。 2 そのウィンドウにデータウィンドウ コントロールを配置します。 3 コントロールのプロパティ ビューで、そのコントロールに特別な 名前を付けます。 特別な名前のリストについては、815 ページの「フォーム様式での データウィンドウ コントロールの命名」を参照してください。 4 必要に応じて、コントロールのプロパティを変更します。 たとえば、垂直および水平のスクロールバーを追加できます。 コントロールにデータウィンドウ オブジェクトを関連付けない 新しいフォームを作成するときに、InfoMaker ユーザがコントロー ルのデータを指定します。 5 作成するフォーム様式が 2 つのデータウィンドウ コントロールを 使用する場合は、ウィンドウ上にもう 1 つ データウィンドウ コン トロールを配置して、その名前を有効な組み合わせに合致させま す。 有効な組み合わせのリストについては、815 ページの「フォーム様 式でのデータウィンドウ コントロールの命名」を参照してくださ い。 6 ウィンドウを保存して、コメントを指定します。 方法については、818 ページの「様式の基礎としてのウィンドウの 識別」を参照してください。 アプリケーション テクニック 819 様式の完成 様式の完成 様式を完成するには、ウィンドウとメニューを拡張して必要な処理を 提供するようにします。たとえば、以下のことが可能です。 • セントラル データウィンドウ コントロールに対して作業する • ウィンドウにコントロールを追加する • アクション(フォーム様式にアクションとして表示される関数)を 定義する • メニューと関連するツールバーを修正する • ウィンドウ、コントロール、およびメニュー項目用にスクリプト を書く • ドラッグ アンド ドロップなどその他の機能をウィンドウに追加 する セントラル データウィンドウ コントロールに対する作業 特別な名前をもつデータウィンドウ コントロールは、フォームの中心 です。これらのコントロールにおいてユーザがフォーム上でデータを 操作します。 次の事柄を理解する必要があります。 フリーフォームのデー タウィンドウのサイズ を指定する方法 • フォーム上でフリーフォームのデータウィンドウのサイズを指定 する方法 • フォーム上でコントロールに対してデータを検索する方法 組み込み様式と同じように、作成するフォーム様式はすべて、フリー フォームのデータウィンドウを含んでいます。PowerBuilder のウィン ドウ ペインタ上でフリーフォームのデータウィンドウ コントロール にどのようなサイズを指定するかに関係なく、フリーフォームのデー タウィンドウは InfoMaker のフォーム ペインタ上のフォーム全体を占 めます。InfoMaker がフリーフォームのデータウィンドウを拡大して、 フォーム上のどこにでも計算フィールドなどのデータを配置できるよ うにします。 これは、PowerBuilder 上で指定するウィンドウの背景色はフォーム上 では無視されるということです。 820 PowerBuilder 第 39 章 セントラル データ ウィンドウ コント ロールに対する行の検 索 InfoMaker の様式とアクションの作成 InfoMaker ユーザがフォームを実行するとき、InfoMaker は自動的に SQLCA トランザクション オブジェクトに正しい値を与えるので、開 発者がそのためのスクリプトを書く必要はありません。セントラル データウィンドウに対して行を検索するのに必要なのは、コントロー ルのトランザクション オブジェクトを設定して、行を検索することだ けです。 たとえば、dw_freeform という名前のコントロールに対してデータを検 索するには、次のようにスクリプトを書きます。 dw_freeform.SetTransObject(SQLCA) dw_freeform.Retrieve() フォームが開くときにデータを提示するには、そのウィンドウの Open イベント内にこのスクリプトを書いてください。 トランザクション オブジェクトの詳細については、第 12 章「トラン ザクション オブジェクトの使い方」を参照してください。 コントロールの追加 フォーム様式の基礎としての役割を果たすウィンドウはすべて、少な くとも 1 つの データウィンドウ コントロールを持っています。それに 加えて、標準の PowerBuilder ウィンドウに追加できるコマンドボタン、 ユーザ オブジェクト、テキスト、編集ボックス、ピクチャ、および描 画オブジェクトなど、そのほかすべてのコントロールを追加できます。 フォームのユーザは、開発者がウィンドウ内に配置したコントロール を移動できますが、削除はできません。 同様に、ユーザはフォーム ペインタ上でフォームにコントロールを追 加できます。アクションを関連付けて、コマンドボタンおよびピクチャ ボタンを作成します。アクションを以下に説明します。 アプリケーション テクニック 821 様式の完成 アクションの定義 ユーザはカスタム フォーム様式を使用して作成されたフォームに、コ マンドボタンまたはピクチャボタンを追加したい場合があります。開 発者は、フォーム様式を作成するとき、フォーム様式にアクションを 定義して、追加したボタンで可能な動作を指定します。ユーザがボタ ンを配置するとき、リストから行いたいアクションを選択します。 アクションはパブリックなウィンドウレベル関数として実装されてい ます。 ❖ アクションを定義するには 1 2 ウィンドウ ペインタのスクリプト ビューで、メニューバーから [挿入|関数]を選択します。 ウィンドウレベル関数を定義します(方法については、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください)。 ウィンドウ関数をアクションとしてフォーム ユーザが使用できる ようにするには、関数をパブリック(public)として定義してくだ さい。定義した関数の引数はアクションのパラメータとして使用 されます。定義した各パブリック ウィンドウ関数は、フォーム ペ インタのアクションの選択 ダイアログボックス内でアクションと して一覧表示されます。 アクションとして使用できない関数の定義 フォーム内でアクションとして使用できないウィンドウ関数を定 義および使用する場合は、その関数をプライベート(private)とし て定義してください。 822 PowerBuilder 第 39 章 InfoMaker の様式とアクションの作成 メニューの使い方 開発者は、ユーザがフォームを実行するときに表示されるメニューと ツールバーを指定します。メニュー ペインタでメニューを定義し、 フォーム様式の土台として役割を果たすウィンドウに関連付けます。 フォームが実行されるとき、定義したメニュー内の各メニュー項目が 表示されます。加えて、InfoMaker は[ウィンドウ]および[ヘルプ] メニューを追加して、InfoMaker 環境下でフォームを実行するときに、 ユーザがウィンドウを操作したり、オンライン ヘルプを参照したりで きるようにします。 オンライン ヘルプの提供 [ヘルプ]項目をメニューバー上で定義して、[ヘルプ]ドロップダウ ン メニュー内で表示されるメニュー項目を定義できます。InfoMaker 上 でフォームを実行するときには、この[ヘルプ]項目は表示されませ んが、実行ファイルからフォームを実行するときには表示されます。 InfoMaker 実行ファイルの詳細については、InfoMaker の『ユーザーズ ガイド』マニュアルを参照してください。 ツールバー上の項目 MDI アプリケーションの場合と同様、フォームの実行時に、ツール バーにメニュー項目を表示するように指定できます。 スクリプト フォームで使用するメニューには、標準ウィンドウで使用するメ ニューに対してと同じスクリプト技術を使用します。通常、ウィンド ウとそのメニューとの間で通信するには、ウィンドウに対してユーザ イベントを定義し、メニュー オブジェクトの親ウィンドウ プロパティ を使用してフォーム ウィンドウに照会し、メニューからそのイベント を発生させます。この技術は組み込みフォーム様式で使用されます。 詳細情報 メニューとユーザ イベントの使い方の詳細については、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください。 メニューに対するツールバーの関連づけの詳細については、第 5 章 「MDI アプリケーションの構築」を参照してください。 アプリケーション テクニック 823 様式の使い方 スクリプトの記述 ウィンドウ、コントロール、およびメニュー オブジェクトに対するス クリプトは、標準ウィンドウおよびメニューに対してと同じ方法で書 きます。データウィンドウ コントロールで作業する場合は、SQLCA ト ランザクション オブジェクトのプロパティを設定する必要はありま せん。これは、ユーザがフォームを実行するときに、InfoMaker が自動 的に設定するからです。 開発者が書くスクリプトをサポートするために、ユーザ定義のグロー バル関数およびグローバル構造体を定義できます。しかし、InfoMaker にはアプリケーション オブジェクトがないので、フォーム様式はグ ローバル変数またはグローバル外部関数宣言を使用できません。 その他の機能の追加 フォームは開発者の必要に応じて洗練されたものにできます。たとえ ば、ドラッグ アンド ドロップ機能を実装したり、フォームでメールを 使用したりできるようにします。 ウィンドウに対して作成できる機能の詳細については、PowerBuilder の『ユーザーズ ガイド』マニュアルを参照してください。 様式の使い方 フォーム様式を完成、または少なくともテストできるバージョンを完 成すると、そのフォームを使用できます。 ❖ InfoMaker ユーザが様式を使用できるようにするには 1 フォーム様式を定義するウィンドウとメニューが InfoMaker のア クセス可能なライブラリ(スタイル ライブラリ)内にあることを 確認します。 2 ウィンドウ、ユーザ オブジェクト、グローバル ユーザ定義関数な どフォーム様式内で使用するその他の PowerBuilder オブジェクト を同じライブラリに追加します。 3 InfoMaker ユーザのパスに、スタイル ライブラリを追加します。 詳細については、InfoMaker の『ユーザーズ ガイド』マニュアルを 参照してください。 824 PowerBuilder 第 39 章 InfoMaker の様式とアクションの作成 カスタム フォーム様式を使用したフォームの作成 スタイル ライブラリを使用する InfoMaker ユーザが新しいフォームを 作成するときには、新規フォーム ダイアログボックスの[フォーム様 式]ボックス上にすべてのカスタム フォーム様式が表示されます。 カスタム様式と汎用アイコンが表示されます。 InfoMaker ユーザはデータ ソースとカスタム様式を選択するだけで、開 発者の作成したフォーム様式を基礎としたフォームの作成を開始でき ます。開発者は作成したフォーム様式について説明を提供しなければ なりません。 継承の理解 ユーザがフォームを作成するときは、開発者がフォーム様式に対して 作成したウィンドウの子孫ウィンドウに対して作業します。つまり、 開発者が PowerBuilder で作成したフォーム様式ウィンドウは先祖ウィ ンドウであり、InfoMaker で使用するフォーム ウィンドウは子孫ウィ ンドウということです。フォーム様式を変更した場合、その変更はユー ザがその様式を使用して次に作業するときに反映されます。 たとえば、フォーム様式にコントロールを追加した場合、ユーザが後 でその様式を使用して既存のフォームを開くときにそのコントロール が自動的に表示されるように設定できます。 注意 様式を使用してすでに作成されたフォームを無効にする変更はしない でください。 アプリケーション テクニック 825 様式の使い方 フォーム様式の使用の管理 ネットワーク上に様式ライブラリを格納して、InfoMaker ユーザ全員が 簡単にそれらを使用できるように設定できます。ネットワーク上に様 式ライブラリをセットアップするには、ネットワーク上で初期設定 ファイルを共有した状態で行います。共有様式ライブラリを参照する InfoMaker 初期設定ファイルをネットワーク上に配置してから、InfoMaker ユーザが初期設定ファイルにアクセスできるように InfoMaker ユーザ を設定します。 ❖ 組織全体でスタイルライブラリを使用できるようにするには 1 InfoMaker ユーザがアクセスできるネットワーク上のディレクトリに 様式ライブラリを配置します。 2 InfoMaker を開き、ライブラリ ペインタに移動し、探索パスにすべ ての様式ライブラリがリストされていることを確認します。 3 InfoMaker を閉じます。 4 InfoMaker 初期設定ファイルを InfoMaker ユーザ全員がアクセスで きるネットワーク上のディレクトリにコピーします。 これが共有初期設定ファイルです。このファイルは[Application] セクションの StyleLib 変数にスタイル ライブラリすべてを記録し ます。 5 InfoMaker ユーザが共有初期設定ファイルにアクセスできるように セットアップします。 各 InfoMaker ユーザが InfoMaker 内で共有初期設定ファイルの位置 を指定する必要があります。 詳細については、次の「InfoMaker 上での共有 InfoMaker 初期設定 ファイルの位置の指定」を参照してください。 InfoMaker 上での共有 InfoMaker 初期設定 ファイルの位置の指定 一度共有初期設定ファイルがユーザの InfoMaker 初期設定ファイルで 定義されると、ユーザの様式ライブラリ探索パスはユーザのローカル InfoMaker 初期設定ファイルに加えて、共有初期設定ファイルで定義さ れた様式ライブラリ全部から成りたちます。ユーザが新しいフォーム を作成する場合、様式ライブラリ全部で定義されたフォーム様式が新 規フォーム ダイアログボックスに表示されます。 各 InfoMaker ユーザは、共有初期設定ファイルの位置を InfoMaker に知 らせる必要があります。 826 PowerBuilder 第 39 章 ❖ InfoMaker の様式とアクションの作成 共有 InfoMaker 初期設定ファイルの位置を指定するには 1 InfoMaker メニューバーの[ツール|システム オプション]を選択 します。 2 [全般]プロパティ ページ内で、共有 InfoMaker 初期設定ファイル へのパスを入力します。 3 [OK]をクリックします。 InfoMaker は、InfoMaker 初期設定のパスをレジストリに保存しま す。 InfoMaker ユーザが組み込みフォーム様式を使用しないようにしたい 場合もあります。つまり、開発者の組織のユーザ定義様式を基礎とす るフォームのみをユーザに使用させたいという場合です。このような 場合、新規フォーム ダイアログボックスに表示されないようにして、 組み込み様式を使用しないようにします。 組み込み様式の使用を 防ぐ ❖ 組み込み様式の表示を禁止するには 1 ネットワーク上の共有初期設定ファイルを前節で説明したように 設定します。 2 共有初期設定ファイルの [Window] セクションに次の行を追加し ます。 ShowStandardStyles = 0 共有初期設定ファイルでこの行を指定すると、新しいフォームを作成 するときに、ユーザはユーザ定義フォーム様式からのみ選択できるよ うになります。InfoMaker はユーザのローカル InfoMaker 初期設定ファ イルにある ShowStandardStyles 行を無視することに注意してください。 アプリケーション テクニック 827 様式の使い方 828 PowerBuilder 第 9 部 配布のテクニック 第 9 部では、アプリケーションを配布するためのパッ ケージ化の方法と、配布に必要なファイルについて説明 します。 第 4 0 章 配布用アプリケーションのパッケー ジ化 この章について この章では、完成した実行アプリケーションをユーザに配布する ための準備方法について説明します。 内容 項目 アプリケーションの配布について アプリケーションの実行版の作成 エンド ユーザへのアプリケーションの配布 ページ 831 832 847 アプリケーションの配布について PowerBuilder を使用すると、数多くのアプリケーション アーキテ クチャ用に、アプリケーションを開発および配布できます。 従来型のクライアント / サーバ アプリケーション インターネットと分散アプ リケーション アプリケーション テクニック この章の主なねらいは、実行ファイルを作成して、単層または 2 階層のアプリケーションを配布用にパッケージ化することです。 この章の内容は、コンパイル済みコードを使用するか擬似コード を使用するか、動的ライブラリ(PBD または DLL)を使用するか どうかとその編成方法、ビットマップやアイコンなどのリソース を別々に配布するのか、それとも PowerBuilder リソース ファイル (PBR)を使用するのか、といった決定をする際に役立ちます。 多層アプリケーションでクライアントを構築する場合には、従来 のクライアント / サーバ アプリケーションの場合と同じ選択を行 う必要があります。EAServer または COM コンポーネントを作成 している場合、あるいは PowerBuilder ウィンドウ プラグインまた は PowerBuilder ウィンドウ ActiveX を使用している場合には、833 ページの「パッケージに含まれる要素」で後述する PowerBuilder 動的ライブラリ(PBD)と PBR について知る必要があります。 831 アプリケーションの実行版の作成 詳細情報 クライアント / サーバ アプリケーション、多層アプリケーション、お よび Web アプリケーションで配布しなければならないファイルにつ いての詳細は、第 41 章「アプリケーションとコンポーネントの配布」 を参照してください。 アプリケーションの実行版の作成 以下の節では、パッケージ化のプロセスについて詳しく説明し、最終 的に作成されるアプリケーションのさまざまな選択事項について、ア ドバイスします。以下のことについて説明します。 • コンパイラの基本事項 • パッケージに含まれる要素 • パッケージ化モデルの選択 • パッケージ化モデルの実装 • 実行アプリケーションのテスト コンパイラの基本事項 アプリケーションを計画するとき、基本的に考慮する事項の 1 つとし て、ア プ リ ケ ー シ ョ ン を 生 成 す る コ ン パ イ ラ 形 式 が あ り ま す。 PowerBuilder では、Pcode とマシン コードのいずれかを選択できます。 Pcode マシン コード Pcode(中間コード)は、PowerBuilder のすべてのプラットフォームで サポートされているインタプリタ言語です。Pcode は、PowerBuilder が 個々のオブジェクトを実行可能な状態で格納する際にライブラリ (PBL ファイル)内で使用する形式と同じです。Pcode の利点は、サイ ズ、信頼性、移植性です。 PowerBuilder は、コードを生成およびコンパイルして、マシン コード の実行ファイルまたは動的ライブラリを作成します。マシン コードの 最大の利点は、実行速度の速さにあります。 PowerBuilder DLL の呼び出しはできない PowerBuilder マシン コード DLL をほかのアプリケーションから呼び 出すことはできません。 832 PowerBuilder 第 40 章 使用するコードの決定 配布用アプリケーションのパッケージ化 自分のプロジェクトにとって Pcode とマシン コードのどちらが適切か を決めるためのガイドラインを以下に示します。 • 作成したアプリケーションでスクリプト処理を集中的に行 う場合は、マシン コードを使用することを検討します。コード内 でループ構造、浮動小数点演算、整数演算、または関数の呼び出 しを使う頻度が非常に高い場合は、Pcode よりも優れた処理能力を 発揮します。アプリケーションに前述のような特徴がない場合は、 マシン コードによる処理が Pcode よりも目に見えて優れているこ とはありません。作成するアプリケーションでマシン コードを使 用するとメリットがあると考えられる場合は、ベンチマーク テス トをいくつか実行して効果を調べます。 速度 Pcode はマシン コードより速く生成されます。マシン コードを 使ってアプリケーションを配布する予定であっても、アプリケー ションのテスト用実行モジュールをすばやく作成したいときには Pcode を使用できます。 • サイズ Pcode を使って生成されるファイルは、マシン コードを 使って生成されるファイルよりサイズが小さくなります。ファイ ルのサイズが大きな問題であるコンピュータにアプリケーション を配布する場合、または Web のダウンロードまたはファイル転送 を使って配布する場合は、マシン コードの速度をあきらめ、Pcode を選択したほうがよいでしょう。 パッケージに含まれる要素 どちらのコンパイラ形式を選択した場合でも、PowerBuilder で作成す るアプリケーションは、以下の要素のいずれか 1 つまたは複数で構成 されます。 • 実行ファイル • 動的ライブラリ • リソース 特定のプロジェクトに必要な要素を決めるには、まず、各要素に関す る知識が必要です。 実行ファイルについて サーバ コンポーネントまたは Web アプリケーションとして配布する のではなく、実行ファイルとしてユーザに配布する単層または 2 階層 のアプリケーションを作成している場合には、必ず実行(EXE)ファ イルを作成することになります。 アプリケーション テクニック 833 アプリケーションの実行版の作成 この実行ファイルは、最低でもアプリケーションをターゲット プラッ トフォームでネイティブに実行するためのコードを含みます。たとえ ば、ユーザが配布されたアプリケーションを起動するときに、実行ファ イルのアイコンをデスクトップでダブルクリックすれば起動できるこ とを意味します。 実行ファイルでのその他の要素 アプリケーション用に選択したパッケー ジ化モデルの種類によって、実行ファイルは以下の要素のいずれか 1 つまたは複数を含みます。 • アプリケーションのライブラリに入っているコンパイル済みオブ ジェクト 配布するファイルが 1 つで済むように、すべてのオブジェクトを 実行ファイルに入れたり、1 つの実行ファイルと 1 つまたは複数の 動的ライブラリにアプリケーションを分割したりできます。詳細 については、834 ページの「動的ライブラリについて」を参照して ください。 • アプリケーション用にパッケージ化した任意の動的ライブラリに 含まれるオブジェクトとリソースを検索するために、PowerBuilder の実行システムが使用する実行ライブラリ リスト • ビットマップなど、アプリケーションが使用するリソース 図 40-1: 実行ファイルの内容 動的ライブラリについ て 834 アプリケーション全体を 1 つの大きな実行ファイルに収める代わり に、そのオブジェクトの一部またはすべてを 1 つまたは複数の動的ラ イブラリで配布できます。PowerBuilder が動的ライブラリを実装する 方法は、選択するコンパイラ形式によって異なります。 PowerBuilder 第 40 章 配布用アプリケーションのパッケージ化 表 40-1: PowerBuilder 動的ライブラリ 作成コード マシン コード 実装される動的ライブラリ DLL ファイル(ダイナミック リンク ライブラリ) Pcode マシン コードの動的ライブラリは、Windows では拡張子 .dll が付加される。これらの動的ライブラリは、オペレー ティング環境における、ほかの標準的な共有ライブラリ と同様に動作する。これらの動的ライブラリは、外部の プログラムから呼び出せない点に注意する PBD(PowerBuilder 動的ライブラリ)ファイル これらの動的ライブラリは、実行時にアプリケーション にリンクされるという点で、DLL ファイルに似ている。 ただし、PBD は内部形式が異なるため、DLL とは互換性 がない 2 種類の動的ライブラリ(DLL と PDB)を 1 つのアプリ ケーション内に混在させることはできない 実行ファイルと同様、動的ライブラリに格納できるのは、オブジェク トのソースではなく、コンパイル済みのオブジェクトだけです。 図 40-2: 動的ライブラリ内のコンパイル済みオブジェクト 実行ファイルとは異なり、動的ライブ ラリにはスタートアップ コードが含まれません。動的ライブラリは、 独立して実行することはできません。動的ライブラリは、アプリケー ションを実行したときに、実行ファイル内に必要なオブジェクトが見 つからない場合にアクセスされます。 動的ライブラリ内のその他の要素 アプリケーション テクニック 835 アプリケーションの実行版の作成 動的ライブラリにはビットマップなどのリソースが含まれる場合があ ります。動的ライブラリのオブジェクトに必要なリソースを、その DLL ファイルまたは PBD ファイルに含めることができます。これによって、 動的ライブラリを、再利用可能な、独立したユニットにすることがで きます。ただし、処理効率の視点から考えると、リソースは実行ファ イル内に格納されているときの方が、実行時に速くロードされます。 図 40-3: 動的ライブラリ内のリソース 動的ライブラリを使う理由 表 40-2 に示すように、動的ライブラリの使 用を推奨する理由がいくつかあります。 表 40-2: 動的ライブラリを使用する理由 理由 モジュール性 保守性 再利用性 柔軟性 効率性 詳細 アプリケーションを、管理のしやすい、より小さく、より 多くのモジュール型ファイルに分割できる アプリケーション コンポーネントの個別配布ができる。 ユーザにバグ修正ファイルを提供するために、影響のある 特定の動的ライブラリを配布できる 動的ライブラリは、ユーザ間だけでなく、アプリケーショ ン間でも共有できるため、複数のアプリケーションで同じ コンポーネントを再利用できる 文字列変数のみによって参照されるウィンドウ オブジェク トなど、実行時にアプリケーションによって動的にのみ参 照されるオブジェクトを提供できる このようなオブジェクトは、データウィンドウの場合を除 いて、実行ファイルに含めることはできない 以下の理由により、大規模なアプリケーションでもメモリ を効率的に使用できる • PowerBuilder では、動的ライブラリ全体をメモリ内に一 度にロードしない。その代わり、必要に応じて、動的ラ イブラリから個々のオブジェクトをロードする • 実行ファイルのサイズを小さく抑えることができるた め、ロード時間が速く、扱いやすい 836 PowerBuilder 第 40 章 配布用アプリケーションのパッケージ化 動的ライブラリの編成 動的ライブラリの利用を決めたら、どのライブ ラリ(PBL ファイル)から作成するかを、PowerBuilder に指示する必 要があります。PowerBuilder は、選択した PBL ファイルからコンパイ ル済みの全オブジェクトを、DLL ファイルまたは PBD ファイル内に配 置します。 アプリケーションで一部のオブジェクトしか使用しない場合は、余分 なオブジェクトを動的ライブラリに含めてもファイルが大きくなるだ けです。その解決法は以下のとおりです。 リソースについて 1 新しい PBL ファイルを作成し、必要なオブジェクトだけをその中 にコピーする 2 動的ライブラリのソースとして、作成した新しい PBL ファイルを 使用する ウィンドウやメニューなどの PowerBuilder オブジェクトに加えて、ア プリケーションではさまざまなリソースを使います。リソースの例に は以下のものがあります。 • ピクチャ コントロールまたはピクチャボタン コントロールで表 示するビットマップ • ウィンドウに割り当てるカスタム ポインタ リソースを使うときは、PowerBuilder オブジェクトとともに、アプリ ケーションの一部として配布する必要があります。 PowerBuilder のアプリケーションでは、複数の異なる リソースを使用できます。表 40-3 は、リソースを、使用できるオブ ジェクトごとにリストしています。 リソースの種類 表 40-3: PowerBuilder オブジェクトおよびリソース オブジェクト ウィンドウ オブジェクト とユーザ オブジェクト データウィンドウ オブ ジェクト MDI アプリケーションに おけるメニュー オブジェ クト 使用されるリソースの種類 アイコン(ICO ファイル) ピクチャ(BMP、GIF、JPEG、RLE、および WMF の各ファイル) ポインタ(CUR ファイル) ピクチャ(BMP、GIF、JPEG、RLE、および WMF の各ファイル) ピクチャ(BMP、GIF、JPEG、RLE、および WMF の各ファイル) アプリケーションといっしょに配布するリソースの パッケージ方法を決めるときは、以下のアプローチから選択できます。 リソースの配布 アプリケーション テクニック 837 アプリケーションの実行版の作成 • リソースを実行ファイルに含める PowerBuilder では、実行ファイルの作成時、そのファイルに配置す るオブジェクトについて、リソース(アイコン、ピクチャ、ポイ ンタ)を明示的に参照しているかどうかが自動的に調べられます。 次に、そのようなリソースをすべて、実行ファイル内に直接コピー します。 文字列変数などを介して動的に参照されるリソースは、自動的に コピーされません。そのようなリソースを実行ファイル内にコ ピーするには、リソース(PBR)ファイルを使わなければなりま せん。これは単純なテキスト ファイルで、既存の ICO、BMP、GIF、 JPEG、RLE、WMF、および CUR の各ファイルをこの中に一覧表 示します。 PBR ファイルが完成したら、実行ファイルを作成するときは、PBR ファイルを読み込むよう PowerBuilder に指示することによって、 追加するリソースを指定します。処理効率上の理由で、ほとんど またはすべてのリソースを実行ファイルに含める場合、PBR ファ イルには、動的ライブラリ内のオブジェクトによって使用される リソースも含めることができます。 • リソースを動的ライブラリに含める 1 つまたは複数の動的ライブラリにリソースを直接含めたい場合 がありますが、PowerBuilder は、リソースがそのファイル内のオブ ジェクトにより明示的に参照されるときでも、作成される動的ラ イブラリ内にそのリソースを自動的にコピーしません。この特定 の DLL ファイルまたは PBD ファイル内にどのリソースを入れる かを PowerBuilder に対して指定する PBR ファイルを作成する必要 があります。 リソースを入れる動的ライブラリごとに、個別の PBR ファイルを 使用します。適切であれば、このアプローチを使って、リソース だけを含み、オブジェクトを含まない動的ライブラリを生成する こともできます。空の PBL ファイルをソースとして作業を始める だけです。 • リソース ファイルを個別のファイルで配布する これは、アプリケーションの配布時に、アプリケーションの実行 ファイルおよび動的ライブラリに加えて、さまざまな画像ファイ ルをユーザに提供することを意味します。多くのファイルを配布 することに問題がなければ、一部のファイルを修正する予定があ る場合に便利な方法です。 838 PowerBuilder 第 40 章 配布用アプリケーションのパッケージ化 この方法は、実行時に必要な検索作業が多くなるため、もっとも 速い方法ではないことに注意してください。アプリケーションで リソースが必要なとき、アプリケーションは最初に実行ファイル を、次に動的ライブラリを検索します。リソースが見つからない 場合、アプリケーションは別個のファイル内で検索します。 これらの個々のファイルがどこに格納されているかを、アプリ ケーションがわかるようにしておく必要があります。そうでない 場合は、対応するリソースが表示されません。 特定のアプリケーションをパッケージ化するときは、以上のアプロー チのいずれか 1 つまたは組み合わせを利用できます。 PBR ファイルを使って、動的に参照されるデータウィンドウ オブジェクト を含める 作成中の実行ファイルの中に、アプリケーションが文字列変数を介し てのみ動的に参照するデータウィンドウ オブジェクトを入れたい場 合があります。そのためには、PowerBuilder によって実行ファイル内 にコピーしたいリソースの名前とともに、そのデータウィンドウ オブ ジェクトの名前を、PBR ファイル内に一覧表示しなければなりません。 動的ライブラリを作成するときは、その必要はありません。PowerBuilder によって、ソース ライブラリ(PBL ファイル)のすべてのデータウィ ンドウ オブジェクトが、新しい DLL ファイルまたは PBD ファイル内 に自動的に含まれます。 PowerBuilder リソース ファイルの作成 PBR ファイルは、リソース名(BMP、CUR、ICO、RLE、WMF ファイ ルなど)とデータウィンドウ オブジェクトが一覧で表示されている ASCII テキスト ファイルです。PBR ファイルを作成するには、テキス ト エディタを使用します。各リソースの名前を 1 行に 1 つずつ記述し、 そのリストに拡張子 PBR を付けてファイルとして保存します。以下 は、PBR ファイルのサンプルです。 ct_graph.ico document.ico codes.ico button.bmp next1.bmp prior1.bmp アプリケーション テクニック 839 アプリケーションの実行版の作成 ❖ PowerBuilder リソース ファイルを作成して使用する手順 1 テキスト エディタを使用して、アプリケーションで動的に参照さ れるリソース ファイルをすべて一覧表示するテキスト ファイル を作成します(ファイルの作成については、以下を参照してくだ さい)。 動的ライブラリのリソース ファイルを作成するときは、スクリプ トで動的に割り当てられたリソースだけでなく、動的ライブラリ によって使用されるすべてのリソースを一覧表示します。 2 プロジェクト ペインタで、リソース ファイルを指定します。動的 ライブラリと同様、実行ファイルにリソース ファイルが添付され ていることもあります。 PowerBuilder がプロジェクトを構築するときは、実行ファイルまた は動的ライブラリの PBR ファイルに指定されているすべてのリ ソースを含めます。動的に割り当てられたリソースを個別に配布 する必要はありません。リソースはアプリケーションに含まれて います。 リソースを指定する リソース ファイルが現行ディレクトリにある場合は、以下のように ファイルを一覧表示するだけです。 FROWN.BMP リソース ファイルが別のディレクトリにある場合は、以下のように ファイルへのパスを指定します。 C:\BITMAPS\FROWN.BMP PBR ファイルとスクリプトのパスの一致 PBR ファイルに指定するファイル名は、スクリプトにおけるリソース の参照方法と正確に一致していなければなりません。 スクリプト内の参照にパスが使用される場合は、PBR ファイルに同じ パスを指定する必要があります。スクリプトのリソース ファイルがパ スで修飾されていない場合は、PBR ファイルでも修飾しないようにし ます。 たとえば、次のようなスクリプトがあります。 p_logo.PictureName = "FROWN.BMP" この場合、PBR ファイルは次のように記述する必要があります。 FROWN.BMP PBR ファイルの記述が下記のように異なる場合について説明します。 840 PowerBuilder 第 40 章 配布用アプリケーションのパッケージ化 C:\MYAPP\FROWN.BMP この場合、スクリプトでパスが指定されていないと、PowerBuilder は 実行時にリソースを見つけることはできません。これは、PowerBuilder が実行時には単純な文字列の比較を行うためです。先ほどの例では、 スクリプトを実行するとき、PowerBuilder は実行ファイルに文字列 「FROWN.BMP」で指定されているオブジェクトを探します。実行ファイ ルでは、リソース「C:\MYAPP\FROWN.BMP」として識別されているため、 PowerBuilder はオブジェクトを見つけることができません。 この場合、実行時にはピクチャが表示されず、ウィンドウのコントロー ルは空白になります。 データウィンドウ オ ブジェクトを PBR ファイルに含める データウィンドウ オブジェクトをリストに含めるには、ライブラリ名 (拡張子 PBL)の後にカッコで囲んだデータウィンドウ オブジェクト 名を付けます。たとえば、次のようになります。 sales.pbl(d_emplist) 実行ファイル作成時の現行ディレクトリにデータウィンドウ ライブ ラリがない場合は、PBR ファイルに完全修飾の参照を指定します。た とえば、次のようになります。 c:\myapp\sales.pbl(d_emplist) パッケージ化モデルの選択 前述したとおり、アプリケーションの実行版をパッケージ化するには、 たくさんのオプションがあります。もっとも一般的なパッケージ化モ デルを以下に示します。 スタンドアロンの実行 ファイル このモデルでは、オブジェクトとリソースがすべて実行ファイル内に 含まれているため、配布するファイルは 1 つだけになります。 説明図 図 40-4 に、このモデルの構造のサンプルを示します。 図 40-4: スタンドアロン実行モデル アプリケーション テクニック 841 アプリケーションの実行版の作成 このモデルは、小規模で、簡単なアプリケーションに適してお り、管理をそれほど必要としないアプリケーションの場合には特に適 しています。そのようなプロジェクトに、このモデルを使用すると、 最高の処理効率ともっとも簡単な配布方法が保証されます。 用途 実行ファイルと外部リ ソース このモデルでは、すべてのオブジェクトと大部分のリソースが実行 ファイルに含まれていますが、特定のリソースについては、別個のファ イルを配布します。 説明図 図 40-5 に、このモデルの構造のサンプルを示します。 図 40-5: 外部リソースを含む実行モデル このモデルも小規模で、簡単なアプリケーションに適していま すが、変更の可能性のあるリソースの管理をサポートしているという 点で、前のモデルとは異なります。つまり、実行ファイルの修正コピー を配布しないで特定のリソースの修正コピーをユーザに配布できま す。 用途 このモデルを使うと、ほかのアプリケーションと共有しなければなら ないリソース、または、大規模で使用頻度の低いリソースを扱うこと も可能です。 実行ファイルと動的ラ イブラリ 842 このモデルでは、アプリケーションを 1 つの実行ファイルと 1 つまた は複数の動的ライブラリ(DLL または PBD)に分割します。アプリ ケーションを分割するときは、オブジェクトとリソースをさまざまな 方法で編成できます。表 40-4 に、いくつかの方法を示します。 PowerBuilder 第 40 章 配布用アプリケーションのパッケージ化 表 40-4: 動的ライブラリを含むオブジェクトとリソースの編成 編成の対象 オブジェクト リソース 行えること 実行ファイルにオブジェクトが含まれないようにし、すべ てのオブジェクトを動的ライブラリに配置して、管理を容 易にする。または、 アクセス頻度の高い一部のオブジェクトを実行ファイル に配置して、これらのオブジェクトへのアクセスを最適化 し、残りのオブジェクトすべてを動的ライブラリ内に配置 する 大部分またはすべてのリソースを、それらを使用するオブ ジェクトとともに、動的ライブラリ内に配置して、再利用 を簡単にする。または、 大部分またはすべてのリソースを実行ファイルに配置す る。これによって、リソースへのアクセスが最適化される 説明図 図 40-6 に、このモデルの構造のサンプルを示します。 図 40-6: 動的ライブラリを含む実行モデル このモデルは、アプリケーションの編成、配布、および管理に おいて柔軟に作業を行えるため、多くの大規模なプロジェクトに適し ています。 用途 アプリケーション テクニック 843 アプリケーションの実行版の作成 たとえば、このモデルを使用すると、1 つの動的ライブラリで、アプ リケーションの特定部分に修正を加えることができます。ただし、ラ イブラリに修正を加えた場合は、必ずアプリケーション全体を再構築 し、すべての動的ライブラリを顧客に配布する必要があります。 実行ファイル、動的ラ イブラリ、および外部 リソース このモデルは、実行ファイルと動的ライブラリにすべてのリソースを 含めるかわりに、特定のリソースについて個別のファイルを配布する という点以外は、直前のモデルと同じです。 説明図 図 40-7 に、このモデルの構造のサンプルを示します。 図 40-7: 動的ライブラリと外部リソースを含む実行モデル このモデルは、大規模なアプリケーションに適しており、特に、 特定のリソースを処理するための柔軟性が必要なアプリケーションの 場合に適しています。柔軟性が求められるのは、以下のようなリソー スです。 用途 844 • 修正する可能性がある • ほかのアプリケーションと共有しなければならない • 大規模で、使用頻度が低い PowerBuilder 第 40 章 配布用アプリケーションのパッケージ化 パッケージ化モデルの実装 アプリケーションについて適切なパッケージ化モデルを決定したら、 PowerBuilder に付属のパッケージ化機能を利用して、パッケージ化モ デルを実装できます。この作業のほとんどは、プロジェクト ペインタ で行います。プロジェクト ペインタを使用すれば、実行アプリケー ションと同様に、コンポーネント、プロキシ ライブラリ、HTML ファ イルが作成できます。 実行アプリケーション 用にプロジェクト ペ インタを使用する 実行アプリケーション用のプロジェクト ペインタは、以下の操作を可 能にすることによって、パッケージ化ジョブのすべての局面を編成し ます。 • 作成する実行ファイルを指定します。 • 作成する動的ライブラリ(DLL ファイルまたは PBD ファイル)を 指定します。 • 実行ファイルまたは特定の動的ライブラリに含めるリソースを指 定します。リソースの取得場所を示す適切な PBR ファイルを利用 します。 • 生成するコンパイラ形式として、マシン コードまたは Pcode を選 択します。 マシン コードでは、最適化、トレース情報、およびエラー コンテ キスト情報などの、さまざまなコード生成オプションも指定でき ます。 • 構築オプションを選択します。実行アプリケーションの生成時に、 プロジェクト ペインタを使用してアプリケーションのオブジェク トのフル構築を行うか、インクリメンタル構築を行うかどうかの 指定も含まれます。 • パッケージ全体を再構築するときにいつでも利用できるプロジェ クト オブジェクトとして、上記の仕様を保存します。 プロジェクト ペインタの使い方の詳細については、PowerBuilder の 『ユーザーズ ガイド』マニュアルを参照してください。 個別の動的ライブラリ の構築 既存のアプリケーションに修正を加えても、そのすべての動的ライブ ラリが影響を受けるわけではありせん。システム ツリーまたはライブ ラリ ペインタのポップアップ メニューから、個別の動的ライブラリを 再構築できます。 アプリケーション テクニック 845 アプリケーションの実行版の作成 変更が限定的で、ほかの PBL の継承オブジェクトに影響しない場合 は、更新またはバグ修正用に個別の PBD をユーザに配布できます。し かし、アプリケーションを修正するたびにフル再構築して、実行ファ イルとアプリケーションのすべての動的ライブラリを配布することを お勧めします。 実行アプリケーションのテスト アプリケーションの実行版を作成したら、配布する前に、その動作を テストしてください。PowerBuilder の開発環境においては、すでにア プリケーションを何度も実行しているかもしれませんが、エンド ユー ザの立場になって独立したアプリケーションの実行版を実行すること は、非常に重要なことです。 アプリケーションを実行する手順は次のとおりです。 1 PowerBuilder を終了して、オペレーティング システム環境に戻り ます。 2 アプリケーションが PowerBuilder ランタイム ライブラリにアクセ スできるようにしておいてください。 そのためには、PowerBuilder 仮想マシンおよびそのほかのランタイ ム ファイルの位置が PATH 環境変数に設定されていること、また は、アプリケーションのレジストリ エントリを作成して、パスを 指定できることを確認します。 3 アプリケーションの実 行をトレースする 846 任意のネイティブ アプリケーションの場合と同じように、アプリ ケーションの実行ファイルを実行します。 問題を見つけやすくするため、PowerBuilder では、トレースとプロファ イルの機能を提供しています。これらの機能は開発環境で利用でき、 アプリケーションの実行版を実行するときにも利用できます。アプリ ケーションの実行ファイルに問題がなくても、この機能を利用して、 アプリケーションの動作に関する監査証跡を生成することをお勧めし ます。実行のトレースの詳細については、PowerBuilder の『ユーザー ズ ガイド』マニュアルを参照してください。 PowerBuilder 第 40 章 配布用アプリケーションのパッケージ化 エンド ユーザへのアプリケーションの配布 アプリケーションの実行版をユーザに配布する場合には、各種のファ イルとプログラムをすべてコンピュータやネットワーク上の適切な位 置にインストールする必要があります。 配布プロセスを自動化 する 配布プロセスを自動化する場合、InstallShield などのソフトウェア配布 アプリケーションを利用することもできます。通常、そのようなアプ リケーションでは、ユーザがアプリケーションを実行するときに必要 となる実行ファイル、リソース ファイル、データ ソース、およびコン フィグレーション ファイルがすべてインストールされます。また、 ユーザの初期設定(INI)ファイルとレジストリも更新されます。 インストール チェックリスト 以下のチェックリストを使用すると、必要なものをすべてインストー ルしたかどうか確認できます。読みやすくするために、チェックリス トは以下の項目に分類されています。 環境要素をインストー ルする • 環境要素をインストールする • アプリケーション要素をインストールする チェックリスト項目 PowerBuilder のランタイ ム DLL のインストール 詳細 PowerBuilder の実行システムを含む、すべての DLL ファイルを、各ユーザのコンピュータにイ ンストールする。DLL ファイルは、PowerBuilder アプリケーションを、開発環境の外で、独立し て実行するために必要になる。これは、Pcode で 生成されたアプリケーションだけでなく、マシ ン コードで生成されたアプリケーションにも該 当する ランタイム DLL のインストールについての詳細 は、866 ページの「PowerBuilder ランタイム ファ イル」を参照 管理リリースの処理。 開発環境で PowerBuilder の管理リリースを使っている場合は、その管理 リリースのランタイム DLL をユーザに提供して おく必要がある アプリケーション テクニック 847 エンド ユーザへのアプリケーションの配布 チェックリスト項目 データベース インタ フェースのインストール インストールする ODBC ドライバの設定 必要に応じたネットワー ク アクセスの設定 オペレーティング システ ムまたはウィンドウ シス テムの設定 848 詳細 各ユーザのコンピュータには、ODBC インタ フェースおよびその他のネイティブなデータ ベース インタフェースなど、アプリケーション が必要とするデータベース インタフェースをイ ンストールする データベース インタフェースのインストールに ついての詳細は、第 41 章「アプリケーションと コンポーネントの配布」を参照。データベース インタフェースについての詳細は、 『データベー スとの接続』マニュアルを参照 ODBC インタフェースおよび 1 つまたは複数の ODBC ドライバをユーザのコンピュータにイン ストールする場合、ODBC ドライバも設定しな ければならない。ドライバの設定作業には、各 ドライバを介してアクセスされる特定のデータ ソースの定義も含まれる ODBC ドライバの設定についての詳細は、 『デー タベースとの接続』マニュアルを参照 アプリケーションがサーバのデータベースまた はその他のネットワーク サービスにアクセスす る必要がある場合は、各ユーザのコンピュータ を正しく接続しておく必要がある 特定のアプリケーションでは、処理効率上また はその他の理由により、オペレーティング シス テムまたはウィンドウ システムの側で特別な調 整が必要になる場合がある。そのようなアプリ ケーションに該当する場合は、各ユーザのコン ピュータを調整しておく必要がある PowerBuilder 第 40 章 アプリケーション要素 をインストールする 配布用アプリケーションのパッケージ化 チェックリスト項目 詳細 実行アプリケーションの 実行アプリケーションを構成するファイルのコ コピー ピーを作成し、それを各ユーザのコンピュータ にインストールする。インストールするファイ ルには、以下のものがある • 実行(EXE)ファイル • 動的ライブラリ(DLL ファイルまたは PBD ファイル) • 個別に配布するリソース ファイル(ICO、 BMP、GIF、JPEG、RLE、WMF、または CUR など) 管理リリースの処理。 これらのファイルを定 期的に修正する計画がある場合は、それらの最 新バージョンをネットワーク上のサーバからコ ピーして、ユーザのコンピュータにコピーする プロセスを自動化することもできる 追加ファイルのコピー このロジックをアプリケーション内で直接構築 することも考えられる。また、PowerBuilder のラ ンタイム DLL の更新ファイルをユーザのコン ピュータにコピーすることも考えられる アプリケーションが使用する追加ファイルのコ ピーを作成し、各ユーザのコンピュータにイン ストールする。インストールするファイルには、 以下のものがある • 初期設定(INI)ファイル • ヘルプ(HLP)ファイル • ほかに、テキスト ファイルやサウンド ファイ ルなど、さまざまなファイルが考えられる ファイルの使用法によっては、特定のファイル をローカルではなく、サーバにインストールす る場合もある ア ク セ ス す る ロ ー カ ル アプリケーションがローカル データベースにア データベースのコピー クセスする必要がある場合は、そのデータベー スを構成するファイルをコピーし、各ユーザの コンピュータにインストールする その場合は、適切なデータベース インタフェー スもインストールし、正しく設定しておく必要 がある アプリケーション テクニック 849 エンド ユーザへのアプリケーションの配布 チェックリスト項目 アクセスするほかのプロ グラムのインストール アプリケーションに必要 なファイルを検索できる ようにする 詳細 アプリケーションが任意の外部プログラムにア クセスする必要がある場合、各外部プログラム を、すべてのユーザのコンピュータかサーバに インストールする また、プログラムを正常に動作させるために必 要な設定も行う。たとえば、ActiveX コントロー ルの登録が必要な場合もある。詳細については、 858 ページの「ActiveX コントロールの配布」を 参照 アプリケーションが使用するさまざまなファイ ルは、アプリケーションが検索できるパス上に インストールしておく必要がある • アプリケーションが特定のパスによってファ イルを参照する場合は、そのパス上にファイ ルをインストールする アプリケーションの値に よる、システム レジスト リの更新 アプリケーションのアイ コンの設定 • アプリケーションが名前のみによってファイ ルを参照する場合は、現行のパスなど、アプ リケーションが検索できるパスにファイルを インストールする Windows レジストリを利用して、アプリケー ション パスなどアプリケーションで必要な情報 を管理する場合は、アプリケーションの値でレ ジストリを更新する ユーザがアプリケーションを起動できるよう に、各ユーザのコンピュータのウィンドウ シス テムを使って、実行ファイルのアイコンを希望 の場所に表示する 代替方法として、ユーザはウィンドウ システム 下で、ネイティブ アプリケーションと同じその ほかの方法で、アプリケーションを起動するこ ともできる 850 PowerBuilder 第 40 章 配布用アプリケーションのパッケージ化 配布済みアプリケーションの起動 ユーザは、配布されたアプリケーションを、ほかの Windows アプリ ケーションと同じ方法で実行できます。たとえば、エクスプローラで 表示される実行ファイルをダブルクリックしたり、アプリケーション のショートカットをデスクトップに作成して、そのショートカット ア イコンをダブルクリックしたりできます。 ユーザがショートカットを作成する場合は、 [ショートカット]プロパ ティ ページの[リンク先]テキスト ボックスで実行ファイルへのパス が指定され、 [作業フォルダ]テキスト ボックスで Powersoft ランタイ ム DLL の場所が指定されている必要があります。 アプリケーション テクニック 851 エンド ユーザへのアプリケーションの配布 852 PowerBuilder 第 4 1 章 アプリケーションとコンポーネント の配布 この章について この章では、ユーザのコンピュータやサーバにアプリケーション とコンポーネントを配布する際に必要な情報について説明しま す。PowerBuilder ランタイム ファイルのパッケージ化に使用する ツールについて説明し、さまざまなターゲットに対して配布が必 要なファイルをリスト表示します。 これらのファイル リストは、新しいデータベース インタフェース が使用可能になったときなど、場合によっては更新する必要があ ります。これらの変更についての詳細は、PowerBuilder の使用し ているバージョンの『リリース ノート』マニュアルを参照してく ださい。 JSP ターゲットの配布についての詳細は、『JSP ターゲットでの作 業』マニュアルを参照してください。 内容 アプリケーション テクニック 項目 ページ アプリケーション、コンポーネント、およびサポート ファイルの配布 PowerBuilder ランタイム パッケージャ サードパーティ製コンポーネントと配布 PowerBuilder ランタイム ファイル データベース接続 Java サポート PowerBuilder エクステンション PDF と XSL-FO のエクスポート データウィンドウ Web コントロール ActiveX プラグインと PowerBuilder ウィンドウ ActiveX コント ロール EAServer 上の PowerBuilder コンポーネント PowerBuilder COM サーバ PowerBuilder オートメーション サーバ EAServer 上の Web データウィンドウ COM+ または IIS 上の Web データウィンドウ 854 859 863 866 869 879 881 882 886 887 888 891 892 893 895 853 アプリケーション、コンポーネント、およびサポート ファイルの配布 アプリケーション、コンポーネント、およびサポート ファイルの配布 配布するアプリケーションの種類に関わらず、動的ライブラリ、BMP ファイルや ICO ファイルのようなリソース、オンライン ヘルプ ファ イル、初期設定ファイルなどの任意のサポート ファイルも一緒に配布 しておく必要があります。アプリケーションの種類によって、必要な サポート ファイルのセットが違います。pbvm110.dll と pbdwe110.dll な どの PowerBuilder ランタイム ファイル、pbsnc110.dll と pbo10110.dll な どの PowerBuilder データベース インタフェースは、アプリケーション を使用して自由に配布できます。ライセンス費用もかかりません。 配布の計画 第 40 章「配布用アプリケーションのパッケージ化」には、動的ライブ ラリ、Pcode(中間コード)またはマシン コード、リソース ファイル の使い方など、PowerBuilder 実行アプリケーションを配布する際の決 定に役立つ情報が含まれています。また、必要な要素がすべてインス トールされているか確認するためのチェックリストも用意されていま す。 Web アプリケーションまたはトランザクション サーバのコンポーネ ントを配布する場合には、上記章の中の PowerBuilder 動的ライブラリ (PBD)および PowerBuilder リソース ファイル(PBR)についての情報 を参照してください。また、このマニュアルまたは表 41-1 に記載され ているマニュアルの、アプリケーション、コンポーネント、またはプ ラグインの特定の種類に関する記述も参考にしてください。 854 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 表 41-1: 追加配布されるマニュアル アプリケーションの種類 EAServer コンポーネント 参照先 564 ペ ー ジ の「EAServer へ の コ ン ポーネントの配布」 アプリケーション サーバ コン ポーネント PowerBuilder Application Server Plug-in の マニュアル セットの『User’s Guide』マ ニュアル COM コンポーネント 642 ペ ー ジ の「PowerBuilder COM サーバの配布」 第 32 章「データウィンドウ プラグ インの使い方」 第 33 章「PowerBuilder ウィンドウ プラグインの使い方」 第 34 章「PowerBuilder ウィンドウ ActiveX の使い方」 データウィンドウ プラグイン ア プリケーション PowerBuilder ウィンドウ プラグ イン PowerBuilder ウィンドウ ActiveX .NET ア プ リケーションとコン 『アプリケーションとコンポーネントの ポーネント .NET への配布』マニュアル Web データウィンドウおよび 『データウィンドウ プログラマーズ ガイ データウィンドウ Web コント ド』マニュアル ロール ActiveX この章での情報の見つ け方 この章は、インストール環境を作成するサードパーティのソフトウェ ア パッケージによるインストール プログラムのプログラミングを支 援する目的で作成されています。ここでは、各コンピュータに必要な ファイル、そのファイルの保存場所、インストール先、作成しなけれ ばならないレジストリ設定を説明します。また、PowerBuilder Enterprise には、アプリケーションに必要なファイルのパッケージ化に役立つツー ルが用意されています。このツールについての詳細は、859 ページの 「PowerBuilder ランタイム パッケージャ」を参照してください。 アプリケーションと一緒に配布する必要のあるファイルの情報につい ては、表 41-2 を参考にしてください。 アプリケーション テクニック 855 アプリケーション、コンポーネント、およびサポート ファイルの配布 表 41-2: 配布に必要な PowerBuilder ファイル シナリオ すべての PowerBuilder クライ アント アプリケーション データベース サーバ上のデー タにアクセスする PowerBuilder クライアント ア プリケーション EJB、SOAP Web サービス、お よび XML サービス用 PowerBuilder クライアント PDF または XSL-FO 形式で データを保存する PowerBuilder クライアント データウィンドウ Web コント ロール ActiveX を使用する Web アプリケーション PowerBuilder プラグインまた はウィンドウ ActiveX を使用 する Web アプリケーション PowerBuilder 内に作成される EAServer コンポーネント PowerBuilder 内に作成される COM コンポーネント EAServer と Web データウィン ドウを使用する Web アプリ ケーション ASP および COM+ または IIS と、Web データウィンドウを 使用する Web アプリケーショ ン インストール先パスと 配布先パス 参照節 866 ページの「PowerBuilder ランタイ ム ファイル」 869 ページの「データベース接続」 881 ページの「PowerBuilder エクステ ンション」 882 ページの「PDF と XSL-FO のエク スポート」 886 ページの「データウィンドウ Web コントロール ActiveX」 887 ページの「プラグインと PowerBuilder ウィンドウ ActiveX コン トロール」 888 ページの「EAServer 上の PowerBuilder コンポーネント」 891 ページの「PowerBuilder COM サー バ」 893 ページの「トランザクション サー バに必要なファイル」 894 ページの「動的ページ サーバに必 要なファイル」 895 ページの「COM+ または IIS サー バで必要なファイル」 この章で、いくつかの表の後に記載されているインストール先パスは、 デフォルトのインストール先を選択して PowerBuilder をインストール したときに、ファイルがインストールされる場所を示しています。ア プリケーションのインストール プログラムを作成する場合は、この場 所から目的とする場所にファイルをコピーできます。 配布先パスは、作成したアプリケーションまたはコンポーネントをイ ンストールする際に、コンピュータ上でこれらのファイルをインス トールすることができる場所を示しています。 856 PowerBuilder 第 41 章 App Path レジストリ キー アプリケーションとコンポーネントの配布 表によっては、レジストリ エントリのリストが後ろに記載されていま す。このレジストリ エントリは、アプリケーションまたはコンポーネ ントが必要なファイルを見つけられるように、インストール プログラ ムを使用して作成する必要があります。Windows 上で実行されるとき、 アプリケーションは、以下の場所で以下の順序に従ってサポート ファ イルを探します。 1 実行ファイルがインストールされているディレクトリ 2 Windows システムおよび Windows ディレクトリ(たとえば、 C:\WINDOWS\system32、C:\WINDOWS\system、および C:\WINDOWS) 3 レジストリに指定されているアプリケーション パス 4 システム パス アプリケーション パスは必ずしも指定する必要はありませんが、指定 することをお勧めします。 アプリケーション パ スの指定 アプリケーションがサポート ファイルを見つけるためのパスを指定 するには、インストール プログラムで、次のレジストリ位置にアプリ ケーションのための App Path キーを作成する必要があります。 HKEY_LOCAL_MACHINE\Software\Microsoft\Windows\ CurrentVersion\App Paths アプリケーションがインストールされるディレクトリの(デフォルト) 文字列値にデータ値を設定し、共有ファイルの保存場所を指定する Path という新しい文字列値を作成します。以下の例は、SQL Anywhere を使用する myapp.exe というアプリケーションの一般的なレジストリ エントリを示します。レジストリ キーは大カッコで囲まれ、後ろに " 名前 "=" 値 " の形式でキーの文字列値が記述されています。 [HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\ CurrentVersion\App Paths\myapp.exe] "Default"="C:\Program Files\myapps\myapp.exe" "Path"="C:\Program Files\myapps;C:\Program Files\ sybase\shared\PowerBuilder;c:\program files\ SQL Anywhere 10\win32\;" アプリケーション テクニック 857 アプリケーション、コンポーネント、およびサポート ファイルの配布 REG ファイルについて .REG 拡張子を持つレジストリ更新ファイルを使用すると、情報をレジ ストリにインポートできます。この章のレジストリ キーの例で使用し ている形式は、レジストリ更新ファイルの形式とよく似ていますが、 これらの例は更新ファイルとしての使用を意図したものではありませ ん。レジストリ更新ファイルのデータ値文字列のパス名には、一般に、 円記号が 1 つではなく 2 つ組み合わされて使用され、 「デフォルト」の 文字列値はアット マーク(@)で表されます。 例を参考にして、インストール プログラムで追加または更新するレジ ストリ キーを決定してください。 ActiveX コントロール の配布 アプリケーションが ActiveX コントロール、OLE コントロール、また は OCX コントロールを使用する場合には、以下の作業が必要です。 • アプリケーションと一緒にコントロール ファイルを配布する • 各コントロールを登録しておく • 必要なファイルをターゲット コンピュータのシステム ディレクトリ に配置しておく 自己登録を行わないコントロールを使用するアプリケーションの場合 は、セットアップ プログラムによって各ユーザのコンピュータに手動 で登録する必要があります。自己登録を行うコントロールかどうかを 調べるには、コントロールに付属のマニュアルを参照してください。 開発プラットフォーム、配布プラットフォーム、および配布するコン トロールの種類によっては、配布先となるコンピュータの WINDOWS システム ディレクトリに、追加の DLL ファイルまたはライセンス ファイルをコピーする必要がある場合もあります。 858 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 PowerBuilder ランタイム パッケージャ PowerBuilder ランタイム パッケージャは、アプリケーションが実行時 に必要 な PowerBuilder フ ァイル を Microsoft Windows イン ストー ラ (MSI)パッケージ ファイルにパッケージ化するツールです。Windows インストーラは、最新の Microsoft Windows オペレーティング システ ムとともにインストールされる、インストールおよび環境設定サービ スです。 ランタイム パッケージャがインストール パッケージの一部として生 成した MSI ファイルを使用できます。このパッケージには、アプリ ケーションで必要な他のファイルも含まれています。 ランタイム パッケージャを正常に実行するには、システム上に Microsoft Windows インストーラが必要です。インストーラは、Windows XP と Windows 2003 で使用できます。 最新版 Windows インストーラの詳細および入手方法については、 Microsoft ドキュメンテーション のサイト http://msdn.microsoft.com を参照し てください。 ランタイム パッケージャは、Windows システムにインストールされた クライアント アプリケーションおよび .NET Framework に配布された アプリケーションで使用できます。ランタイム パッケージャは、アプ リケーションがデータウィンドウ Web コントロール ActiveX またはプ ラグインを使用する場合に必要なファイルをパッケージ化しません。 また、ほとんどのサードパーティ コンポーネントをインストールする こともありません。詳細については、863 ページの「サードパーティ 製コンポーネントと配布」を参照してください。 また、856 ページの表 41-2 内の該当する箇所を参照して、インストー ルが必要なファイルであるが、ランタイム パッケージャによってはイ ンストールされないファイルを確認してください。 アプリケーション テクニック 859 PowerBuilder ランタイム パッケージャ ❖ PowerBuilder ランタイム パッケージャを使用するには 1 Windows の[スタート]メニューから[プログラム| Sybase | PowerBuilder 11.0 | PowerBuilder ランタイム パッケージャ]を選 択するか、Shared\PowerBuilder ディレクトリの pbpack110 実行ファ イルを起動します。 2 生成された MSI ファイルの保存場所を選択します。 3 .NET ターゲットを配布する場合は、[PowerBuilder .NET コンポー ネント]を選択します。それ以外の場合は、[PowerBuilder 標準コ ンポーネント]を選択します。 4 アプリケーションに必要なデータベース インタフェースを選択し ます。 選択したデータベースの DLL がパッケージに追加されます。ODBC および OLE DB の場合、pbodb110.ini ファイルも追加されます。 JDBC の場合、pbjdbc12110.jar と pbjvm110.dll ファイルも追加され ます。Java Runtime Environment(JRE)は追加されません。詳細に ついては、863 ページの「サードパーティ製コンポーネントと配 布」を参照してください。 そのほかの ODBC または OLE DB ファイルをアプリケーションが 必要とする場合がありますが、これらのファイルは追加されませ ん。これらのファイルの配布方法についての詳細は、871 ページの 「ODBC データベース ドライバとサポート ファイル」および 876 ページの「OLE DB データベース プロバイダ」を参照してくださ い。 860 PowerBuilder 第 41 章 5 アプリケーションとコンポーネントの配布 アプリケーションがデータウィンドウ XML のエクスポートまた はインポート、あるいは XML Web データウィンドウを使用する場 合、[XML サポート]チェックボックスをオンにします。 ランタイム パッケージャは、PBXerces110.dll、xerces-c_2_6.dll、お よび xerces-depdom_2_6.dll を追加します。 6 アプリケーションが、PowerBuilder Document Object Model が提供 する XML サービスを使用する場合、またはアプリケーションが EJB または SOAP Web サービス クライアントである場合は、それ に該当するチェックボックスをオンにします。 ランタイム パッケージャは、必要な DLL、PBX、および JAR ファ イルをパッケージに追加します。ランタイム パッケージャは、 [SOAP クライアント(Web サービス)]チェックボックスが選択さ れると、必要なファイルを EasySoap と .NET Web サービス エンジ ンの両方に追加します。これらのサービスに必要なファイル情報 については、881 ページの「PowerBuilder エクステンション」を参 照してください。 Web サービス データウィンドウ アプリケーションで Web サービス データウィンドウを使用する 場合は、[SOAP クライアント(Web サービス)]ボックスもオン にします。このボックスをオンにすると、 Sybase.PowerBuilder.WebService.Runtime.dll と Sybase.PowerBuilder.WebService.Runtime.RemoteLoader.dll の 2 つの ファイルが追加されます。これらファイルも、Web サービス デー タウィンドウで必要なファイルです。 7 アプリケーションでリッチテキスト コントロールやデータウィン ドウを使用する場合は、[リッチ テキスト サポート]チェック ボックスをオンにします。 ランタイム パッケージャは、868 ページの表 41-5 にリストされて いるリッチテキスト サポート用のファイルをインストールしま す。 8 [生成]をクリックします。 ランタイム パッケージャは、選択したコンポーネントに必要な ファイルと、PowerBuilder の標準アプリケーション用のランタイム DLL、または、表 41-3 に示した、PowerBuilder の .NET アプリケー ション用のランタイム DLL および .NET アセンブリを格納した MSI ファイルを作成します。 アプリケーション テクニック 861 PowerBuilder ランタイム パッケージャ 表 41-3: 基本コンポーネント 選択した基本コンポーネント PowerBuilder 標準コンポーネ ント PowerBuilder .NET コンポーネ ント ファイル libjcc.dll libjutils.dll pbacc110.dll pbcomrt110.dll pbdbl110.dll pbdwe110.dll pbdwr110.dll pbdwr110.pbd pbjag110.dll pbjvm110.dll pbshr110.dll pbtra110.dll pbtrs110.dll pbvm110.dll pbdbl110.dll pbshr110.dll pbrth110.dll pbdwm110.dll PowerBuilder .NET アセンブリ : Sybase.PowerBuilder.ADO.dll Sybase.PowerBuilder.Common.dll Sybase.PowerBuilder.Core.dll Sybase.PowerBuilder.Datawindow.Web.dll Sybase.PowerBuilder.DataWindow.Win.dll Sybase.PowerBuilder.Datawindow.Interop.dl l Sybase.PowerBuilder.Db.dll Sybase.PowerBuilder.DBExt.dll Sybase.PowerBuilder.EditMask.Win.dll Sybase.PowerBuilder.EditMask.Interop.dll Sybase.PowerBuilder.Graph.Web.dll Sybase.PowerBuilder.Graph.Win.dll Sybase.PowerBuilder.Graph.Core.dll Sybase.PowerBuilder.Graph.Interop.dll Sybase.PowerBuilder.RTC.Win.dll Sybase.PowerBuilder.RTC.Interop.dll Sybase.PowerBuilder.Interop.dll Sybase.PowerBuilder.Web.dll Sybase.PowerBuilder.Win.dll MSI ファイルは、あらゆる Windows プラットフォーム上で直接実行可 能な圧縮ファイルです。MSI ファイルは、自己登録 DLL を登録し、 Windows レジストリにインストール先のパスを追加し、システムの 862 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 PATH 環境変数を設定し、さらに、Windows のコントロール パネルの [アプリケーションの追加と削除]ページに情報を追加します。また、 サードパーティのインストール ソフトウェア パッケージの中には MSI ファイルを使用できるものもあります。 .NET アプリケーションでは、MSI ファイルは .NET アセンブリをグ ローバル アセンブリ キャッシュ(GAC: Global Assembly Cache)内に インストールします。.NET Framework 2.0 を対象コンピュータにイン ストールする必要があります。インストールしていない場合はインス トール処理が停止しエラー メッセージが表示されます。.NET Web フォーム ターゲットで必要な IE Web Controls がインストールされてい ない場合は、警告メッセージが表示されますが、インストール処理は 続行されます。.NET Web フォーム アプリケーションや Web サービス 用の本稼動サーバ、または .NET Windows フォームやスマート クライ アント アプリケーション用のクライアント コンピュータで MSI ファ イルを実行したあとは、対象システムを再起動する必要があります。 .NET ターゲットの配布の詳細については、『アプリケーショとコン ポーネントの .NET への配布』マニュアルの最初の章を参照してくだ さい。 サードパーティ製コンポーネントと配布 PowerBuilder アプリケーションは、PowerBuilder とともにインストール されるサードパーティ製のコンポーネントへの依存性を持つ場合があ ります。依存性を持つコンポーネントの多くは、PowerBuilder ランタ イム パッケージャではインストールされません。これらのコンポーネ ントの一部は、アプリケーションと一緒に再配布できる場合もありま すが、別途ベンダーから入手する必要がある場合もあります。 無償でダウンロードが可能なコンポーネントの詳細については、無償 ダウンロード規約に関するドキュメントを参照してください。このド キュメントは、DVD の Support ディレクトリに収録されています。ま た、Sybase Web のサイト http://www.sybase.com/softwarelicenses/third_party_legal でも参照できます。 アプリケーション テクニック 863 サードパーティ製コンポーネントと配布 Apache ファイル PowerBuilder に含まれる Apache ファイルをユーザに再配布できます。 PowerBuilder 11 に含まれる Apache コードを使用したり再配布したり する場合は、Apache ライセンスに従う必要があります。このライセン スについては、PowerBuilder 11 の無償ダウンロード規約に関するド キュメントを参照してください。 ファイルを PDF として保存するためにアプリケーションで XSL-FO を 使用するには、Apache Formatting Objects Processor(FOP)のバージョ ン 0.20.4 が必要です。FOP についての詳細は、Apache FOP Web のサイ ト http://xmlgraphics.apache.org/fop/ を参照してください。 XML Web データウィンドウのサポート、また、データウィンドウと データストアの XML サポート、PBDOM、Web サービスの SOAP クラ イアントには、Apache Xerces ファイルである xerces-c_2_6.dll および xerces-depdom_2_6.dll が必要です。Xerces についての詳細は、Xerces C++ Parser Web のサイト http://xml.apache.org/xerces-c/ を参照して ください。 Microsoft ファイル PowerBuilder のコア ランタイム ファイルを配布する場合は、ユーザの コンピュータまたはサーバに、Microsoft Visual C++ ランタイム ライブ ラ リ msvcr71.dll お よ び msvcp71.dll、お よ び Microsoft .NET Active Template Library(ATL)モジュール atl71.dll が存在していることを確認 します。PowerBuilder ランタイム ファイルは、これらのファイルに実 行時依存するため、PowerBuilder ランタイムを必要とするすべてのア プリケーションおよびコンポーネントで必要です。これらのファイル の 入 手 方 法 と 使 用 方 法 に つ い て の 詳 細 は、Microsoft Web のサ イト http://www.microsoft.com を参照してください。 PowerBuilder ランタイム ファイルは、Microsoft Windows GDI+(gdiplus.dll) にも実行時依存します。システムで gdiplus.dll を使用できない場合は、 PowerBuilder .NET ターゲットは起動できません。GDI+ は、Windows XP または Windows Server 2003 オペレーティング システムのサブシステ ムであり、画面やプリンタでの高度な画像処理を行います。GDI+ は Windows Vista にも組み込まれていますが、Windows 2000 では使用でき ないため、PowerBuilder アプリケーションを Windows 2000 に配布する 場合は、gdiplus.dll が対象のコンピュータのシステム パスで使用でき ることを確認する必要があります。GDI+ は、Microsoft Web のサイト http://www.microsoft.com/downloads/details.aspx?FamilyID=6A63AB9C-DF124D41-933C-BE590FEAA05A&displaylang=en からダウンロードできます。 864 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 MSI ファイルの実行前にインストールするファイル PowerBuilder ランタイム パッケージャで生成した MSI ファイルにより インストールされる一部のファイルは、これらのファイルに依存して います。たとえば、atl71.dll および gdiplus.dll は、pbjvm110.dll を登録 する前にユーザのコンピュータにインストールしておく必要がありま す。PowerBuilder ランタイム パッケージャで生成した MSI ファイルを 実行する前に、これらのファイルが対象のコンピュータにあることを 確認してください。 アプリケーションで InkEdit および InkPicture コントロールを使用する 場合は、Microsoft.Ink、Microsoft.Ink.dll、および Microsoft.Resources.dll が必要です。これらのファイルは Microsoft Windows XP Tablet PC Edition の Software Development Kit 1.7 の一部です。この SDK は、 Microsoft Web のサイト http://www.microsoft.com/downloads/details.aspx?FamilyId=B46D4B83-A82140BC-AA85-C9EE3D6E9699&displaylang=en からダウンロードできます。 これらの DLL と .NET Framework 2.0 との間には、互換性の問題がある ことが Microsoft で確認されています。この問題に対処するための更 新プログラムは、Microsoft Web のサイト http://www.microsoft.com/downloads/details.aspx?familyid=84BBEFA4-704741DF-8583-E3BDBF9D805F&displaylang=ja からダウンロードできます。 PowerBuilder .NET Web フォームは、タブ、ツリービュー、ツールバー コントロールを正常に表示して機能させるために Internet Explorer Web コントロールを使用します。この IE Web Controls は、Microsoft Web の サイ ト http://www.asp.net/downloads/archived/ie-web-controls/ か ら ダ ウ ン ロードできます。コントロールのインストールについての詳細は、 『ア プリケーショとコンポーネントの .NET への配布』マニュアルを参照 してください。 Sun Microsystems ファイル JSP ターゲット、EJB クライアント、JDBC 接続、および XSL-FO を使 用した PDF の保存には、Java Runtime Environment(JRE)が必要です。 JRE のサードパーティ条項については、無償ダウンロード規約に関す るドキュメントを参照してください。JRE は、Sun Developer Network の サイト http://java.sun.com/javase/downloads/index.jsp からダウンロードでき ます。 アプリケーション テクニック 865 PowerBuilder ランタイム ファイル Web サービスの SOAP クライアントで使用するソフトウェア PowerBuilder では、EasySoap110.dll 内に実行可能形式の EasySoap++ ラ イブラリが含まれており、PBSoapClient110.pbx に動的にリンクされて い ます。EasySoap++ ライ ブラリと その使 用は、GNU Lesser General Public License(LGPL)の適用範囲です。このライセンスについては、 無償ダウンロード規約に関するドキュメントを参照してください。 また、EasySoap++ ライブラリは、LGPL の規定に従ってサードパーティ に配布することができます。配布の前には、LGPL を確認してくださ い。 EasySoap++ ライブラリのコンピュータが読取可能なソース コードは、 DVD の Support\WSExtn フォルダ内の EasySoap.zip ファイルにありま す。さらに、PBSoapClient110.pbx のオブジェクト コードと Microsoft Visual C++ プロジェクト ファイル は、同じディレクトリの soapclient.zip ファイルにあります。 これらのファイルは LGPL の規定に基づいて提供されているものであ り、EasySoap++ ライブラリを変更したり、変更した EasySoap110.dll を生 成するために再リンクしたりすることができます。また、PBSoapClient110.pbx と変更した EasySoap++ インポート ライブラリを再リンクすることも できます。LPGL では、EasySoap++ ライブラリで変更した定義を使用 するために、PBSoapClient110.pbx の再コンパイルが必ず必要なわけで はないということがわかります。 PBSoapClient110.pbx を構築するには、soapclient.zip ファイルに含まれ る Readme.txt ファイルに従います。 PowerBuilder ランタイム ファイル データベースの接続 データベースの接続に必要なファイルについては、869 ページの「デー タベース接続」に個別に一覧表示されています。 主なランタイム ファ イル 866 表 41-4 は、PowerBuilder の主なランタイム ファイルです。 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 表 41-4: 主な PowerBuilder ランタイム ファイル 名前 pbvm110.dll pbshr110.dll libjcc.dll libjutils.dll pbdwe110.dll Microsoft ファイル 必要とする対象 すべて すべて。pbvm110.dll は、このファイルへの依存性を 持つ すべて。pbvm110.dll は、このファイルへの依存性を 持つ すべて。libjcc.dll は、このファイルへの依存性を持つ データウィンドウおよびデータストア(.NET アプリ ケーションの場合は、かわりに pbdwm110.dll を使用) 基本的な PowerBuilder ランタイム ファイルを配布する際に、ユーザの マシンに msvcr71.dll と msvcp71.dll Microsoft Visual C++ ランタイム ラ イブラリおよび Microsoft .NET Active Template Library(ATL)モジュー ル atl71.dll が存在しない場合は、これらのファイルも配布する必要が あります。PowerBuilder ランタイム ファイルは、実行時はこれらのファ イルに依存します。詳細については、863 ページの「サードパーティ 製コンポーネントと配布」を参照してください。 Microsoft Windows GDI+ は、スクリーンおよびプリンタ用の拡張グラ フィック機能を実装する Windows XP オペレーティング システムや Windows Server 2003 オペレーティング システムのサブシステムです。 PowerBuilder ランタイム ファイルは、実行時は gdiplus.dll に依存しま す。Windows 2000 プラットフォームに PowerBuilder アプリケーション を配布する場合は、対象のコンピュータで gdiplus.dll が利用できるこ とを確認する必要があります。 ほかのランタイム ファイル 表 41-5 に、アプリケーションがさらに必要とする可能性があるランタ イム ファイルを示します。たとえば、pbvm110.dll はすべての配布アプ リケーションに必要ですが、pbrtc110.dll および関連するランタイム ファイルは、リッチテキスト コントロールまたはリッチテキスト デー タウィンドウ オブジェクトを使用するアプリケーションでのみ必要 になります。 Java サポート対応の pbjvm110.dll を使用する配布アプリケーションに ついての詳細は、879 ページの「Java サポート」を参照してください。 アプリケーション テクニック 867 PowerBuilder ランタイム ファイル 表 41-5: 追加の PowerBuilder ランタイム ファイル 名前 pbacc110.dll 必要とする対象 アクセシビリティのサポート(米国リハビリ テーション法 508 条) データ パイプラインのサポート Web データウィンドウのサポート pbdpl110.dll pbdwr110.dll、 pbdwr110.pbd PBXerces110.dll、 xerces-c_2_6.dll、 xerces-depdom_2_6.dll Sybase.PowerBuilder.WebServi ce.Runtime.dll、 Sybase.PowerBuilder.WebServi ce.RuntimeRemoteLoader.dll pbjvm110.dll pbrth110.dll pbrtc110.dll、tp13.dll、 tp13_bmp.flt、tp13_css.dll、 tp13_doc.dll、tp13_gif.flt、 tp13_htm.dll、tp13_ic.dll、 tp13_ic.ini、tp13_jpg.flt、 tp13_obj.dll、tp13_pdf.dll、 tp13_png.flt、tp13_rtf.dll、 tp13_tif.flt、tp13_tls.dll、 tp13_wmf.flt、tp13_wnd.dll、 tp4ole13.ocx pblab110.ini pbtra110.dll、pbtrs110.dll XML Web データウィンドウのサポートおよ びデータウィンドウとデータストアの XML サポート Web サービス データウィンドウ Java サポート .NET Web フォームおよび ADO.NET リッチテキストのサポート データウィンドウのラベル提示様式の定義 済みフォーマット データベース接続のトレース インストール先パス \Program Files\Sybase\Shared\PowerBuilder また は、リッチ テキストに必要なファイルの多くは \Program Files\Sybase\shared\PowerBuilder\RTC アプリケーションと同じパス、システム パスのディレクト リ、または App Path レジストリ キー 配布先パス レジストリ エントリ 857 ページの「App Path レジストリ キー」を参照 してください。 868 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 データベース接続 データベースにアクセスする実行ファイルまたはコンポーネントを配 布する場合、ユーザは DBMS およびアプリケーションが使用するデー タベースにアクセスする必要があります。 データベース接続ファイルのインストール先 別のコンピュータの中間層コンポーネントを使用してデータベース トランザクションを実行するクライアント アプリケーションでは、 データベース接続ファイルを配布する必要はありません。データベー ス接続ファイルは、データベース サーバと対話するコンピュータに配 布しなければなりません。 以下の作業を行う必要があります。 • 必要であれば、DBMS ランタイム(クライアント)ファイルを、ア プリケーション ディレクトリかシステム パス上のディレクトリ にインストールする スタンドアロンの SQL Anywhere データベースを使用するアプリ ケーションの場合には、ユーザのコンピュータに SQL Anywhere ラ ンタイム エディション ファイルをインストールできます。詳細に ついては、872 ページの「SQL Anywhere ファイル」を参照してく ださい。それ以外の場合は、ベンダによって明示された指示およ びライセンス規約に従ってください。 • アプリケーションが使用するデータベースに各ユーザがアクセス できるようにしておく アプリケーションがローカル データベースを使用する場合は、 データベースとログ ファイルなどの関連ファイルをユーザのコン ピュータにインストールします。 アプリケーションがデータベース サーバを使用する場合は、ユー ザのコンピュータからアクセスできるようにセットアップしてお きます。この作業は、データベース管理者が行います。 • ユーザのコンピュータ上でアプリケーションが使用するデータ ベース インタフェースをインストールする • アプリケーションが ODBC インタフェースを使用する場合は、875 ページの「ODBC データ ソースとドライバの環境設定」の説明に 従って、ODBC データベース ドライバとデータ ソースを設定する データベース ドライバとインタフェースの詳細については、以下を参 照してください。 アプリケーション テクニック 869 データベース接続 • 次の「ネイティブ データベース ドライバ」 • 871 ページの「ODBC データベース ドライバとサポート ファイル」 • 876 ページの「OLE DB データベース プロバイダ」 • 877 ページの「ADO.NET データベース インタフェース」 • 878 ページの「JDBC データベース インタフェース」 ネイティブ データベース ドライバ 表 41-6 は、PowerBuilder で提供されるネイティブ データベース ドライ バのリストを示します。アプリケーションまたはコンポーネントが、 指定のデータベースを使用する場合、コンピュータ上にそのファイル が必要です。ネイティブ データベース ファイル名の最初の 2 つの文字 は PB であり、次の 3 つの文字でデータベースを識別し、最後の 2 つ の文字で PowerBuilder のバージョンを識別します。 表 41-6: PowerBuilder ネイティブ データベース ドライバ 名前 pbin9110.dll pbo84110.dll pbo90110.dll pbo10110.dll pbsnc110.dll pbase110.dll pbsyc110.dll pbsyj110.dll 必要とする対象 INFORMIX I-Net 9 Oracle 8.0.x と Oracle8i 8.1.x Oracle9i Oracle 10g SQL Native Client for Microsoft SQL Server Sybase Adaptive Server Enterprise CT-LIB(Adaptive Server 15 のみ) Sybase Adaptive Server Enterprise CT-LIB Sybase Adaptive Server Enterprise CT-LIB(EAServer 配布 の場合のみ) インストール先パス \Program Files\Sybase\Shared\PowerBuilder アプリケーションと同じパス、システム パスのディレクト リ、または App Path レジストリ キー 配布先パス レジストリ エントリ 857 ページの「App Path レジストリ キー」を参照 してください。 870 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 注意 PowerBuilder カスタム クラス ユーザ オブジェクトを EAServer に配布するときは、SYC ではなく SYJ データベース インタフェースを 使用して Adaptive Server Enterprise データベースに接続する必要があり ます。PowerBuilder の開発環境で SYJ を使用することはできませんが、 SYJ DB プロファイル設定 ダイアログボックスを使用して、該当する 接続パラメータを設定することができます。その後、 [プレビュー]タ ブからトランザクション オブジェクトのスクリプトに構文をコピー できます。 ODBC データベース ドライバとサポート ファイル この節では、PowerBuilder アプリケーションまたは InfoMaker アプリ ケーションからのすべての ODBC データベース接続に必要なファイル と、特定のデータベース インタフェースまたは DBMS に必要なファイ ルを一覧します。 PowerBuilder ODBC インタフェース ファ イル アプリケーションが ODBC を使用する場合は、以下の PowerBuilder ODBC インタフェース ファイルが必要です。 表 41-7: PowerBuilder ODBC インタフェース ファイル 名前 pbodb110.dll pbodb110.ini インストール先パス 説明 PowerBuilder ODBC インタフェース PowerBuilder ODBC 初期設定ファイル \Program Files\Sybase\Shared\PowerBuilder 配布先パス アプリケーションと同じパス、 システム パスのディレクト リ、または App Path レジストリ キー レジストリ エントリ 857 ページの「App Path レジストリ キー」を参照 してください。 INI ファイルと DLL ファイルは、同じディレクトリにあること が必要です。pbodb110 初期設定ファイルを修正した場合には、修正し たバージョンを配布してください。 注意 Microsoft ODBC ファ イル 表 41-8 に、アプリケーションが ODBC を使用する場合に必要な Microsoft ODBC ファイルを一覧します。 アプリケーション テクニック 871 データベース接続 表 41-8: Microsoft ODBC ファイル 名前 DS16GT.dll DS32GT.dll ODBC32.dll ODBC32GT.dll ODBCAD32.exe ODBCCP32.cpl ODBCCP32.dll ODBCCR32.dll ODBCINST.cnt ODBCINST.hlp ODBCINT.dll ODBCTRAC.dll 説明 Microsoft ODBC ドライバ マネージャ、DLL、およびヘ ルプ ファイル インストール先パス Windows システム ディレクトリ 配布先パス Windows システム ディレクトリ レジストリ エントリ なし 通常、Microsoft ODBC ドライバ マネージャ(ODBC32.dll)とサ ポート ファイルは、すでにユーザの Windows システム ディレクトリ にインストールされています。 注意 SQL Anywhere ファイ ル SQL Anywhere データベースを使用する PowerBuilder アプリケーショ ンの場合には、SQL Anywhere の ODBC データベース ドライバだけで なく、SQL Anywhere DBMS も配布する必要があります。 制約 PowerBuilder には、開発プロセスで使用する SQL Anywhere が含まれて います。ただし、この製品を特許権使用料なしでユーザに配布するこ とはできません。 データ定義言語(DDL)、トランザクション ログ、ストアド プロシー ジャ、またはトリガがアプリケーションに必要な場合は、サイベース 社におたずねください。 SQL Anywhere データベースおよびアプリケーションの配布の詳細に ついては、SQL Anywhere のマニュアルを参照してください。 872 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 アプリケーションがスタンドアロンのデータベースを使用する場合 は、ユーザのコンピュータに SQL Anywhere デスクトップ ランタイム システムを配布することができます。この場合、追加のライセンス料 金はかかりません。ランタイム システムを使うことによって、ユーザ はデータベース内のデータの取り出しや変更を行えますが、データ ベース スキーマの変更はできません。また、トランザクション ログ、 ストアド プロシージャ、およびトリガはサポートしていません。 SQL Anywhere ドライバ、ランタイム エンジン、およびサポート ファ イルの完全インストールは、DVD の Support\SA10Runtime ディレクト リから行えます。表 41-9 に、インストールされるファイルを示します。 詳細については、インストール ディレクトリの RuntimeEdition.html ファイルを参照してください。 アプリケーション テクニック 873 データベース接続 表 41-9: SQL Anywhere ファイル 名前 dbodbc10.dll dbbackup.exe dbcon10.dll dbisqlc.exe dblgen10.dll dblib10.dll dbtool10.dll dbunlspt.exe dbvalid.exe rteng10.exe dbctrs10.dll dbserv10.dll dbelevate10.exe *1 dblgja10.dll *2 dbicu10.dll *2 dbicudt10.dll *2 rteng10.lic *3 説明 SQL Anywhere ODBC ドライバ SQL Anywhere バックアップ ユーティリティ 接続 ダイアログボックス。開発者が独自のダイアログ ボックスを提供せず、エンド ユーザが独自のデータ ソースを作成する場合、データベースに接続するとき にユーザ ID とパスワードの入力が必要な場合、あるい はそのほかの目的で接続 ダイアログボックスを表示す る必要がある場合に必要 対話型 SQL ユーティリティ 言語固有の文字列ライブラリ(EN は英語版を示す) インタフェース ライブラリ SQL Anywhere データベース ツール SQL Anywhere アンロード ユーティリティ SQL Anywhere 検証ユーティリティ 制限つきのランタイム エンジン パフォーマンス ユーティリティ サーバ ユーティリティ 昇格された権限が必要な操作を実行するためのユー ティリティ 言語固有の文字列ライブラリ(JA は日本語版を示す) データベースの文字セットがマルチバイトであるか、 UCA 照合順が使用されている場合のみ必要 データベースの文字セットがマルチバイトであるか、 UCA 照合順が使用されている場合のみ必要 制限つきのランタイム エンジン ライセンス ファイル *1 Windows Vista に配布する場合必要です。 *2 日本語環境に配布する場合必要です。 *3 すべての環境で必要です。 インストール先パス \Program Files\Sybase\SQL Anywhere 10\win32 アプリケーションと同じパス、システム パスのディレクト リ、または App Path レジストリ キー 配布先パス 857 ページの「App Path レジストリ キー」および 次の「ODBC データ ソースとドライバの環境設定」を参照してくださ い。 レジストリ エントリ 874 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 サポート ファイルは、dbodbc10.dll と同じディレクトリにインス トールしなければなりません。英語版の文字列ライブラリを使用しな い場合は、使用言語固有の文字列ライブラリの該当するバージョンを 配布しておく必要があります。 注意 ODBC データ ソース とドライバの環境設定 ユーザが特定のデータ ソースに接続できるようにするには、 インストール プログラムによって、データ ソースにアクセスするコン ピュータのレジストリにある ODBC.INI キーに、そのデータ ソースの 定義を提供する必要があります。ユーザ DSN の場合は HKEY_CURRENT_USER、システム DSN の場合は HKEY_LOCAL_MACHINE になります。データ ソース定義では、デー タベース ドライバの名前と保存場所だけでなく、データベース エンジ ンの起動に必要なコマンドも指定します。ODBC Data Sources キーの データ ソースも、ODBC.INI に一覧表示する必要があります。 ODBC.INI 以下の例では、SQL Anywhere を使用する MyApp DB というデータ ソースの一般的なレジストリ エントリを示します。レジストリ キーは 大カッコで囲まれ、後ろに " 名前 "=" 値 " の形式でキーの文字列値が記 述されています。 [HKEY_CURRENT_USER\SOFTWARE\ODBC\ODBC.INI\MyApp DB] "Driver"="C:\Program Files\Sybase\SQL Anywhere 10\ win32\dbodbc10.dll" "Start"="c:\program files\sybase\SQL Anywhere 10\win32\ rteng10.exe -c9m" "UID"="dba" "PWD"="sql" "Description"="Database for my application" "DatabaseFile"="C:\Program Files\myapps\myapp.db" "AutoStop"="Yes" [HKEY_CURRENT_USER\SOFTWARE\ODBC\ODBC.INI\ ODBC Data Sources] "MyApp DB"="SQL Anywhere 10.0" ODBCINST.INI インストール プログラムは、 HKEY_LOCAL_MACHINE\SOFTWARE\ODBC の ODBCINST.INI キー に、配布するアプリケーションが使用する各ドライバについて以下の 2 種類のエントリを作成する必要があります。 • ODBCINST.INI の ODBC DRIVERS キーにドライバ名を指定した 文字列値と "Installed" を指定したデータ値を追加します。 • ODBCINST.INI キーに Driver および Setup という文字列値を使用 したドライバごとの新しいキーを追加します。 アプリケーション テクニック 875 データベース接続 ドライバによっては、ODBCINST.INI にさらに文字列値が必要な場 合があります。 ODBC データベース ドライバ ファイルがシステム パスのディレクト リ内に保存されていない場合は、その保存場所も実行ファイルの App Paths キーに追加する必要があります。 ベンダから提供された ODBC ドライバを使用している場合は、ドライ バのセットアップ プログラムを使用して、ドライバをインストールし てレジストリ エントリを作成することができます。 以下の例は、SQL Anywhere の一般的なレジストリ エントリを示しま す。レジストリ キーは大カッコで囲まれ、後ろに " 名前 "=" 値 " の形 式でキーの文字列値が記述されています。 [HKEY_LOCAL_MACHINE\SOFTWARE\ODBC\ODBCINST.INI\ SQL Anywhere 10.0] "Driver"="c:\program files\sybase\SQL Anywhere 10\ win32\dbodbc10.dll" "Setup"="c:\program files\sybase\SQL Anywhere 10\ win32\dbodbc10.dll" ODBC ドライバとデータ ソースのレジストリ エントリの内容につい ての詳細は、 『データベースとの接続』マニュアルを参照してください。 OLE DB データベース プロバイダ OLE DB を使用してデータにアクセスするアプリケーションの場合、 各ユーザのコンピュータに Microsoft の Data Access Components ソフト ウェアがインストールされていない場合はインストールしなければな りません。 PowerBuilder OLE DB インタフェースには、Microsoft Data Access Components(MDAC)バージョン 2.8 以降のソフトウェアの機能が必 要です。バージョン 2.8 は、Windows XP Service Pack 2 および Windows Server 2003 に同梱されて配布されています。 コンピュータの MDAC のバージョンを確認するには、MDAC ダウンロー ド ページ のサイト http://msdn2.microsoft.com/en-us/data/aa937730.aspx から MDAC Component Checker ユーティリティをダウンロードして実行し てください。 Windows Vista オペレーティング システムに対しては、Windows Data Access Components(DAC)バージョン 6.0 に、Vista 対応の変更がいく つか含まれていますが、それ以外の機能は MDAC 2.8 に相当します。 876 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 MDAC とともにインストールされる OLE DB データ プロバイダ SQL Server(SQLOLEDB)用および ODBC(MSDASQL)用を含む、い くつかの Microsoft OLE DB データ プロバイダが MDAC とともに自動 的にインストールされます。 PowerBuilder OLE DB インタフェース ファ イル アプリケーションで OLE DB を使用する場合は、PowerBuilder OLE DB インタフェース ファイルが必要です。ODBC 初期設定ファイルを使用 して OLE DB 設定をカスタマイズした場合は、ODBC 初期設定ファイ ルが必要です。 表 41-10: PowerBuilder OLE DB インタフェース ファイル 名前 pbole110.dll pbodb110.ini インストール先パス 説明 PowerBuilder OLE DB インタフェース PowerBuilder ODBC 初期設定ファイル \Program Files\Sybase\Shared\PowerBuilder 配布先パス アプリケーションと同じパス、 システム パスのディレクト リ、または App Path レジストリ キー レジストリ エントリ 詳細については、857 ページの「App Path レジス トリ キー」を参照してください。 INI ファイルと DLL ファイルは、同しディレクトリにあること か必要です。pbodb110 初期設定ファイルを修正した場合には、修正し たバーションを配布してくたさい。 注意 ADO.NET データベース インタフェース PowerBuilder ADO.NET イ ン タ フ ェ ー ス は、OLE DB、Microsoft SQL Server .NET、Oracle ODP.NET、および Sybase ASE データ プロバイダ をサポートしています。ADO.NET を使用する場合は、pbado110.dll、 pbrth110.dll、Sybase.PowerBuilder.Db.dll、Sybase.PowerBuilder.DbExt.dll、 および OLE DB のための OLE DB データ プロバイダを配布しなければ なりません。 pbado110.dll および pbrth110.dll ファイルは標準 DLL ファイルであり、 ほかの PowerBuilder DLL と同じ方法で配布することができます。しか し、Sybase.PowerBuilder.Db.dll および Sybase.PowerBuilder.DbExt.dll は、 .NET アセンブリです。そのファイルを配布するためには、以下の 3 つ の方法のうち 1 つを使用します。 アプリケーション テクニック 877 データベース接続 • ADO.NET ドライバを呼び出す実行ファイルと同じディレクトリ に、Sybase.PowerBuilder.Db.dll および Sybase.PowerBuilder.DbExt.dll ファイルを配布する • Sybase.PowerBuilder.Db.dll および Sybase.PowerBuilder.DbExt.dll の パスを割り当てるために、.NET アプリケーションの構成ファイル を使用する。そのファイルは、アプリケーションが読みこむ環境 設定と共通言語ランライム(CLR)が読み込む環境設定を含む。実 行ファイルの場合、構成ファイル名は実行ファイルと同じ名前に、 拡張子 .config をつけたものである。見本の pb110.exe.config ファイ ルが PowerBuilder 11.0 ディレクトリにある 構成ファイルの詳細については、Microsoft Visual Studio SDK のマ ニュアルを参照してください。 • グローバル アセンブリ キャッシュ(GAC:Global Assembly Cache ) に Sybase.PowerBuilder.Db.dll お よ び Sybase.PowerBuilder.DbExt.dll アセンブリを追加する。GAC の詳細については、Microsoft Visual Studio SDK マニュアルのグローバル アセンブリ キャッシュに関す る資料を参照してください。ランタイム パッケージャを使用する 場合は、アセンブリを GAC にインストールする JDBC データベース インタフェース PowerBuilder JDB イ ン タ フ ェ ー ス は、Sun Java Runtime Environment (JRE)バージョン 1.2 以降をサポートしています。 アプリケーションまたはコンポーネントが JDBC 接続を使用する場合 は、使用する Java VM に対応する Java パッケージだけでなく、JDB ド ラ イ バ を 配 布 し な け れ ば な り ま せ ん。Java 仮 想 マ シ ン と、Sybase jConnect® for JDBC などベンダ提供の JDBC 準拠ドライバも、データ ソースにアクセスするコンピュータ上にインストールして設定する必 要があります。 Java VM の詳細については、次の「Java サポート」を参照してください。 表 41-11: PowerBuilder JDB ファイル 名前 pbjdb110.dll pbjdbc12110.jar 説明 JRE 1.2 以降対応 PowerBuilder JDBC ドライバ(JDB) PowerBuilder JDB ドライバおよび JRE 1.2 以降対応 Java パッケージ インストール先パス \Program Files\Sybase\Shared\PowerBuilder 878 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 配布先パス アプリケーションと同じパス、 システム パスのディレクト リ、または App Path レジストリ キー レジストリ エントリ CLASSPATH 環境変数には、PowerBuilder pbjdbc12110.jar ファイルを含めておいてください。たとえば、次のよ うになります。 [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control \Session Manager\Environment] "CLASSPATH"="C:\Program Files\sybase\shared\ PowerBuilderbjdbc12110.jar;... 注意 888 ページの「EAServer 上の PowerBuilder コンポーネント」お よび 893 ページの「EAServer 上の Web データウィンドウ」を参照して ください。 Java サポート Java Runtime Environment(JRE)を使用するアプリケーションまたはコ ンポーネントとともに PowerBuilder pbjvm110.dll ファイルを配布し、さ らにターゲット コンピュータに JRE をインストールしておく必要が あります。JRE は、JSP ターゲット、EJB クライアント、JDBC 接続、 および XSL-FO を使用した PDF での保存をする場合に必要になりま す。PowerBuilder とともにインストールされている JRE を、ターゲッ ト コンピュータ上の PowerBuilder ランタイム ファイルと同じディレ クトリにコピーするか、ユーザの PATH システム環境変数で定義され た場所に保存されている既存の JRE を使用します。 Java VM の検索 PowerBuilder アプリケーションで Java VM が必要になると、PowerBuilder ランタイムは、ユーザ コンピュータ上で pbjvm110.dll がインストール されているディレクトリのサブディレクトリ内の jvm.dll ファイルを 探します。jvm.dll ファイルは、JDK 1.4 以降のインストール ディレク トリ JRE\bin\client と、JDK 1.2 および 1.3 インストール ディレクトリ JRE\bin\classic にインストールされます。 PowerBuilder は、PowerBuilder アプリケーションが使用する現在のパス の先頭に jvm.dll の保存場所を追加します。このパスは、ユーザの PATH システム環境変数で定義されているパスです。PowerBuilder は、Windows レジストリに保存されている環境変数を変更しません。 アプリケーション テクニック 879 Java サポート jvm.dll を探すために、PowerBuilder は、まず pbjvm110.dll がインス トールされている場所を確認します。pbjvm110.dll が、 C:\Sybase\Shared\PowerBuilder にインストールされていると仮定しま す。次に、PowerBuilder はこの検索プロシージャを使って、現在使用 しているパスに jvm.dll の保存場所を追加します。 1 C:\Sybase\Shared\PowerBuilder\ 内でディリクトリ構造 JRE\bin\client(JDK 1.4 以降の場合)を検索し、見つかったらこ れをパスの先頭に追加します。 2 見つからなかった場合、JRE\bin\client を含む JDK ディリクトリ構 造を C:\Sybase\Shared\PowerBuilder\ 内で検索し、見つかったらこ れをパスの先頭に追加します。 3 見つからなかった場合、C:\Sybase\Shared\PowerBuilder\ 内でディ リクトリ構造 JRE\bin\classic(JDK 1.2 または 1.3 の場合)を検索 し、見つかったらこれをパスの先頭に追加します。 上記のディレクトリ構造がいずれも見つからなかった場合、PowerBuilder はユーザの PATH 環境変数で定義された場所にある最初の jvm.dll を 使用します。jvm.dll が見つからないと、Java VM は起動されません。 ランタイム Java VM クラスパス ランタイム スタ ティック レジストリ クラスパスの上書き 880 PowerBuilder が Java VM を起動すると、Java VM は内部パスとクラス パス情報を使って、必要な Java クラスが常に使用できる状態にします。 実行時、Java VM は以下のパスを結合して作成されたクラス パスを使 用します。 • システム JAVA_HOME 環境変数 • Java VM の起動時にプログラムによって追加されるクラス パス。た とえば、EJB クライアント アプリケーションは、CreateJavaVM メ ソッドにクラス パスを渡すことができます。 • PowerBuilder ランタイム スタティック レジストリ クラスパス。これ は、PowerBuilder でアプリケーションを配布するときに使用される、 Windows レジストリ内のパスに対応する pbjvm110.dll ファイルに 組み込まれるパスです。このパスには、Java VM を使用する機能 が実行時に必要とするクラスが含まれます。 • システムの CLASSPATH 環境変数 • 現行ディレクトリ 必要に応じて、スタティック レジストリ内でランタイムの使用のため に定義された JVM 設定およびプロパティを上書きできます。 PowerBuilder は、次のアルゴリズムを使用して設定情報を探します。 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 1 JVM に対して最初のリクエストが発生すると、PowerBuilder は、 JVM を作成する関数に渡す設定情報およびプロパティのレジスト リ エントリを探します。 2 PowerBuilder が設定情報のレジストリエントリを見つけた場合、ス タティック レジストリのかわりにこのレジストリ エントリを使 用します。レジストリ エントリが見つからない場合、PowerBuilder はスタティック レジストリを使用します。 3 PowerBuilder が JVM に渡すカスタム プロパティのレジストリ エ ントリを見つけた場合、スタティック レジストリのかわりにこの レジストリを使用します。レジストリ エントリが見つからない場 合、PowerBuilder はスタティック レジストリ エントリを使用しま す。 デフォルト設定を上書きするには、 HKEY_LOCAL_MACHINE\Software\Sybase\PowerBuilder\11.0\Java キー内に、PBRTConfig という名前の新しいキーを作成した後、 PBJVMconfig および PBJVMprops のどちらか一方または両方のサブ キーを作成したキーに追加します。 スタティック レジストリ エントリを複製するには、PBIDEConfig キー 内に表示される次のサブキーに同じ文字列値を追加します。 サブキー PBJVMconfig PBJVMprops 文字列値名 Count 0 java.compiler 文字列値データ 1 -verbose:jni,class なし 環境設定またはプロパティ エントリのどちらか一方または両方を上 書きできます。エントリを誤って指定すると、PowerBuilder はスタ ティック レジストリのデフォルト設定に戻します。ただし、これらの エントリを正しく設定しないと JVM 内で正しく動作しなくなるので、 エントリを変更する際は注意が必要です。 PowerBuilder エクステンション PowerBuilder 11.0 には、複数の PowerBuilder エクステンション ファイ ルが備えられています。アプリケーションがこれらのエクステンショ ンを使用する場合、表 41-12 に示すファイルを配布する必要がありま す。 アプリケーション テクニック 881 PDF と XSL-FO のエクスポート 表 41-12: PowerBuilder の組み込みのエクステンションを使用する場合に 必要なファイル エクステンション PowerBuilder Document Object Model EJB クライアント Web サービス用 SOAP クライアン ト ファイル pbdom110.pbx、PBXerces110.dll、xerces-c_2_6.dll、 xerces-depdom_2_6.dll pbejbclient110.pbx、pbejbclient110.jar ExPat110.dll 、libeay32.dll、ssleay32.dll、 xerces-c_2_6.dll、xerces-depdom_2_6.dll、 EasySoap110.dll、pbnetwsruntime110.dll、 pbsoapclient110.pbx、pbwsclient110.pbx、 Sybase.PowerBuilder.WebService.Runtime.dll、 Sybase.PowerBuilder.WebService.RuntimeRemoteLoader.dll EJB クライアントに関しては、表に示したファイルに加えて、EJB サーバ の JDK と互換性のある Java Runtime Environment(JRE)をクライアン トで使用できるようにし、CLASSPATH に追加する必要があります。 詳細については、879 ページの「Java サポート」を参照してください。 PDF と XSL-FO のエクスポート PowerBuilder は、データウィンドウのデータと提示様式を 2 つのテクニッ クを使って Portable Document Format(PDF)ファイルとして保存できま す。PowerBuilder は PDF ファイルとして保存する場合に、デフォルトで distiller を使用します。PowerBuilder では Apache XML Formatting Objects プロセッサを使用して、PDF または XSL Formatting Objects(XSL-FO) 形式に保存することもできます。 Ghostscript distiller の使い方 SaveAs メソッドを使って distiller でデータを PDF として保存するには、 まず、次の手順に従って Ghostscript をダウンロードし、コンピュータ にインストールする必要があります。 GPL Ghostscript の使用に際しては、GNU General Public License(GPL) の規定に従う必要があります。GPL Ghostscript をコンピュータにイン ストールする前に、 GPL を読んでください。 GPL は GNU Project Web server のサイト http://www.gnu.org/licenses/gpl.html から入手できます。 882 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 AFPL Ghostscript の使用に際しては、Aladdin Free Public License(AFPL) の規定に従う必要があります。AFPL Ghostscript の商用配布は通常商用 のライセンスを必要とします。詳細については、Ghostscript Web のサイ ト http://www.ghostscript.com/awki を参照してください。 ❖ Ghostscript をインストールするには 1 コンピュータの一時ディレクトリに、Ghostscript Web のサイト http://www.ghostscript.com/awki にあるサイトの 1 つから必要な Ghostscript のバージョンの自己解凍型実行ファイルをダウンロー ドします。 テスト用に使用した Ghostscript のバージョンについては『リリー ス ノート』マニュアルを参照してください。 2 実行ファイルを実行して、Ghostscript をシステムにインストールし ます。 デフォルトのインストール ディレクトリは C:\Program Files\gs で す。別のディレクトリを選択したり、Ghostscript コンソールと readme ファイルへのショートカットを作成したりすることもでき ます。 Ghostscript をインストールした後で、Ghostscript の使い方およびアプ リケーションでそれを配布することについて調べるために、Ghostscript インストレーション ディレクトリの doc サブディレクトリにある readme.htm ファイルを読む必要があります。 名前を付けて行を保存に失敗 データウィンドウ ペインタで PDF として保存するには、[ファイル| 名前を付けて行を保存]を選択して、ファイルの種類として「PDF」を 選択します。Ghostscript をインストールしないで、デフォルトのエク スポート プロパティを使用する場合は、PowerBuilder は名前を付けて 行を保存することに失敗したことを知らせるポップアップ ウィンド ウを表示します。Ghostscript をインストールし、Ghostscript をインス トールしたディレクトリ名を変更すると、PDF 形式での行の保存はエ ラーを通知することなく失敗します。 ファイルの場所 distill メソッドを使ってデータウィンドウ オブジェクトを PDF として 保存する場合、PowerBuilder は、次の場所からインストールされた GPL または AFPL Ghostscript を探します。 • • アプリケーション テクニック Windows レジストリ pbdwe110.dll ファイルの相対パス (通常は Sybase\Shared\PowerBuilder) 883 PDF と XSL-FO のエクスポート • システムの PATH 環境変数 GPL または AFPL Ghostscript を Ghostscript 実行ファイルを使ってイン ストールした場合は、Windows レジストリにパスが追加されます。 Ghostscript ファイルが pbdwe110.dll ファイルの相対パスにある場合、 Ghostscript は次のディレクトリ構造でインストールされています。 dirname\pbdwe110.dll dirname\gs\gsN.NN dirname\gs\fonts dirname はランタイム DLL を含むディレクトリ、N.NN は Ghostscript の リリース バージョン番号です。 すべてのフォントを配布する必要はないかもしれません。フォントに ついての詳細は、Fonts and font facilities supplied with Ghostscript のサイト http://www.ghostscript.com/doc/current/Fonts.htm を参照してください。 PostScript プリンタ ドライバ 使用しているコンピュータに PostScript プリンタがすでにインストー ルされている場合は、PDF ファイルの作成に必要な PostScript ドライ バ ファイルである PSCRIPT5.DLL、PS5UI.DLL、および pscript.ntf も インストールされています。通常、これらのファイルは、Windows XP の場合は C:\WINDOWS\system32\spool\drivers\w32x86 に、また、 64 ビット Vista システムの場合は C:\Windows\System32\DriverStore\FileRepository\ntprint.inf_1a216484\ Amd64 にあります。ユーザは PDF の作成に使用するオペレーティン グシステムに適したドライバ ファイルを使用する必要があります。 これらのファイルは dirname\drivers ディレクトリにコピーします。 Sybase\Shared\PowerBuilder\drivers に イ ン ス ト ー ル さ れ て い る 関 連 ファイルも配布する必要があります。これらのファイルはユーザのコ ンピュータにコピーまたはインストールできます。次のディレクトリ 構造で配置する必要があります。 dirname\pbdwe110.dll dirname\drivers PostScript プリンタ プロファイル 各ユーザのコンピュータに、Sybase DataWindow PS という PostScript プ リンタ プロファイルがなければなりません。このプロファイルは、 データウィンドウ ペインタで PDF ファイルにデータウィンドウの行 を保存する際に、自動的に開発コンピュータに追加されます。この方 法を使用すると、PowerBuilder がインストールされているコンピュー タに Sybase DataWindow PS プリンタを追加できます。 ユーザは、次のいずれかの方法で、プリンタの追加ウィザードを使用 して手動でプロファイルを追加することもできます。 884 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 • ウィザードの[プリンタ ソフトウェアのインストール]ページで [ディスク使用]ボタンをクリックし、 (Shared\PowerBuilder\drivers デ ィ レ ク ト リ に、PowerBuilder と と も に イ ン ス ト ー ル さ れ た) Adist5.inf ファイルまたは別の PostScript ドライバ ファイルを検索 し、 [プリンタ名]ページでプリンタ名を「Sybase DataWindow PS」 に変更します。 • ウィザードの[プリンタ ソフトウェアのインストール]ページ で、一覧表示されているプリンタから、名前に「PS」が含まれる プリンタ([Apple Color LW 12/660 PS]など)を選択し、[プリン タ名]ページでプリンタ名を「Sybase DataWindow PS」に変更し ます。 アプリケーションで IIS サーバから PDF ファイルまたは XSL ファイル を印刷する場合、 『アプリケーションとコンポーネントの .NET への配 布』マニュアルのプリント マネージャの章を参照してください。 Apache FO プロセッサの使い方 Apache プロセッサを使用して PDF または XSL-FO 形式で保存するア プリケーションの場合には、アプリケーションとともに fop-0.20.4 ディ レクトリと Java Runtime Environment(JRE)を配布する必要がありま す。 これらのディレクトリは、PowerBuilder ランタイム ファイルと同じ ディレクトリに配布する必要があります。たとえば、MyApplication と いうディレクトリにアプリケーションと pbvm110.dll とそのほかの PowerBuilder ランタイム ファイルを配布する場合、Apache プロセッサ を MyApplication\fop-0.20.4 および MyApplication\jre の JRE に配布し ます。ただし、ターゲット コンピュータ上に JDK をフル インストー ルし、クラスパスに追加してある場合は、その場所に JRE のコピーを 置く必要はありません。 ユーザのクラスパスに、次の JAR ファイルが必要です。 fop-0.20.4\build\fop.jar fop-0.20.4\lib\batik.jar fop-0.20.4\lib\xalan-2.3.1.jar fop-0.20.4\lib\xercesImpl-2.1.0.jar fop-0.20.4\lib\xml-apis.jar fop-0.20.4\lib\avalon-framework-cvs-20020315.jar JRE についての詳細は、879 ページの「Java サポート」を参照してく ださい。 アプリケーション テクニック 885 データウィンドウ Web コントロール ActiveX Windows DBCS プラットフォームでは、 ターゲット コンピュータの Windows フォント ディレクトリ(C:\WINDOWS\fonts など)に、DBCS 文字を サポートするファイルも配布する必要があります。フォントの設定に ついての詳細は、Apache Web のサイト http://xml.apache.org/fop/fonts.html を 参照してください。 データウィンドウ Web コントロール ActiveX データウィンドウ Web コントロール ActiveX を使用している場合は、 Web サーバに以下のファイルを配布する必要があります。 表 41-13: データウィンドウ Web コントロール ActiveX 用の PowerBuilder ファイル 名前 psdwc110.cab pbjdbc12110.jar 必要とする対象 Open Software Distribution 情報ファイル、Web ActiveX およびトランザクション コントロール用 DLL を含む CAB ファイル 必要な Java クラスを含む JAR ファイル 配布先システムに Sun JRE がインストールされていない場合は、Sun Java Web サイトから JRE をダウンロードする必要があります。クライ アント ブラウザで Web ActiveX およびトランザクション コントロール を使用できるようにするには、配布された HTML ページの Object 要素 に CODEBASE 属性を記述します。 CODEBASE 属性につ いて CODEBASE 属性は、CAB ファイルまたは OCX ファイルの保存場所を 識別します。この属性によってブラウザは、CAB ファイルまたは OCX ファイルをダウンロードし、CAB ファイルの場合はアンパックして、 それをユーザのコンピュータに登録することができます。CODEBASE の一般的な値は、CAB または OCX ファイルの保存場所を識別する相 対 URL の後に、# 記号と、カンマで 4 つに区切られたバージョン番号 とが記述されます。バージョン番号は、PowerBuilder のバージョン番 号と同じです。たとえば、次のようになります。 CODEBASE="cabs/psdwc110.cab#10,0,0,5031" 追加ファイルが必要になる場合もあります。詳細については、PowerBuilder オンライン ブックの「データウィンドウ Web コントロールの配布」ま たは『データウィンドウ プログラマーズ ガイド』マニュアルを参照し てください。 886 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 プラグインと PowerBuilder ウィンドウ ActiveX コント ロール プラグイン データウィンドウまたはウィンドウ プラグインを使用している場合 は、表 41-14 のファイルをユーザのコンピュータに配布する必要があ ります。 表 41-14: ウィンドウおよびデータウィンドウ プラグイン用 PowerBuilder ファイル 名前 nppba110.dll nppbs110.dll npdwe110.dll 必要とする対象 標準ウィンドウ プラグイン セキュリティ ウィンドウ プラグイン データウィンドウ プラグイン インストール先パス \Program Files\Sybase\PowerBuilder 11.0\Internet Tools\Plugins 配布先パス ブラウザ プラグイン ディレクトリ すべてのプラグインで、プラグインをサポートするブラウザが 必要です。Microsoft Internet Explore 5.5 Service Pack 2 以降のバージョン では、プラグインをサポートしていません。またウィンドウ プラグイ ンでは、ユーザのコンピュータに PowerBuilder ランタイム DLL が必要 です。詳細については、第 32 章「データウィンドウ プラグインの使 い方」および第 33 章「PowerBuilder ウィンドウ プラグインの使い方」 を参照してください。 注意 ウィンドウ ActiveX コ ントロール PowerBuilder ウィンドウ ActiveX を使用している場合は、ユーザのコ ンピュータで表 41-15 のファイルが使用できるようにしなければなり ません。 表 41-15: ウィンドウ ActiveX 用 PowerBuilder ファイル 名前 pbrx110.ocx pbrxs110.ocx 必要とする対象 標準 PowerBuilder ウィンドウ ActiveX セキュリティ PowerBuilder ウィンドウ ActiveX インストール先パス 配布先パス アプリケーション テクニック \Program Files\Sybase\Shared\PowerBuilder Windows システム ディレクトリ 887 EAServer 上の PowerBuilder コンポーネント レジストリ エントリ PowerBuilder ウィンドウ ActiveX コントロールを クライアント コンピュータで使用できるようにするには、これらのコ ントロールをコンピュータにコピーし、REGSVR32 ユーティリティを 使用して登録します。または、Web サーバの HTML ページの Object 要 素に CODEBASE 属性を含めます。詳細については、886 ページの 「CODEBASE 属性について」を参照してください。 注意 PowerBuilder ウィンドウ ActiveX コントロールには、ActiveX コ ントロールをサポートするブラウザが必要です。また、ユーザ コン ピュータで、PowerBuilder ランタイム DLL、Microsoft のファイル MFC42.dll、MSVCRT.dll、URL.dll、および URLMON.dll を使用できる 必要があります。Microsoft のファイルは、通常の場合、対象コン ピュータの Windows システム ディレクトリにすでにインストールさ れています。インストールされていない場合は、Microsoft の Web サ イト Internet Explorer Components Gallery のサイト http://activex.microsoft.com/controls/vc/mfc42.cab を参照してください。 詳細については、第 34 章「PowerBuilder ウィンドウ ActiveX の使い方」 を参照してください。 EAServer 上の PowerBuilder コンポーネント EAServer で PowerBuilder コンポーネントを実行するには、コンポーネ ントを開発した時の PowerBuilder のバージョンとビルド番号のランタ イム ライブラリが、サーバ上で使用できるようにします。PowerBuilder のメンテナンス リリースをインストールし、EAServer に新しいコン ポーネントまたはアップデートしたコンポーネントを配布するときに は、サーバ上の PowerBuilder VM もアップデートする必要があります。 PowerBuilder で生成されたコンポーネントを実行する EAServer ホスト では、表 41-16 のファイルが必要です。PowerBuilder コンポーネントが 表に一覧表示されている機能またはデータベース インタフェースを 使用しない場合は、サーバにファイルをインストールする必要はあり ません。PowerBuilder VM には、EAServer libjcc ファイルとその関連 ファイルも必要です。表の UNIX の列にある ext は、ライブラリ名に 対応するプラットフォーム固有の拡張子を表します。たとえば Solaris では、このファイル名は libpbvm110x.so になります。 888 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 表 41-16: EAServer ホストに必要な PowerBuilder ファイル Windows UNIX 説明 pbvm110.dll libpbvm110x.ext PowerBuilder 仮想マシン (すべての PowerBuilder コ ンポーネントに必要) pbshr110.dll pbshr110.ext PowerBuilder 仮想マシンに 必要 pbdwe110.dll libpbdwe110x.ext データストアのサポート pbjag110.dll libpbjag110x.ext、 EAServer での PowerBuilder pbjag110.ext のサポート pbdwr110.pbd pbdwr110.pbd Web データウィンドウの サポート(PBDWE が必 要) htmldw.js htmldw.js Web データウィンドウの サポート — pbRTC110.dll および 表 リッチテキストのサポー 41-5 に記載の追加のラ ト ンタイム ファイル PBXerces110.dll、 xerces-c_2_6.dll、 xerces-depdom_2_6.dll libxerces110x.ext、 XML サポート libxerces-c_2_1_0.ext pbdom110.pbx libpbdom110x.ext PBDOM サポート EasySoap110.dll、 ExPat110.dll、 libeay32.dll、 ssleay32.dll、 pbsoapclient110.pbx、 pbwsclient110.pbx、 pbnetwsruntime110.dll、 xerces-c_2_6.dll、 xerces-depdom_2_6.dll、 Sybase.PowerBuilder.Web Service.Runtime.dll、 Sybase.PowerBuilder.Web Service.RuntimeRemoteL oader.dll pbo84110.dll — EasySoap のための SOAP クライアントおよび .NET Web サービス( .NET Web サービスでは 2 つの Sybase.PowerBuilder DLL ファイルが EAServer\Bin ディレクトリに配布され る必要がある) libpbo84110x.ext Oracle 8.0.x と Oracle 8i 8.1.x データベース ドライ バ Oracle9i データベース ドラ イバ pbo90110.dll アプリケーション テクニック libpbo90110x.ext (Solaris と Linux の み) 889 EAServer 上の PowerBuilder コンポーネント Windows pbo10110.dll pbodb110.ini Windows の場合 UNIX libpbo10110x.ext (Solaris と Linux の み) pbodb110.ini pbodb110.dll libpbodb110x.ext pbsnc110.dll libpbsnc110x.ext pbsyj110.dll libpbsyj110x.ext pbjdb110.dll libjdb110x.ext — libpbwfr110.ext pbjdbc12110.jar pbjdbc12110.jar 説明 Oracle 10g データベース ド ライバ PowerBuilder ODBC 初期設 定ファイル PowerBuilder ODBC インタ フェース SQL Native Client ネイティ ブ データベース インタ フェース Adaptive Server Enterprise ネイティブ データベース インタフェース Sun Java VM JRE 1.1 以降対 応 JDBC データベース ド ライバ PowerBuilder UNIX 拡張ラ イブラリ PowerBuilder JDBC ドライ バ対応 Java クラス(JRE 1.2 以降に必要) PowerBuilder VM インストーラを使用できます。このインストーラは、 表 41-16 に記載されているファイルをインストールするために DVD の PBVM フォルダに用意されています。PBVM セットアップ プログラム は、PowerBuilder 11.0 用の Web データウィンドウ サーバ コンポーネント (HTMLGenerator110)とリモート デバッグに必要な PBDebugBroker110 コンポーネントもインストールします。 EAServer コンポーネントにほかのデータベース ドライバを使用する こともできますが、トランザクション管理およびインスタンス プーリ ングのための EAServer サポートを活用したい場合は、上の表に記載さ れているいずれかのドライバを使用してください。 UNIX の場合 890 EAServer をインストールしたときに表 41-16 に記載されているファイ ルがインストールされなかった場合、Sybase Downloads EBFs/Maintenance page のサイト http://downloads.sybase.com/ からご利用の プラットフォームで必要なファイルを入手できることがあります。 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 UNIX プラットフォームで動作する EAServer に配布される PowerBuilder コンポーネントは、Windows API に依存したり、GUI を使用したりす ることはできません。共有ライブラリは、UNIX サーバ上の EAServer lib ディレクトリにインストールされる必要があります。PowerBuilder JDBC ドライバに必要な Java クラスを、EAServer の html/classes/com/sybase/powerbuilder/jdbc ディレクトリにインストール する必要があります。 UNIX の接続キャッシュ PowerBuilder コンポーネントが接続キャッシュ を使用するためには、表 41-16 に記載のデータベース ドライバが必要 です。PowerBuilder コンポーネントが接続キャッシュを使用するとき は、該当する PowerBuilder ドライバがロードされます。 PowerBuilder COM サーバ コンポーネントが次の表に一覧表示されている機能を使用する場合 は、PowerBuilder で生成される COM サーバ ファイルに加えて、表 4117 の PowerBuilder ランタイム ファイルを、サーバが実行されるコン ピュータ上にインストールする必要があります。 表 41-17: COM サーバ ホストに必要な PowerBuilder ファイル 名前 pbvm110.dll 説明 PowerBuilder 仮想マシン(すべての PowerBuilder コン ポーネントに必要) pbcomrt110.dll PowerBuilder COM ランタイム pbshr110.dll pbvm110.dll に必要 libjcc.dll pbvm110.dll に必要 libjutils.dll libjcc.dll に必要 pbdwe110.dll コンポーネントがデータストアを使用する場合に必要 pbrtc110.dll および コンポーネントがリッチテキストを使用する場合に必 表 41-5 に記載の追 要 加のランタイム ファイル pbodb110.ini データベース接続に必要な PowerBuilder ODBC 初期設 定ファイル pbodb110.dll データベース接続に必要な PowerBuilder ODBC インタ フェース インストール先パス アプリケーション テクニック \Program Files\Sybase\Shared\PowerBuilder 891 PowerBuilder オートメーション サーバ COM サーバと同じディレクトリ、またはシステム パス上 のディレクトリ 配布先パス レジストリ エントリ PowerBuilder COM サーバは自己登録を行います。 つまり、REGSVR32 ユーティリティを使用して、COM サーバを使用す るコンピュータ上でサーバを登録することができます。 注意 PowerBuilder COM サーバの配布の詳細については、642 ページ の「PowerBuilder COM サーバの配布」を参照してください。 データベース ドライバ コンポーネントがデータベースに接続する場合は、該当するデータ ベース ドライバも配布しなければなりません。COM コンポーネント ではどのデータベース ドライバでも使用できますが、COM+ によるト ランザクション管理と接続プーリングのサポートを活用したい場合 は、ODBC を使用する必要があります。接続プーリングのみのサポー トを必要とする場合は、任意のスレッド セーフ ODBC ドライバを使用 できます。トランザクションのサポートも必要な場合は、Microsoft の Oracle 対応 ODBC ドライバまたは Microsoft の SQL Server 対応 ODBC ドライバなど、Microsoft Distributed Transaction Coordinator(DTC)を サポートするドライバを使用しなければなりません。 データベース ドライバの詳細については、869 ページの「データベー ス接続」を参照してください。 PowerBuilder オートメーション サーバ PowerBuilder オートメーション サーバを使用するには、以下のファイ ルを配布する必要があります。 892 • オートメーション サーバの実装を含む PBD または DLL • タイプ ライブラリ ファイルの作成を選択した場合は生成された タイプ ライブラリ ファイル。また、名前付きサーバを構築する場 合は、PowerBuilder アプリケーションのタイプ ライブラリ情報を 提供する pbaen110.tlb ファイル • プロジェクト ペインタで生成され、PBD または DLL とタイプ ラ イブラリ ファイルの配布先ディレクトリを参照するように編集さ れたレジストリ更新ファイル(.reg)のコピー PowerBuilder 第 41 章 • アプリケーションとコンポーネントの配布 891 ページの「PowerBuilder COM サーバ」に記載されているよう な、サーバが必要とする PowerBuilder ランタイム ファイルおよび データベース接続ファイル 上記のファイルを配布したのち、レジストリ更新ファイルを実行して、 ターゲット コンピュータ上にサーバを登録します。オートメーション サーバの使い方についての詳細は、443 ページの「オートメーション サーバを使用するアプリケーションの配布」を参照してください。 OLE オートメーション オブジェクトのレジストリ情報の作成 OLE インバウンド オートメーションで使用されるユーザ オブジェク トがアプリケーションに含まれる場合、ユーザのレジストリを更新し なければなりません。PowerBuilder オートメーション オブジェクト レ ジストリ ファイル ジェネレータを使うと、重複しないグローバル識別 子(GUID)、登録(REG)ファイル、およびタイプ ライブラリ(TLB) を生成できます。オートメーション サーバ プロジェクト ウィザード は、新規作成 ダイアログボックスの[プロジェクト]ページにありま す。 詳細については、443 ページの「オートメーション サーバを使用する アプリケーションの配布」を参照してください。 EAServer 上の Web データウィンドウ EAServer 上で、ページ サーバとして JSP を使用して、Web データウィ ンドウ サーバ コンポーネントを実行できます。コンポーネントのトラ ンザクション サーバとページ サーバは、同一コンピュータ上でも異な るコンピュータ上でも実行できます。 トランザクション サーバに必要なファイ ル トランザクション サーバには、以下の 2 種類のファイルが必要です。 • データウィンドウ オブジェクトの定義を含む PBL または PBD ファイル これらのファイルは、サーバのパス内のディレクトリにインス トールしておく必要があります。EAServer がサービスとして実行 されている場合は、これらのファイルがシステム パス上に存在す るか、または完全修飾名で指定されなければなりません。 アプリケーション テクニック 893 EAServer 上の Web データウィンドウ • PowerBuilder ランタイム ファイル(Windows 上の pbvm110.dll、 pbshr110.dll、pbjag110.dll、および pbdwe110.dll を含む)と pbdwr110.pbd。pbdwr110.pbd ファイルには、データウィンドウ HTMLGenerator110 コンポーネントの実装が含まれる PowerBuilder VM インストーラを使用できます。このインストーラ は DVD の PBVM フォルダに用意されていて、これらのファイル をインストールします。必要なファイルの詳細については、888 ページの「EAServer 上の PowerBuilder コンポーネント」を参照し てください。 さらに、コンポーネントがアクセスするデータベースの接続キャッ シュを作成する必要があります。詳細については、 『データウィンドウ プログラマーズ ガイド』マニュアルを参照してください。 カスタム コンポーネント データウィンドウ コンポーネントのカスタム バージョンを作成し、よ り効率的に再使用できるようにプロパティを構成できます。詳細につ いては、『データウィンドウ プログラマーズ ガイド』マニュアルを参 照してください。 動的ページ サーバに 必要なファイル JSP をページ サーバとして使用し、Java を使って EAServer に接続する には、JSP サーバ コンピュータ上に以下のファイルが必要です。 これらは、アプリケー ション用に作成したファイルです。JSP ターゲットを使用してこれら のファイルを作成した場合は、組み込み配布コントローラを使ってこ れらのファイルをインストールできます。詳細については、 『 JSP ター ゲットでの作業』マニュアルを参照してください。 HTML ページ、テンプレート、およびスクリプト Java 対応 EAServer クライアント ソフトウェア JSP サーバでは、表 41-18 のファイルが必要です。 表 41-18: JSP サーバに必要な EAServer クライアント ファイル 名前 easclient.jar easj2ee.jar 説明 クライアントに必要な Java クラス J2EE サポートに必要な Java クラス Sun Java 開発キット(JDK) EAServer とともにインストールされた JDK は、どのバージョンも、Sybase\Shared\Sun ディレクトリに保存され ています。PowerBuilder とともにインストールされた JDK は、 Sybase\Shared\PowerBuilder ディレクトリに保存されています。 894 PowerBuilder 第 41 章 アプリケーションとコンポーネントの配布 JDK 1.2 または 1.3 を使用する場合、JDK の JRE\bin\classic サブディレ クトリが、システムの PATH 環境変数に追加されていることを確認し ます。 JDK 1.4 以降を使用する場合、JDK の JRE\bin\client サブディレクトリ が、システムの PATH 環境変数に追加されていることを確認します。 COM+ または IIS 上の Web データウィンドウ ASP をページ サーバとして使用すると、COM+ 上で Web データウィ ンドウ サーバ コンポーネントを実行できます。また、Microsoft IIS ア プリケーション サーバ上で Web データウィンドウを実行することも できます。 COM+ または IIS サー バで必要なファイル COM+ または IIS サーバでは、次の 2 種類のファイルが必要です。 • データウィンドウ オブジェクトの定義を含む PBL または PBD ファイル これらのファイルは、システム パス内のディレクトリにインス トールしておく必要があります。 システム パスおよびシステム DSN の使用 COM+ および IIS はどちらもシステム サービスとして実行される ため、必要なファイルはシステム パス上で使用でき、データ ソー スはシステム DSN として定義されていなければなりません。ユー ザ パスおよびユーザ DSN は参照されません。 • アプリケーション テクニック PowerBuilder ランタイム ファイルと、データウィンドウの HTMLGenerator コンポーネントの実装を含む pbdwr110.dll 895 COM+ または IIS 上の Web データウィンドウ 表 41-19: COM+ または IIS サーバで必要な PowerBuilder ファイル 名前 pbvm110.dll pbshr110.dll libjcc.dll libjutils.dll pbdwe110.dll pbodb110.dll pbodb110.ini pbdwr110.dll 説明 PowerBuilder 仮想マシン pbvm110.dll に必要 pbvm110.dll に必要 libjcc.dll に必要 データウィンドウのサポート PowerBuilder ODBC インタフェース PowerBuilder ODBC インタフェース セットアップ ファイル データウィンドウ HTMLGenerator コンポーネント インストール先パス PowerBuilder が COM+ ま た は IIS サーバ コン ピュータにインストールされていない場合、これらのファイルは COM+ または IIS サーバのシステム パス上のディレクトリにインストールし なければなりません。これらのファイルは、PowerBuilder がインストー ルされているコンピュータの Sybase\Shared\PowerBuilder ディレクト リから取得できます。 レジストリ エントリ 別のコンピュータから pbdwr110.dll をコピーした 場合は、COM+ または IIS サーバにこのファイルを登録しなければな りません。 注意 ODBC データ ソースは、システム DSN として定義する必要があ ります。ODBC の環境設定の詳細については、875 ページの「ODBC データ ソースとドライバの環境設定」を参照してください。 COM+ がサーバ コンポーネントのホストになり、IIS とは異なるコン ピュータで実行されている場合、クライアント インストール パッケー ジを作成し、それを IIS サーバにインストールする必要があります。 896 PowerBuilder 索引 数字 508 条 790 A AccessibleRole カタログ データ(列挙体)値 793 AccessiWeb アクセシビリティ基準 791 Activate イベント、EAServer 内 513 Activate 関数 359, 361 ActiveX コントロール ActiveX のプロパティ、イベント、関数 366 Object プロパティ 381 アクティブ 368 イベント 369 ウィンドウ ActiveX 747 オートメーション 381 概要 347, 349 組合せイベント リスト 369 動作 367 配布 858 表示形態 367 プログラミング 368 プロパティ 366, 367 プロパティ シート 367 Adaptive Server Anywhere(SQL Anywhere 同期を 参照) Adaptive Server Enterprise データベース インタ フェースのプロパティ(トランザクショ ン オブジェクト) 177 AddColumn 関数 158 AddData 関数 277 AddItem 関数 145, 149, 150, 153 AddLargePicture 関数 155 AddPicture 関数 146, 151 AddSeries 関数 277 AddSmallPicture 関数 155 アプリケーション テクニック AddStatePicture 関数 155, 156 ADO.NET、配布要求 877 ALIAS FOR キーワード 概要 193 スクリプト記述 194 AncestorReturnValue 変数 33 Any データ型 388 Application Server Plug-in 499 application/datawindow MIME タイプ 718 application/vnd.powerbuilder MIME タイプ 742 application/vnd.powerbuilder-s MIME タイプ 742 AutoCommit プロパティ(トランザクション オブ ジェクト) COMMIT 文と ROLLBACK 文の実行 179 概要 174 データベース インタフェースごとのリスト 177 B bind.object コンポーネント プロパティ Blob OLE コントロール 365 データウィンドウの同期 530 BMP ファイル リソースとしての配布 837 リソース ファイルでの命名 839 509 C CacheName DBParm 525 Cancel 関数 320, 332 ClassName 関数 388 Clicked イベントとグラフ 283 CLSID PowerBuilder ウィンドウ ActiveX 760 897 索引 レジストリ 435 COM サーバ 621 サーバとオートメーション サーバの比較 621 データ型 625 COM+ クライアントの構築 651 コンポーネントの構築 617 配布 639 COM+ の ImpersonateClient メソッド 637 COM+ の IsCallerInRole メソッド 636 COM+ の IsSecurityEnabled メソッド 636 COM+ の RevertToSelf メソッド 637 COM/COM+ コンポーネントの検証 627 COM/COM+ コンポーネント(COM コンポーネント を参照) COMMANDPARM 属性 Embed 要素 739, 741 Object 要素 761 COMMIT 文 AutoCommit の設定 179 COM コンポーネント 633 EAServer コンポーネント 521 UseContextObject 518 エラー処理 188 概要 178 接続解除時の自動コミット 179, 185 デフォルト以外のトランザクション オブジェクト 186 COM クライアント 環境設定 651 結果集合 630 構築 651 サーバへの接続 652 トランザクションの制御 654 COM コンポーネント 埋め込み PBD 640 開発プロセス 619 構築 617 セキュリティ問題 636 データベース アクセス 628 登録 639 トランザクション サポート 632 898 プロジェクト ペインタでの構築 637 メモリの割り当て 641 CONNECT 文 USING TransactionObject 句 183 エラー処理 188 概要 178 スクリプト記述 183 デフォルト以外のトランザクション オブジェク ト 186 CORBAUserException オブジェクト 599 CreateInstance 関数 577, 578, 636 CreateInstance メソッド、Web サービス プロキシ 705 CreateJavaVM メソッド 668 CreateObject 関数 447 create メソッド 673 CUR ファイル リソースとしての配布 837 リソース ファイルでの命名 839 C 関数に受け渡す Char 変数 473 D Database プロパティ(トランザクション オブジェ クト) 概要 174 データベース インタフェースごとのリスト 177 DataObject プロパティ(データ パイプライン) 320, 325 dbmlsrv9 204 dbmlsync 概要 207 プロセス 208 DBMS プロパティ(トランザクション オブジェク ト) 概要 174 データベース インタフェースごとのリスト 177 DBParm MsgTerse パラメータ 336 DBParm プロパティ(トランザクション オブジェ クト) 概要 174 PowerBuilder 索引 データベース インタフェースごとのリスト 177 DBPass プロパティ(トランザクション オブジェ クト) 概要 174 データベース インタフェースごとのリスト 177 DDE 概要 343 クライアント イベントと関数 345 クライアント関数 345 サーバ イベントと関数 346 Deactivate イベント、EAServer 内 513 DeleteLargePictures 関数 157 DeleteLargePicture 関数 157 DeletePicture 関数 146 DeleteSmallPictures 関数 157 DeleteStatePictures 関数 157 DeleteStatePicture 関数 157 DisableCommit メソッド 520 DISCONNECT 文 USING TransactionObject 句 184 エラー処理 188 概要 178 スクリプト記述 184 データベース トランザクションのプール時 189 デフォルト以外のトランザクション オブジェ クト 186 DLL ファイル PBD ファイルとの比較 834 PowerBuilder 配布 847 概要 834 関数の実行 467 作成 845 テスト 846 含まれるリソース 838 例 841 dwprint.ini 560 E EAServer アプリケーション テクニック PowerBuilder DLL 565 PowerBuilder との統合 496 Unicode 接続キャッシュ 527 インスタンス プーリング 512 共有コンポーネント 505 クライアント プル 592 コンポーネントの配布 565 接続 571 接続エラー 596 トランザクション サポート 516 非同期リクエスト 592 ログ 558 EAServer 環境変数 PB_FOP_SUPPRESSLOG 564 PB_HEAP_LOGFILE_OVERWRITE 52 PB_HEAP_LOGFILENAME 52 PB_POOL_THRESHOLD 51 PBOnFatalError 521 PBRollbackOnRTError 521 EAServer クライアント 構築 569 配布 601 EAServer コンポーネント インタフェース 537 構築 501 データベース更新 529 デバッグ 555 プロパティ 546 メソッドの呼び出し 576 有効期間 515, 522 EAServer プロキシ オブジェクト 概要 574, 575 破棄 582 EAServer プロファイル、作成 503 EAServer プロファイル ダイアログボックス、概要 504 EasySoap Web サービス エンジン 695 EJBConnection オブジェクト 660 EJBTransaction オブジェクト 660 EJB クライアント Java コレクション クラス 677 構築 657 動的キャスティング 676 戻り値のダウンキャスト 675 899 索引 例外処理 677 EJB コンポーネント、メソッドの呼び出し 578, 672 EJB プロキシ オブジェクト 概要 658 生成 658 Embed 要素 712, 716, 725, 738 Embed 要素の APPLICATION 属性 732, 739, 741 Embed 要素の HEIGHT 属性 716, 738 Embed 要素の LIBRARY 属性 739, 741 Embed 要素の SRC 属性 716, 738 Embed 要素の WIDTH 属性 716, 738 Embed 要素の WINDOW 属性 739, 741 EnableCommit メソッド 520 ExternalException イベント 390 F FileEncoding 関数 54 FileLength64 関数 54 FileOpen 関数 54 FileReadEx 関数 55 FileSeek64 関数 54 FileWriteEx 関数 55 FindSeries 関数 278 FOR...NEXT 文(ウィンドウ インスタンスを開く / 閉 じる) 95 FUNCTION 宣言 概要 193 スクリプト記述 194 G gdiplus.dll、Windows 2000 への配布に必要 864 GenerateGUID 関数 450 GenerateRegFile 関数 452 GenerateTypeLib 関数 455 GetChanges 関数 529 GetConnectionOption DBParm 527 GetFocus イベントによるマイクロヘルプの提供 GetFullState 関数 529 GetJavaClasspath メソッド 668 GetJavaVMVersion メソッド 668 GetParent 関数 28, 108 GUID 444, 450 900 78 GUID とレジストリ 435 H HKEY_CLASSES_ROOT 436 HotLinkAlarm DDE イベント 345 HTML Embed 要素 716, 738 Object 要素 760 ウィンドウ ActiveX 760 属性 738 文書、ウィンドウ プラグイン 725, 738 文書、データウィンドウ プラグイン 712, 716 I IAccessible プロパティ 793 ICO ファイル ドラッグ アイコンの指定 163 リソースとしての配布 837 リソース ファイルでの命名 839 imstyle.pbl 812 InfoMaker 様式の作成 812 INFORMIX データベース インタフェース ストアド プロシージャ呼び出しでサポートされ る機能 200 プロパティ(トランザクション オブジェクト) 177 InsertItemFirst 関数 122 InsertItemLast 関数 122 InsertItemSort 関数 122 InsertItem 関数 122, 145, 149, 150, 153 InvokePBFunction 関数 JavaScript 769 VBScript 770 IsInTransaction メソッド 520 IsJavaVMLoaded メソッド 668 IsTransactionAborted メソッド 520 J J2EE アーキテクチャ 497 PowerBuilder 索引 J2EE サーバへの接続 671 Java VM、実行時に起動 879 JavaScript とウィンドウ ActiveX InvokePBFunction 関数 769 PowerScript 関数の呼び出し 767 TriggerPBEvent 関数 771 イベント ハンドラ 765 ユーザ イベントの呼び出し 771 ユーザ定義関数の引数 769 ユーザ定義関数の呼び出し 769 JavaVM オブジェクト 660 Java コレクション クラス、EJB クライアント 677 JBoss のサポート(PowerBuilder Application Server Plug-in) 499 JDBC データベース インタフェースのプロパティ (トランザクション オブジェクト) 177 JRE、配布に必要 879 JVM、実行時に起動 879 L LibraryList プロパティ 446 Lock プロパティ(トランザクション オブジェク ト) 概要 174 データベース インタフェースごとのリスト 177 LogID プロパティ(トランザクション オブジェ クト) 概要 174 データベース インタフェースごとのリスト 177 LogPass プロパティ(トランザクション オブジェ クト) 概要 174 データベース インタフェースごとのリスト 177 LUW(論理的な作業単位) 178 アプリケーション テクニック M MachineCode プロパティ 446 MailSession オブジェクト 463 MAPI アプリケーションからのアクセス 463 概要 463 MDI_1 コントロール 73 MDI アプリケーション キーボード操作 87 構築 71 シートの使い方 75 ショートカット キー 89 マイクロヘルプの提供 77 メニューの使い方 74 MDI アプリケーションのキーボード サポート 87 MDI アプリケーションの標準フレーム 73 MDI シート 概要 74 最大化 77 整列 76 閉じる 77 開く 75 マイクロヘルプの提供 77 メニューの使い方 74 リストを開く 76 MDI フレーム カスタムのサイズ変更 84 シートの整列 76 シートを開く 75 マイクロヘルプの使い方 77 MicroHelpHeight 属性 87 Microsoft Active Accessibility 792 Microsoft Active Accessibility プロパティ 792 Microsoft Excel、OLE 382, 386 Microsoft SQL Server ストアド プロシージャの呼び出し 201 プロパティ(トランザクション オブジェクト) 177 Microsoft Windows インストーラ、ランタイム パッ ケージャに対して必要 859 Microsoft Word OLE 373, 384, 387 901 索引 レター フォーム例 375 MIME タイプ ウィンドウ プラグイン 725 ウィンドウ プラグインの指定 742 データウィンドウ プラグイン 712 データウィンドウ プラグインへの指定 718 MIME タイプの PBD ファイル拡張子 742 MIME タイプの PSR ファイル拡張子 718 MobiLink 同期 dbmlsrv9 204 dbmlsync 207, 208 PowerBuilder オブジェクト 210 アーティクル 207, 233 ウィザード 210 階層構造 205 概要 203 クライアント 207 サーバ 204 削除の処理 239 サブスクリプション 207, 236 スクリプト 206, 228 スクリプトのデフォルト 225 接続イベント 223 テーブル イベント 224 テクニック 237 統合 204 統合データベース 222 パブリケーション 207, 231 ユーザ 207, 234 リモート 204 リモート データベース 231 リモート マシンで必要なファイル 219 MSAA 792 MSAA プロパティ 792 MsgTerse パラメータ 336 MSI ファイル(Microsoft Windows インストーラ) 859 N .NET Web サービス エンジン 693 .NET ターゲット、配布に必要なファイル 902 861 Netscape プラグイン API PowerBuilder ウィンドウ プラグイン 725 データウィンドウ プラグイン 712 NPDWEnn.DLL ファイル 713, 714, 728 NPPBAnn.DLL ファイル 714, 727, 728 NPPBSnn.DLL ファイル 714, 727, 728 O ObjectAtPointer 関数 284 Object プロパティ 概要 38 ドット表記 29 Object 要素の CODEBASE 属性 760 OCI_9U 接続キャッシュ 527 OCX(ActiveX コントロールを参照) ocx_error イベント 391 ODBCU 接続キャッシュ 527 ODBCU_CONLIB データベース パラメータ 528 ODBC インタフェース インストール 847 環境設定 847 ストアド プロシージャ呼び出しでサポートされ る機能 200 プロパティ(トランザクション オブジェクト) 177 OLE PowerBuilder 例外コード 459 アンビエント プロパティ 367 インプレース アクティブ化 358 インプレース アクティブ化のメニュー 359 埋め込み 356 エラー処理 390 オートメーション 371 オートメーションで使用する言語 395 オフサイト アクティブ化 358 オブジェクト 350 オブジェクトと代入 373 オブジェクトのアクティブ化 361 概要 418 型のない変数 388 括弧 383 PowerBuilder 索引 コンテナ アプリケーション 347 コンパイラのチェック 381 サーバ アプリケーション 347, 350, 400, 418 サーバ コマンドの修飾子 371, 386 サーバのメソッドとプロパティ 381 サーバ メモリの割り当て 385 処理効率 389 ストリーム 411 挿入可能オブジェクト 349 低レベルのアクセス時のポインタ 396 データウィンドウ オブジェクトの関数 397 データウィンドウのカラム 398 データ ファイル 364 名前のついたパラメータ 384 バーブ 361, 399 配布 440, 443 引数の参照渡し 383 ブラウザ 400 プログラム可能なオブジェクト 418 プロパティの変更通知 393 ホット リンク 393 リンク 357 リンク情報の管理 357 リンクと埋め込みの比較 356 レジストリ 435 レター フォーム例 375 OLE DB データベース インタフェースのプロパ ティ(トランザクション オブジェクト) 177 OLEActivate 関数 399 OLEObject オブジェクト エラー イベントの継承 427 概要 371 作成 371 接続 371 接続解除と破棄 373 OLEStorage オブジェクト 404 OLEStream オブジェクト 404 OleTxnObject オブジェクト 654 OLE オートメーション Object プロパティ 396, 398 OLEObject 371 構文 381 アプリケーション テクニック シナリオ 375 例 375 OLE オブジェクト、ドット表記 29 OLE オブジェクトの埋め込み 364 OLE オブジェクトの挿入 362 OLE オブジェクトの貼り付け 363 OLE オブジェクトのリンク 362, 364 OLE カスタム コントロール(ActiveX コントロー ルも参照) 347 OLE クラス ユーザ オブジェクト 404 OLE 項目のブラウザ 400 OLE コントロール Blob 365 Contents プロパティ 363 ObjectData プロパティ 365 Object プロパティ 381 アクティブ化 361 イベント 365 埋め込み 353, 362 埋め込みデータの保存 364 オートメーション 381 オフサイト アクティブ化とインプレース アク ティブ化の比較 358 オブジェクトのアイコン 353 オブジェクトのアクティブ化 353, 354 オブジェクトの削除 355 オブジェクトの挿入 362 オブジェクトの表示 353 オブジェクトの変更 355, 362 概要 347 空の OLE コントロール 350, 359 サーバ アプリケーション 364 定義 350 動作 352, 355 表示形態 352 プロパティ シート 352 メニュー 359 ユーザ インタラクション 355 リンク 353, 362, 364 リンクの更新 354 リンクの中断 359 OLE ストリーム read/write ポインタ 413 903 索引 概要 402, 411 長さ 413 開く 411 読み込みと書き込み 413 OLE ストレージ 概要 402 構造 403 効率 405 ストレージの構造の記録管理 416 ファイルの構築 408 保存 406 メンバー 407 例 408 OLE のタイプ ライブラリ 425, 439, 455 Open 関数 96 Open 関数(OLE) 362 OpenSheet 関数 75 ORACLE データベース インタフェース プロパティ(トランザクション オブジェクト) 177 ストアド プロシージャの使い方 192, 199 ストアド プロシージャ呼び出しでサポートされる 機能 200 P Parent 代名詞 28 PB.INI ファイル UserHelpPrefix 169 トランザクション オブジェクト値の読み込み 182 PB_FOP_SUPPRESSLOG 環境変数 564 PB_HEAP_LOGFILE_OVERWRITE 環境変数 52 PB_HEAP_LOGFILENAME 環境変数 52 PB_POOL_THRESHOLD 環境変数 51 PBDOM クラス、概要 244 PBD ファイル DLL ファイルとの比較 834 ウィンドウ ActiveX 759 ウィンドウ プラグイン 737 概要 834 作成 845 テスト 846 904 含まれるリソース 838 例 841 pbejbclient110.pbd 658 pbejbclient110.pbx 658 pbjvm110.dll、保存場所 879 PBOnFatalError 環境変数 521 PBRollbackOnRTError 環境変数 521 PBRXnn.OCX インストール場所 750 解説 749 クライアント ワークステーション 774 PBRXSnn.OCX インストール場所 750 解説 749 登録 750 PBR ファイル 838 ウィンドウ ActiveX 758 ウィンドウ プラグイン 736 pbsoapclient110.pbx 697 PBUSR0nn.HPJ ファイル 166 pbwsclient110.pbx 697 PBX、インポート 260, 696 Pcode、実行アプリケーション 832 PipeEnd イベント 320 pipeline システム オブジェクト 320 PipeMeter イベント 320 PipeStart イベント 320 PostEvent 関数 477 Post 関数 476 PowerBuilder 実行時 DLL 847 実行システム 834 パイプライン エラー データウィンドウ 335 PowerBuilder Application Server Plug-in 499 PowerBuilder.Application CreateObject 関数 447 GenerateGUID 関数 450 GenerateRegFile 関数 452 GenerateTypeLib 関数 455 概要 421, 428, 445 関数 447 名前の変更 423, 433 プロパティ 446 ユーザ オブジェクト 428 PowerBuilder 索引 例外コード 459 PowerBuilder イベントの発生 477 PowerBuilder ウィンドウ ActiveX 683 PowerBuilder オートメーション サーバ CLSID 435 GUID 444 PowerBuilder アプリケーション 421 Visual Basic クライアント 427, 432 エラー処理 427 オブジェクトのランタイム ライブラリ 424, 429 概要 418 クライアント アプリケーション 419 クライアント コード 426, 430, 434 タイプ ライブラリ 425, 439 名前付きサーバ 423, 433 名前付きサーバの登録 433 配布 440, 443 プログラム可能なオブジェクト 418 プログラム識別子 425, 427, 435 未登録のユーザ オブジェクト 428 ユーザ オブジェクトの登録 420, 423, 425 用途 419 ランタイム オーバーヘッド 419 例外コード 459 レジストリ 435 レジストリ更新ファイルのサンプル 460 PowerBuilder 初期設定ファイル、トランザクショ ン オブジェクト値の読み込み 182 PowerBuilder セキュア ウィンドウ プラグイン 683 PowerBuilder 単位系(PBU)と拡張コントロール プロパティ 349 PowerBuilder の ADO Recordset 631 PowerBuilder 標準ウィンドウ プラグイン 683 PowerBuilder ランタイム パッケージャ 859 PowerScript 関数 JavaScript での呼び出し 767 VBScript での呼び出し 768 ウィンドウ ActiveX 766 PowerScript ドット表記、ストアド プロシージャ 呼び出しのための使い方 197 Powersoft データベース インタフェース インストール 847 アプリケーション テクニック ストアド プロシージャ呼び出しでサポートさ れる機能 199 Powersoft レポート(PSR) 711 PrintCancel 関数 803 PrintClose 関数 803 ProfileString 関数 概要 182, 809 スクリプト記述 182 PropertyChanged イベント 394 PropertyRequestEdit イベント 393 PSR ファイル 作成 715 データウィンドウ プラグイン 711 R REF キーワード 383 RegEdit ユーティリティ、サポートされているバー ブの取得 399 RegistryGet 関数 810 RegistrySet 関数 810 REGSVR32.EXE 751 ReleaseConnectionOption DBParm 527 RemoteHotLinkStart DDE イベント 346 RemoteHotLinkStop DDE イベント 346 RemoteRequest DDE イベント 346 RemoteSend DDE イベント 346 Repair 関数 320, 336 RLE ファイル リソースとしての配布 837 リソース ファイルでの命名 839 ROLLBACK 文 AutoCommit の設定 179 UseContextObject 518 概要 178 デフォルト以外のトランザクション オブジェ クト 186 RowsInError プロパティ(データ パイプライン) 320, 330 RowsRead プロパティ(データ パイプライン) 320, 330 RowsWritten プロパティ(データ パイプライン) 320, 330 RPCFUNC キーワード 905 索引 概要 193 スクリプト記述 RTF 287 Run 関数 507 194 S Save 関数(OLE) 406 SaveAs 関数(OLE) 364, 406 Secure Sockets Layer プロバイダ サービス 480 Send 関数 476 ServerName プロパティ(トランザクション オブジェ クト) 概要 174 データベース インタフェースごとのリスト 177 SetAbort メソッド 520 SetAutomationLocale 関数 395 SetChanges 関数 529 SetColumn 関数 158 SetComplete メソッド 520 SetFullState 関数 529 SetItem 関数 159 SetMicroHelp 関数 78 SetOptions メソッド、Web サービス プロキシ 705 SetOverLayPicture 関数 156 SetProfileString 関数 809 SetTransPool 関数 189 SOAP 大文字と小文字の区別 701 サーバへの接続 705 例外処理 707 SOAPConnection オブジェクト 697 SoapException オブジェクト 697 Solaris 印刷、設定 560 SQL Anywhere MobiLink 同期 204 ストアド プロシージャ呼び出しでサポートされる 機能 202 データ ソース 872 SQL Server、ストアド プロシージャの呼び出し 201 SQLCA SQLCA からのユーザ オブジェクトの継承 191, 196 SQLCA のプロパティとしてのストアド プロシー 906 ジャの呼び出し 197 アプリケーション ペインタ プロパティ シート での設定 196 インスタンスの作成と破棄の禁止 185 エラー処理 188 概要 174, 180 ストアド プロシージャ呼び出しのためのカスタ マイズ 190 データベース インタフェースごとのプロパティ のリスト 177 デフォルトのグローバル変数の型の指定 195 プロパティの記述 174 プロパティへの値の設定 181 SQLCode プロパティ(トランザクション オブジェ クト) 概要 174, 188 スクリプト記述 189 データベース インタフェースごとのリスト 177 SQLDBCode プロパティ(トランザクション オブ ジェクト) 概要 174, 189 スクリプト記述 189 データベース インタフェースごとのリスト 177 SQLErrText プロパティ(トランザクション オブ ジェクト) 概要 174, 189 スクリプト記述 189 データベース インタフェースごとのリスト 177 SQLNRows プロパティ(トランザクション オブ ジェクト) 概要 174 データベース インタフェースごとのリスト 177 SQLReturnData プロパティ(トランザクション オ ブジェクト) 概要 174 データベース インタフェースごとのリスト 177 SQLSTATE エラー番号の省略 336 SQL 文 PowerBuilder 索引 SQL 文のセミコロンでの終了 181, 183 エラー処理 188 トランザクション オブジェクトの指定 186 トランザクション処理 179 SQL 文の後のエラー処理 188 SQL 文の終止符のセミコロン 181, 183 SSL EAServer との接続 603 コールバック 612 プロバイダ オブジェクト 609 プロバイダ サービス 480 プロパティ 606 SSLCallback オブジェクトの使い方 612 SSLServiceProvider オブジェクト インスタンスの作成 609 使い方 605 Start 関数 320, 328, 507 Stop 関数 508 SUBROUTINE 宣言 概要 193 スクリプト記述 194 Super 代名詞 32 Sybase Adaptive Server Enterprise データベース イ ンタフェースのプロパティ(トランザク ション オブジェクト) 182 Sybase EAServer プロファイル EAServer プロファイル ダイアログボックス 504 Sybase SQL Anywhere、ストアド プロシージャの 呼び出し時にサポートする機能 202 Sybase System 10 と System 11 ストアド プロシージャの呼び出し 201 Syntax プロパティ(データ パイプライン) 320 SystemError イベント、スクリプト作成 600 T TabularResults、PowerBuilder での使い方 535 Tag 属性、マイクロヘルプの使い方 78 This 代名詞 27 thread.safe プロパティ 508 TransactionServer コンテキスト オブジェクト COM+ 632, 636 EAServer 518, 544 アプリケーション テクニック TriggerEvent 関数 477 TriggerPBEvent 関数 JavaScript 771 VBScript 771 U Unicode EAServer 接続キャッシュ 527 URL ウィンドウ プラグイン 742 データウィンドウ プラグイン 718 UseContextObject DBParm 521 UserID プロパティ(トランザクション オブジェク ト) 概要 174 データベース インタフェースごとのリスト 177 USING TransactionObject 句 CONNECT 文 183 DISCONNECT 文 184 概要 186 V VBScript InvokePBFunction 関数 770 PowerScript 関数の呼び出し 768 TriggerPBEvent 関数 771 ウィンドウ ActiveX のイベント ハンドラ 766 ユーザ イベントの呼び出し 771 ユーザ定義関数の呼び出し 770 Visual Basic OLE クライアント 427, 432 Voluntary Product Accessibility Template(VPAT を 参照) VPAT 796 W WCAG(Web Content Accessibility Guidelines) 790 907 索引 Web Content Accessibility Guidelines(WCAG を参照) WebLogic のサポート(PowerBuilder Application Server Plug-in) 499 WebSphere のサポート(PowerBuilder Application Server Plug-in) 499 Web アプリケーションの設計 724 Web サーバ ウィンドウ ActiveX 774 データウィンドウ プラグイン 718 Web サービス EasySoap エンジン 695 .NET エンジン 693 PowerScript クライアント 691 概要 684 コンポーネントのエクスポーズ 551 サービスの作成 692 プロキシ オブジェクト 698 メソッドの起動 707 例外処理 707 Web ブラウザ プラグインの互換性 712, 725 プラグインの動作 712, 725 Windows イベント イベント発生 476 処理 478 Windows メッセージ、送信 474 WMF ファイル リソースとしての配布 837 リソース ファイルでの命名 839 Word 97 オートメーション 386 WordBasic ステートメント 384 WSDL Web サービス プロキシに対する選択 698 概要 692 ア アーキテクチャ J2EE 497 アイコン、配布 837 アクセサ メソッド(COM オブジェクト インタフェー スへの追加) 624 アクセシビリティ 機能 787 908 データウィンドウのサポート 794 テスト 796 必要な DLL 867 値、引数の受け渡し 35 EAServer 539 アプリケーション MDI 71 外部ファイルからのトランザクション オブジェ クト値の読み込み 182 実行 846 実行のトレース 846 多言語 779 データベース ストアド プロシージャの呼び出 し 190 データベース トランザクションのプール 189 配布 831 ユーザ オブジェクトにストアド プロシージャ を実行させるスクリプト 197 ローカライズ 779, 786 アプリケーション、クライアント 構築 651 配布 601 アプリケーション、サーバ COM/COM+ コンポーネントの構築 637 EAServer コンポーネントの構築 501 アプリケーション環境設定、格納 807 アプリケーション管理 アプリケーション管理を容易にする動的ライブ ラリの使い方 836 アプリケーション管理を容易にするリソースの パッケージ化 837 更新された PowerBuilder ランタイム DLL の提 供 847 アプリケーションの実行版 コンパイル オプション 832 テスト 846 トレース 846 パッケージ化モデルの実装 845 パッケージ化モデルの選択 841 パッケージに含まれる要素 833 アプリケーションのテスト 実行のトレース 846 実行版 846 PowerBuilder 索引 アプリケーションのパッケージ化 コンパイル オプション 832 実行版の処理 833 テスト 846 モデルの実装 845 モデルの選択 841 アプリケーションのユーザ、コンピュータ環境 設定 847 アプリケーション ペインタ アプリケーション プロパティ シート、変数の 型プロパティ ページを使用 196 デフォルトのグローバル変数型の変更 195 アンビエント プロパティ 367 イ 位置、ウィンドウ 94 位置ポインタ 54 イベント DDE 344 イベント発生 476, 477 グラフ コントロール 276 先祖からの戻り値 33 先祖の呼び出し 32 データ パイプライン 320 ドラッグ アンド ドロップ 163 引数の受け渡し 35 呼び出し 477 イベント発生 476, 477 イベント ハンドラ PowerBuilder ウィンドウ ActiveX JavaScript 765 VBScript 766 印刷 EAServer コンポーネントのデータストア 558 Solaris 559 UNIX 559 印刷カーソル 801, 803 印刷領域 801 概要 799 関数 799 行間隔 805 アプリケーション テクニック 高度な印刷技法 804 ジョブ 801 測定単位 801 タブ 802 停止 803 描画オブジェクト 805 印刷カーソル 801 印刷領域 801 インスタンス、ウィンドウ 参照変数 93 配列 94 インスタンス プーリング 512 インスタンス変数 アクセス 30 名前の重複 32 インストール後のプラグインの移動 714, 728 インターネット サービス 480 インタフェース定義言語(IDL:Interface Definition Language) 537 インデックス、ウィンドウ配列 94 ウ ウィザード COM/COM+ コンポーネント 618 EAServer コンポーネント 502 EAServer プロキシ オブジェクト 575 EJB プロキシ オブジェクト 661 ウィンドウ MDI アプリケーション 72, 74, 76 実行中の型の選択 37 データ型として定義 91 データ パイプラインの制御 321 表示 91 ウィンドウ ActiveX CLASSID 値の検索 760 CODEBASE 属性 760 HTML の作成 760 Object 要素 760 Param 構成要素 761 PowerScript 関数 766 Web サーバ 774 909 索引 アプリケーションのアイデア 748 イベント 773 イベント ハンドラ 764 インストール場所 750 ウィンドウの作成 752 外部リソース 755 概要 747 既存アプリケーションの変換 756 クライアント側のスクリプト 764 クライアント ワークステーション ソフトウェア 774 サポートされるブラウザ 748 セキュリティ 749 データベース アクセス 755 テスト 757 動的ライブラリのリソース ファイル 758 登録 750 必須 DLL 752 表示 775 ユーザ定義関数 768 要件 749 ウィンドウ ActiveX の DISPLAYERRORS 属性 761 ウィンドウ ActiveX の LIBLIST 属性 761 ウィンドウ ActiveX の Object 構成要素 760 ウィンドウ ActiveX の Param 構成要素 761 ウィンドウ ActiveX の PBAPPLICATION 属性 761 ウィンドウ ActiveX の PBWINDOW 属性 761 ウィンドウ ActiveX のクライアント側のスクリプト 764 ウィンドウ インスタンスを複数開く 91 ウィンドウ プラグイン HTML 文書 725 アプリケーション設計 731 アプリケーションのアイデア 724 ウィンドウ管理 731 オブジェクト 731 開発 729 外部リソース 733 概要 722 既存アプリケーションの変換 734 クライアント ワークステーション ソフトウェア 743 サーバ上のファイル 742 910 サポートされるブラウザ 723 スクリプト 732 セキュリティ 724 セキュリティ バージョン 723, 728 チャイルド ウィンドウ 734 データベース アクセス 733 テスト 735 動的ライブラリ 736 動的ライブラリのリソース ファイル 736 配布コンポーネント 730 表示 744 標準バージョンの概要 723 ブラウザ / サーバ間対話 725 変数 732 要件 727 ウィンドウ ペインタ、コントロールのドラッグ モードの指定 162 埋め込み SQL でのエラー処理 188 運動障害 789 エ エクステンション PowerBuilder で使用 260 エクステンション ファイル pbsoapclient110.pbx 697 pbwsclient110.pbx 696 オブジェクトのインポート 696 エラー EAServer サーバ ログへの書き込み 558 Windows ログへの書き込み 627 データ パイプライン実行時 317, 335 例外処理 39, 677 ログへの書き込み 480 エラー イベントのスクリプト記述 EAServer クライアント 599 OLE サーバ 390 エラー処理 OLE 390 SQL 文の後 188 エラー ロギング サービス COM+ 627 EAServer 558 PowerBuilder 索引 概要 480 エリアス、XML メソッド 701 オ オートメーション、OLE 417 オートメーション サーバ PowerBuilder COM サーバとの比較 621 概要 418 オートメーション サーバ ウィザード 425 オートメーションで使用する言語 395 オブジェクト DLL ファイル 834 PBD ファイル 834 PowerBuilder の OLE オートメーション 418 オブジェクトの代名詞 27 共有 505 子孫オブジェクトのインスタンス化 36 子孫オブジェクトの参照 97 実行中の型の選択 36 実行ファイル 834 先祖の関数とイベントの呼び出し 32 動的に参照されるオブジェクトの配布 836, 839 名前の重複 31 オブジェクト、プロキシ EJB に対して生成 658 生成 574, 575 オブジェクト指向概念としての代行 22 オブジェクト指向プログラミング、用語 13 オブジェクトの挿入 ダイアログボックス 350 オペレーティング システム、環境設定 847 親オブジェクト 25 カ 外部関数 EAServer コンポーネント 474 宣言 468 使い方 467 データベース ストアド プロシージャ呼び出し のための使い方 193 アプリケーション テクニック 外部ファイル、トランザクション オブジェクト値 の読み込み 182 外部リソース ウィンドウ ActiveX 758 ウィンドウ プラグイン 733 データウィンドウ プラグイン 716 学習障害 789 拡張属性の概要 317 カスタム クラス ユーザ オブジェクト COM/COM+ コンポーネント 618 EAServer コンポーネント 501 オートメーション サーバ 418 典型的な用途 14 カスタム フレーム MDI アプリケーション 73 サイズ変更 84 カッコと OLE オートメーション 383 カプセル化 17, 30 ガベージ コレクション 49 可変長ウィンドウ配列 94 環境変数 PB_FOP_SUPPRESSLOG 564 PB_HEAP_LOGFILE_OVERWRITE 52 PB_HEAP_LOGFILENAME 52 PB_POOL_THRESHOLD 51 PBOnFatalError 521 PBRollbackOnRTError 521 関数 上書き 35 グラフ 276 先祖の呼び出し 32 動的 37 引数の受け渡し 35 関数、PowerScript AddColumn 158 AddItem 145, 149, 150, 153 AddLargePicture 155 AddPicture 146, 151 AddSmallPicture 155 AddStatePicture 155, 156 DDE 344 DeleteLargePicture 157 DeleteLargePictures 157 DeletePicture 146 DeleteSmallPicture 157 911 索引 DeleteSmallPictures 157 DeleteStatePicture 157 DeleteStatePictures 157 InsertItem 122, 145, 149, 150, 153 InsertItemFirst 122 InsertItemLast 122 InsertItemSort 122 MAPI 463 SetColumn 158 SetItem 159 SetOverlayPicture 156 データ パイプライン 320 ドラッグ アンド ドロップ 164 ファイル操作 53 ユーティリティ 474 関数、外部 概要 468 宣言 469 データベース ストアド プロシージャ呼び出しのた めの使い方 193 引数の受け渡し 471 関数の多重定義 20 キ キーワード サービス 480 行、テーブル間のパイプライン処理 行間隔、設定 805 共有オブジェクト、概要 594 共有コンポーネント 505 315 ク クライアント アプリケーション COM/COM+ の構築 651 EAServer の構築 569 PowerBuilder.Application の要件 430 PowerBuilder サーバの要件 434 オートメーション 419, 426 同期 207 配布 601 クライアント管理のトランザクション 588 912 クライアント コンピュータの環境設定 ウィンドウ ActiveX 774 ウィンドウ プラグイン 743 データウィンドウ プラグイン 719 配布 847 クライアント領域 MDI アプリケーション 73 サイズ変更 84 クラス、PBDOM 概要 244 クラス ID(CLSID を参照) グラフ PowerScript 関数 276 ウィンドウ内での系列の作成 277 ウィンドウ内でのデータの作成 276 ウィンドウ内でのデータ ポイントの作成 277 実行中の修正 279 情報取得 282, 284 データの保存 283 データ表示の修正 283 データ プロパティ 281 内部表現 280 プロパティ 280 グラフ関数 データ アクセス 281 データについての情報取得 282, 284 データの保存 283 データ表示の修正 283 グラフでのデータ保存 283 グラフの grAxis サブオブジェクト 280 グラフの grDispAttr サブオブジェクト 280 クリップボードのアプリケーションでの使い方 363 グローバル外部関数 468 グローバル変数 ウィンドウ 91 名前の重複 32 グローバル変数型、デフォルト 195 ケ 継承 階層構造 95 PowerBuilder 索引 サービス オブジェクト 15 先祖オブジェクトの仮想関数 16 継承したオブジェクト間の多相性 19 系列、グラフ ウィンドウ内での作成 277 ウィンドウ内での識別 278 ウィンドウ内でのデータ ポイントの追加 277 結果集合 EAServer での受け渡し 534 PowerBuilder によるストアド プロシージャの 処理 190, 200 トランザクション サーバ環境での受け渡し 629 言語と OLE オートメーション 395 検証、EAServer コンポーネント 541 コ 更新、EAServer コンポーネント内 529 更新ステータス、分散アプリケーション内 529 項目の追加 リストビューへの 153 リストボックスへの 144, 149, 150 コード セット EAServer Manager での変更 567 Management Console での変更 567 国際化アプリケーション 設計 779 コロン(スコープ演算子) 32 コンテキスト情報 480 コンテキスト情報サービス 480 コントロール 種類 364 タブ ページ 104 ツリービュー 117 ドラッグ アンド ドロップ 161 ドロップダウン ピクチャ リストボックス 146, 149, 150 ドロップダウン リストボックス 149 ピクチャ リストボックス 144, 145, 146 マイクロヘルプの使い方 78 アプリケーション テクニック リストビュー 152, 154, 155, 157 リストボックス 144 コンパイル オプション 832 スクリプトの記述 53 チェックされない OLE 構文 381 コンポーネント オブジェクト モデル(COM を参 照) コンポーネント管理のトランザクション 588 サ サーバ、MobiLink 同期 204 サーバ データベース、環境設定 847 サーバ アプリケーション、OLE 347 サーバ コンピュータ、環境設定 847 サービス オブジェクト 480 再利用可能な動的ライブラリ 836 削除 リストビュー ピクチャ 157 リストボックス ピクチャ 146 サブスクリプション 概要 207 複数サーバとの同期 236 サブルーチン、データベース ストアド プロシー ジャ呼び出しのための使い方 193 参照 EAServer コンポーネントでの引数渡し 538 オブジェクトの動的な参照 836, 839 引数の受け渡し 35, 383 リソースの動的な参照 838 サンプル、コード 5 シ 視覚障害 788 システム例外ハンドラ 597 子孫オブジェクト エンティティの参照 97 概要 36 定義 191 実行 913 索引 アプリケーションの起動 846 グラフへのアクセス 279 データ パイプライン 328 トレース機能 846 ライブラリ リスト 834 実行アプリケーションのトレース 846 実行ファイル 概要 833 作成 845 スタンドアロン 841 テスト 846 含まれるリソース 838 例 841 [自動的なデマケーション / 不活性化]設定 520 従属関係 23 障害者差別禁止法 791 ショートカット キー、MDI アプリケーション 89 初期設定ファイル アクセス 807 トランザクション オブジェクト値の読み込み 182 ジョブ、印刷 801 処理効率 概要 30, 389 リソースの配布モデルの影響 836, 838 リストボックス ピクチャの追加 146, 151 スコープ演算子 32 スタンドアロン実行ファイル 841 ステートメント、WordBasic 内(OLE) 384 ストアド プロシージャ、アプリケーションでの呼 び出し DBMS 機能のサポート 199 ORACLE7 の例 192 ORACLE の例 199 SQLCA に対するデフォルトのグローバル変数 の型の指定 195 アプリケーションのスクリプト記述 197 外部関数としての宣言 193 概要 190 基本的な手順 191 結果集合、PowerBuilder による処理 190, 200 標準クラス ユーザ オブジェクトの定義 192 ユーザ オブジェクトの保存 195 ストアド プロシージャ呼び出しでサポートされる DBMS 機能 199 ストリーム モード 53 スペル チェック(リッチテキスト エディット コン トロール) 302 セ ス スクリプト OLE オートメーション 396 OLE オブジェクトの操作 380 OLE カラムのアクティブ化 399 グラフの修正 279 同期 206 ブラウザからの OLE 情報 401 リストビュー カラム値の設定 159 リストビュー カラムの追加 158 リストビュー項目の削除 157 リストビュー項目の追加 153 リストビュー ピクチャの削除 157 リストビュー ピクチャの追加 155 リストボックス項目の追加 145, 149, 150 914 静的呼び出し 22 セキュリティ ウィンドウ ActiveX 749 ウィンドウ プラグイン 724 データウィンドウ プラグイン 712 セキュリティ ウィンドウ ActiveX 749 セキュリティ ウィンドウ プラグイン 概要 723 使い方 728 接続 EAServer 571 EJB サーバ 671 OLE オブジェクト 371 トランザクション オブジェクト 183 複数のデータベースの使用 185 接続オブジェクト ウィザード 573 接続キャッシュ PowerBuilder 索引 プロキシの使い方 526 利点 524 宣言 外部関数 468 定数 30 トランザクション オブジェクト 先祖オブジェクト ウィンドウ 95 概要 36 関数とイベントの呼び出し 32 先祖スクリプトからの戻り値 33 185 削除 102 スクリプトで閉じる 111 スクリプトで開く 111 スクリプト内のコントロール 110 定義 99 独立したユーザ オブジェク 100 表示順序の変更 102 プロパティ シート 104 タブ ページの配列の管理 111 チ 聴覚障害 ソ 挿入可能 OLE オブジェクト 788 349 ツ タ ターゲットとなるコントロールのドラッグ アン ド ドロップ 161 代名詞 27 多相性(ポリモフィズム) 18 タブ コントロール Control プロパティ配列 111 CreateOnDemand プロパティ 113 イベント 114 親 107 概要 99 タブの位置 105 タブ ページの管理 102 タブ ページの種類 100 タブ ラベル 106 定義 99 ドット表記 107 表示形態 104 プロパティ シート 104 タブ ページ イベント 114 埋め込み 100 オブジェクトの参照 111 親 107 アプリケーション テクニック 通信エラー、処理 596 ツールバー、MDI アプリケーション内 ツリービュー コントロール 概要 117 例 139 74 テ 定数 30 データ ウィンドウのグラフとの関連付け 276 ウィンドウのグラフに追加 277 グラフでの保存 283 データ ソース間のパイプライン処理 315 同期 203 データウィンドウ、OLE OLE オブジェクトの関数 397 オートメーション 396, 398 データウィンドウ Web コントロール ActiveX 687 データウィンドウ オブジェクト 概要 287 動的な参照 836, 839 ドット表記 29 リソース ファイルへの組み込み 841 915 索引 データウィンドウ関数 GetChanges 529 GetFullState 529 GetStateStatus 529 SetChanges 529 SetFullState 529 データウィンドウ コントロール データ共有 305 データ パイプライン エラーの処理 322, 328, 335 リッチテキストと関数 290 データウィンドウ式、最適化 38 データウィンドウの同期 529 データウィンドウ プラグイン HTML 文書 712 OLE オブジェクト 716 PSR の作成 715 Web サーバ 718 開発 714 外部リソース 716 概要 711 クライアント ワークステーション ソフトウェア 719 サーバ上のファイル 718 セキュリティ 712 配布コンポーネント 714 ブラウザ / サーバ間の対話 712 要件 713 リッチテキスト提示様式 716 データ型 Any 388 COM/COM+ 625 EAServer 576 XML 702 ウィンドウ 95 ウィンドウの定義 91 データ共有、リッチテキスト エディット コントロー ル 305 データストア オブジェクト EAServer コンポーネントの使い方 523 ツリービューの値の設定 140 標準クラス ユーザ オブジェクト 24 データ ソース SQL Anywhere 872 配布 872 916 データ ソース間のデータ転送 315 データ パイプライン PowerBuilder 開発環境での使い方 316 SQLSTATE エラー番号の省略 336 アプリケーションでの使い方 316 エラー行の修復 336 エラー行の処理 335 エラー行の廃棄 338 エラー処理のデータウィンドウ コントロール 322, 328, 335 概要 316 行解析結果の表示 330 更新のコミット 334 実行時の後処理 339 実行時の処理の準備 325 実行の開始 328 実行の監視 330 実行のキャンセル 332 制御用のウィンドウの提供 321 特性の指定 317 パイプライン処理の指定 325 ユーザ オブジェクトのサポート 320, 325, 330, 339 例 315 データ パイプラインの転送先テーブル 317 データ パイプラインの転送元テーブル 317 データ パイプライン ペインタ 対話的な使い方 316 データ パイプラインの定義 316, 317 データ パイプラインへのコミット 317, 334 データベース COM コンポーネントからのアクセス 628 EAServer コンポーネントからのアクセス 523 OLE データの保存 365 アプリケーションでのストアド プロシージャの 呼び出し 190 インタフェースのプロパティ(トランザクショ ン オブジェクト) 177 環境設定 847 接続 183 接続解除 184 データ パイプラインの転送先 325, 339 データ パイプラインの転送元 325, 339 PowerBuilder 索引 データベース間のテーブルの移行 315 トランザクションのプール 189 複数のデータベースへの接続 185 プロファイル、接続プロパティ 174 リッチテキスト 288 データベース インタフェース インストール 847 環境設定 847 プロパティ(トランザクション オブジェク ト) 177 データベースからの接続解除 184 データベース ストアド プロシージャ、データ パ イプラインの転送元 317 データベース トランザクションのプール 189 データベース内またはデータベース間のテーブ ルの移行 315 テーブル データ パイプラインの転送先 317 データ パイプラインの転送元 317 データベース内またはデータベース間の移行 315 テキスト ファイル 関数 53 読み書き 53 デザイン、ユーザ インタフェース 786 デバッグ 実行のトレース 846 実行ファイル 846 デフォルト以外のトランザクション オブジェク ト SQL 文での指定 186 値の設定 185 概要 185 作成 185 破棄 187 デフォルト以外のトランザクション オブジェク トの作成 185 デフォルト グローバル変数型 195 デフォルトのトランザクション オブジェクト (SQLCA) 174, 180 電子メール システム、アクセス 463 アプリケーション テクニック ト 同期(MobiLink 同期を参照) 同期サーバ 204 統合データベース 204 同時実行コンポーネント プロパティ 508 動的 SQL でのエラー処理 188 動的関数呼び出し 37 動的参照 オブジェクト 836, 839 リソース 838 動的呼び出し 20 動的ライブラリ PowerBuilder ウィンドウ ActiveX 759 PowerBuilder ウィンドウ プラグイン 736 概要 834 独立関係 23 独立したオブジェクト間の多相性 18 ドット表記 概要 25 ストアド プロシージャ呼び出しのための PowerScript の使い方 197 ドラッグ アンド ドロップ アイコンの指定 163 関数 164 自動ドラッグ モード 161 使い方 161 ドラッグ コントロールの識別 164 プロパティ 162 トランザクション オブジェクト SQLCA 174, 180 値の設定 181 エラー処理 188 外部ファイルからの値の読み込み 182 概要 173 組み込みシステム型 193 指定 186 ストアド プロシージャ呼び出しのための使い 方 190 デフォルト 174, 180 デフォルト以外、SQL 文での指定 186 デフォルト以外、作成 185 デフォルト以外、トランザクション オブジェ クトの値の設定 185 917 索引 デフォルト以外、破棄 187 複数のデータベース接続 185 リモート プロシージャの呼び出しのテクニック 190 トランザクション オブジェクトのインスタンス化 185 トランザクション オブジェクトのプロパティ 値の設定 181, 185 外部ファイルからの値の読み込み 182 概要 174 記述 174 ストアド プロシージャの呼び出し 197 データベース インタフェースごとのリスト 177 トランザクション コンテキスト サービス 632 トランザクション処理 COM+ のサポート 632 COM クライアントからの制御 654 EAServer 516 SQL 文 179 エラー処理 188 概要 178 データベース トランザクションのプール 189 トランザクション プール 189 ドロップダウン ピクチャ リストボックス コントロー ル 概要 149 項目の追加 149 ピクチャの削除 146 ピクチャの追加 150 例 147 ドロップダウン リストボックス コントロール 概要 149 項目の追加 149 例 147 ナ 内容の種類 名前の修飾 918 725 25 ニ 入力条件則、リッチテキスト 入力フィールド 概要 304 スクリプト 304 テキストへの挿入 288 編集 313 認知障害 789 289 ネ ネットワーク、ユーザ アクセスの設定 847 ハ バイナリ ファイルの読み書き 53 配布 EAServer コンポーネント 565 OLE とレジストリ 440, 443 概要 831 クライアント アプリケーション 601 ランタイム パッケージャ 859 配布 DLL、PowerBuilder 847 パイプライン エラー データウィンドウ 335 パイプライン オブジェクト データ パイプライン ペインタでの定義 317 配布 328 パイプライン処理の指定 325 配列 EAServer コンポーネントでの受け渡し 538 ウィンドウ インスタンスの 94 配列の 705 パッケージ、COM+ 639 パッケージ化アプリケーションのモデル 概要 841 作成方法 845 テスト 846 パフォーマンス 概要 38 コンパイル時間の短縮 53 変数のスコープ 53 PowerBuilder 索引 パブリケーション 207, 231 パブリック アクセス 30 汎用的スクリプト記述テクニック 108 ヒ 引数 EAServer コンポーネントでの受け渡し 538 OLE 383 受け渡し方法 35 引数の受け渡し EAServer 538 OLE 383 概要 35 ピクチャ、リソースとしての配布 837 ピクチャの高さ 145, 150, 154, 155 ピクチャの追加 リストビューへの 154, 155 リストボックスへの 145, 146, 150 ピクチャの幅 145, 150, 154, 155 ピクチャ マスク 145, 150, 154, 155 ピクチャ リストボックス コントロール 概要 144 項目の追加 144, 145 ピクチャの削除 146 例 147 ビジネス ロジック、概要 495 非同期処理 EAServer 592 描画オブジェクト、印刷 805 表記規則 xx 標準クラス データ型の選択 ダイアログボックス 193 フ ファイアウォール設定 695 ファイル DLL 834 PBD 834 PBR 838 外部、ファイルからのトランザクション オブ ジェクト値の読み込み 182 アプリケーション テクニック 実行時 866 実行ファイル 833 リソース 837 リッチテキスト 293 ファイル ポインタ 54 フォーム様式の作成 812 フォント、定義 804 複数データベース、アクセス 185 プライベート アクセス 30 プロキシ サーバ 695 プロキシ オブジェクト Web サービスに対する生成 698 生成 574, 575 プログラム可能なオブジェクト 418 プログラム識別子 427, 435 プロジェクト オブジェクト、作成 845 プロジェクト ペインタ オートメーション オブジェクトの構築 424, 429 配布アプリケーションのパッケージ化における 使い方 845 プロテクト アクセス 30 プロパティ データ パイプライン 320 ドラッグ アンド ドロップ 162 プロパティ、トランザクション オブジェクト 値の設定 181, 185 外部ファイルからの値の読み込み 182 概要 174 記述 174 ストアド プロシージャの呼び出し 197 データベース インタフェースごとのリスト 177 プロパティの変更通知 393 プロファイル、データベース 174 分散アプリケーション アーキテクチャ 495 エラー処理 596 データストア 523 データベース アクセス 523 データベース更新の実行 529 919 索引 ヘ ページ余白(リッチテキスト エディット コントロー ル) 309 ヘルプ PBUSER110.HLP の名前変更 169 UserHelpFile 169 UserHelpPrefix 169 開発者への提供 167 新規ユーザ ヘルプ ファイル名の指定 169 デフォルトの接頭辞の変更 169 ユーザ定義関数のための作成 168 変数 ウィンドウ型の変数 95 型のない 388 宣言、ウィンドウの型 93 デフォルトのグローバル変数 195 トランザクション オブジェクトのための宣言 185 パフォーマンスへの影響 53 変数のアクセサ メソッド(COM オブジェクト インタ フェースへの追加) 624 変数の型プロパティ ページ(アプリケーション ペイ ンタ プロパティ シート) 196 ホ ポインタ、リソースとして配布 837 ポイント アンド クリック、グラフ内 283 ポンド記号、EAServer コンポーネント 567 マ マイクロヘルプの MDI アプリケーションでの使い方 77 マシン コード 832 メ メール関連のオブジェクトと構造体 メール システム、アクセス 463 メール マージのリッチテキストの例 920 463 306 メッセージ オブジェクト 概要 478 プロパティ 478 メニュー MDI アプリケーション 73, 74 OLE 359 マージ 359 メニュー項目に対するマイクロヘルプの提供 メニュー ペインタでのマイクロヘルプの提供 メモリの管理 49 78 78 ユ ユーザ、MobiLink 207, 234 ユーザ イベント、ウィンドウ ActiveX JavaScript での呼び出し 771 VBScript での呼び出し 771 ユーザ インタフェース、国際的な配布のためのデ ザイン 786 ユーザ オブジェクト COM+ コンポーネント 617 Control プロパティ配列 112 EAServer コンポーネント 501 OLE の登録 425 OLE レジストリ 435 PowerBuilder.Application 428 オートメーション サーバ 420, 423 概要 99 構造体としての使い方 24 実行中の型の選択 37 タイプ ライブラリ 425, 439, 455 データ パイプライン処理のサポートのための使 い方 325, 330, 339 データベース ストアド プロシージャ呼び出し のための使い方 192 ユーザ オブジェクトの保存 ダイアログボックス 195 ユーザ オブジェクト ペインタ カスタム トランザクション オブジェクトを定 義する使い方 192 データ パイプライン処理をサポートするユーザ オブジェクトの定義 330 PowerBuilder 索引 ユーザ オブジェクトを構造体として使用する構 造体オブジェクト 24 ユーザ定義関数 上書き 19 状況依存ヘルプの作成 168 多重定義 19 ユーザ定義関数、ウィンドウ ActiveX JavaScript での引数 769 JavaScript での呼び出し 769 VBScript での呼び出し 770 ユーザ定義関数の上書き 19, 35 ユーザ定義関数の多重定義 COM ではサポートされない 626 概要 19, 20 ユーザ ヘルプ ボタン 167 ユーティリティ関数 474 ユーロ記号、EAServer コンポーネント 567 ヨ 読み込み専用、引数の受け渡し 35 ラ ライブラリ、動的 834 ライブラリ探索パス、実行アプリケーションで の使用 834 ライブラリ ペインタによるオートメーション オ ブジェクトの構築 424, 429 ライン モード 53 ランタイム パッケージャ 859 リ リストビュー項目 インデックス 152 オーバーレイ ピクチャ インデックス 状態ピクチャ インデックス 152 ピクチャ インデックス 152 ラベル 152 リストビュー コントロール イメージ リスト 154 アプリケーション テクニック 152 概要 152 カラム値の設定 159 カラムの設定 158 カラムの追加 158 項目 152 項目の追加 153 詳細表示 158 ピクチャの削除 157 ピクチャの追加 154, 155 リストボックス コントロール 概要 144 項目の追加 144 例 147 リソース DLL ファイル 836, 838 PBD ファイル 836, 838 ウィンドウ ActiveX 758 ウィンドウ プラグイン 736 概要 837 個別のファイルでの配布 838 実行ファイル 834, 838 テスト 846 動的参照 838 パッケージ化の手順 845 リソース ファイルでの命名 839 例 841 リソース ファイル、作成 839 リソース ファイルでのリソースの探索パス 841 リッチテキスト オブジェクトと書式設定 312 概要 287 作成 288 実装 287 選択 307 ツールバー 292 データウィンドウ プラグインの制約 716 データベース 293 データベースへの保存 288 入力条件則 289 入力フィールド 288 日付フィールド 305 ページ番号 305 921 索引 メール マージ例 306 ユーザ操作 311 用途 287 ワード ラップ 292 リッチテキスト エディット コントロール FileExists イベント 296 LoseFocus イベント 296, 308 Modified プロパティとイベント 296 印刷 310 オブジェクト 303, 312 概要 291 書式設定 303 スクロール 306 スペル チェック 302 設定 292 選択 307 挿入ポイント 307 タブ順序 308 ツールバー 292 データ ソース 305 データベースにテキストを保存する例 294 テキストの挿入 293 入力フィールド 304 日付フィールド 305 ファイル 293, 296 ファイルを開く例 297 フォーカス 308 プレビュー 308 ページ番号 305, 310 ページ余白 309 変更の取り消し 293 編集キー 314 保存 296 保存の例 297 メール マージ例 306 ワード ラップ 292 リッチテキストが使えるワード プロセッサ 288 リッチテキスト 提示様式 523 リッチテキスト提示様式 新しい行 289 スクリプト 290 スクロール 289 922 入力条件則エラー 289 編集キー 314 ユーザ操作 289 リモート ストアド プロシージャ ダイアログボック ス 194 リモート データベース 204 リモート プロシージャの呼び出しのテクニック DBMS 機能のサポート 199 SQLCA に対するデフォルトのグローバル変数 の型の指定 195 アプリケーションのスクリプト記述 197 外部関数としてのストアド プロシージャの宣言 193 概要 191 ストアド プロシージャの結果集合 190, 200 標準クラス ユーザ オブジェクトの定義 192 ユーザ オブジェクトの保存 195 レ 例外、処理 39 EAServer クライアント 596 EJB クライアント 677 Web サービス メソッド 707 レジストリ エントリの作成 439 概要 435 キー 436 クラス情報 400 更新ファイルの作成 452 更新ファイルのサンプル 460 情報の格納 807 ファイルの配置 443 ロ ローカライゼーション 779 ローカル外部関数 469 ログ、EAServer 558 論理的な作業単位 178 PowerBuilder
© Copyright 2024 Paperzz