ビジネスデータカタログ (BDC = Business Data Catalog) を使ってみましょう


環境: Office SharePoint Server 2007 Beta 2 


こんにちは。


今日は、Office Sharepoint Server 2007 からの新機能であるビジネスデータカタログの仕組みについてご紹介します。


まず、この機能についてですが、米国の Office Developer Conference などでご覧になられた方も居られるかもしれませんが、平たく言えば、XML で定義されたデータ接続情報です。しかしながら、その特徴は、単なる "データ接続の仕組み" ではなく、ユーザが指定可能なプロパティや、表示方法、データ間の関係情報、ひいては 利用可能なアクションなど(詳細は後述します)、Sharepoint 上における「振る舞い」も定義されたいわば 「擬似的なアプリケーション」 とお考えください。BDCを一度作成したら、その定義情報をSharepoint 上のどこでも登録して「アプリケーション」のごとく使える、というものですから、(ここのサンプルではせいぜい 2 つの Entity までの簡単な BDC でしか説明しませんが) 現実には、例えば、SAP や Siebel などといったパッケージアプリケーションで使う非常に多数の Entity やそれらの関係・動作などを BDC として定義して、製品が持つ機能の Sharepoint 版のごとく配布(再利用)する、などといった使い方が可能となります。


では、その使い方を実際の XML ソースを見ながら以下にご紹介しましょう。以下は、すべて、Office Sharepoint Server 2007 Beta 2 (TR ではありません) で確認しています。またここでご紹介するデモでは、SQL Server に標準で付属している AdventureWorks のデータベースを使っていますので、そのまま動かしてみたい方は、あらかじめ AdventureWorks と AdventureWorksDW をご準備ください。(できるだけ簡単なサンプルにしましたので、独自にテーブルなどを用意して作成して頂いても結構です。)


■ 単純なサンプル


まずは最も簡単な例からスタートしましょう。
以下の XML ファイルを準備してください。ファイル前半に記載されている接続先のデータベースやログインID (認証方法) は私の環境のまま書いていますので、ご利用される皆さんの環境にあわせて変更してください。(ここでは、Office Sharepoint Server がデフォルトでインストールした SQL Server 2005 Express Edition を使っています。)


<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<LobSystem xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://schemas.microsoft.com/office/2006/03/BusinessDataCatalog BDCMetadata.xsd" Type="Database" Version="1.0.0.0" Name="AdventureWorksDW1" xmlns="http://schemas.microsoft.com/office/2006/03/BusinessDataCatalog">
  <LobSystemInstances>
    <LobSystemInstance Name="AdventureWorksDW1">
      <Properties>
        <Property Name="DatabaseAccessProvider" Type="Microsoft.Office.Server.ApplicationRegistry.SystemSpecific.Db.DbAccessProvider">SqlServer</Property>
        <Property Name="RdbConnection Data Source" Type="System.String">TSMATSUZ21\OFFICESERVERS</Property>
        <Property Name="RdbConnection Initial Catalog" Type="System.String">AdventureWorksDW</Property>
        <Property Name="RdbConnection Integrated Security" Type="System.String">SSPI</Property>
      </Properties>
    </LobSystemInstance>
  </LobSystemInstances>
  <Entities>
    <Entity EstimatedInstanceCount="10000" Name="Part">
      <Properties>
        <Property Name="Title" Type="System.String">PartName</Property>
      </Properties>
      <Identifiers>
        <Identifier TypeName="System.Int32" Name="PartID" />
      </Identifiers>
      <Methods>
        <Method Name="GetParts">
          <Properties>
            <Property Name="RdbCommandText" Type="System.String">
       SELECT
        productname,
        productcode,
        partkey,
        partcode,
        partname,
        reorderpoint,
        inventory,
        dealerprice,
        InventoryComfortLevel
       FROM
        partinformation
      </Property>
            <Property Name="RdbCommandType" Type="System.Data.CommandType, System.Data, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">Text</Property>
          </Properties>
          <Parameters>
            <Parameter Direction="Return" Name="Parts">
              <TypeDescriptor TypeName="System.Data.IDataReader, System.Data, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" IsCollection="true" Name="PartDataReader">
                <TypeDescriptors>
                  <TypeDescriptor TypeName="System.Data.IDataRecord, System.Data, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" Name="PartDataRecord">
                    <TypeDescriptors>
                      <TypeDescriptor TypeName="System.Int32" IdentifierName="PartID" Name="PartKey">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">PartID</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                        <Properties>
                          <Property Name="DisplayByDefault" Type="System.Boolean">false</Property>
                        </Properties>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="PartCode">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">PartCode</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="ProductCode">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">ProductCode</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="PartName">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Name</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                        <Properties>
                          <Property Name="DisplayByDefault" Type="System.Boolean">true</Property>
                        </Properties>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.Int16" Name="ReorderPoint">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Reorder Point</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.Int32" Name="Inventory">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Inventory</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.Int32" Name="InventoryComfortLevel">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Inventory Comfort Level</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                    </TypeDescriptors>
                  </TypeDescriptor>
                </TypeDescriptors>
              </TypeDescriptor>
            </Parameter>
          </Parameters>
          <MethodInstances>
            <MethodInstance Type="Finder" ReturnParameterName="Parts" Name="PartFinderInstance" />
            <MethodInstance Type="SpecificFinder" ReturnParameterName="Parts" Name="PartSpecificFinderInstance" />
          </MethodInstances>
        </Method>
      </Methods>
    </Entity>
  </Entities>
</LobSystem>


では、以下でこの XML を Sharepoint 上に設定していきましょう。まず Sharepoint Central Administration (Sharepoint の管理サイト) を起動し SSP (Sharepoint Shared Service Provider) の管理画面を表示してください。(初期インストール時はどの Sharepoint Web アプリケーションも同じ SSP (SharedService1) を使っていますが、複数の SSP を作成された場合は、使用する SSP の管理画面を起動してください。)
表示したら、[Business Data Catalog] - [Add applicatrion] を選択して、上記の XML ファイルを登録 (アップロード) してみましょう。
エラーなく登録されましたか?エラーが表示された場合は、その内容を見て XML を修正してください。


では、つぎに、登録した BDC を Sharepoint 上で使用します。上記の SSP を利用しているサイト上(どこでも良いです)から、[Site Actions] - [Create] を選択し、[Web Part Page] を選択してください。おなじみの、Web Part を使ったページ作成画面が表示されます。
ページ上で Web Part の追加をおこいますが、種類として、[Business Data List] を選択します。追加後は [Edit] - [Modify Shared Web Part] を選択し、設定用のペインを表示し、この中の [Type] 欄の右にある本のアイコンをクリックして、表示される [Part] のアイテムを選択してください。
これで完了です。ページを表示して [Retrieve Data] をクリックするとデータを検索して Web Part 上に結果が一覧表示されます。


XML のソースの意味ですが、開発者の方なら、長々と記述するより、中身を黙って見て頂いたほうが話が早いかもしれません。簡単にご説明すると、まずこの BDC は、データベースの検索を利用した BDC を定義しています。前半のほうではデータベースへの接続情報を記載しており、以降では、Entity というタグを使って、使用する要素(Entity)を記載しています。Entities というタグの名称からご想像できる通り、実は複数の Entity を設定できます (後ほど複数の Entity を持った例を記載します) が、ここでは、簡単のため 1 つの Entity のみを指定しています。Entity タグの中では、どのような検索をおこない、どのような結果を返すかといった情報を記載しています。


■ Action の追加


では、次に Action を追加していきましょう。ここからは、このブログの添付ファイルをダウンロードして見てください。
AdventureWorksDW_Sample2_Actions.xml にサンプルを添付しました。変更箇所は windiff で見て頂くとわかりますが、99行目以降の 7 行です。


      <Actions>
        <Action Name="Open order form" Position="1" IsOpenedInNewWindow="true" Url="http://testsite/_layouts/formserver.aspx?xsnlocation=http://testsite/formservertemplates/testform.xsn&amp;openin=browser&amp;PartCode={0}" ImageUrl="">
          <ActionParameters>
            <ActionParameter Name="PartCode" Index="0" />
          </ActionParameters>
        </Action>
      </Actions>


PartCode (Return で定義していた Name と同じ名称を使います) を引数として所定の URL に飛ばしているのがわかります。このように指定すると、表示されている1つ1つのデータについて、それぞれ固有の引数を伴って上記の URL にジャンプするアクションへのリンクが追加されますので、上述と同様の方法で登録と動作をさせて確認してみてください。
BDC ではこのように URL をベースとしたアクションの実行が可能で、例えば、InfoPath の Web フォームに所定の引数を渡して飛ばすといった利用方法などが可能です。また、Action を Business Data List とわけて Web Part として配置して関係付けるといった配置方法も可能です。


■ Property を指定する


次に Property を追加していきましょう。本ブログ添付ファイルの AdventureWorksDW_Sample3_Properties.xml にサンプルを添付しました。(変更箇所は windiff で確認してください。)
このように入力用の Parameter を記述すると、Web Part 上の引数の指定欄で、該当の引数を選択してユーザが絞り込むをおこなうことができるようになります。またこのサンプルのように、デフォルトの値(何も指定しない場合の値)も指定することができます。


■ Association を指定する


さいごに Association を追加していきましょう。Entity を複数作成してこの複数の Entity 間の関係を XML に記述すると、Web Part 上でそこで定義した関係 (Association) の通りに2つの Web Part を関係させることができます。本ブログ添付ファイルの AdventureWorksDW_Sample4_Associations.xml にサンプルを添付しました。使い方は以下の通りです。


まず、この XML (BDC のアプリケーション) を上述同様、管理画面から登録してください。つぎに、Web Part の [Business Data List] をページ上に追加し、[Type] として [Product] を指定してください。さらに、[Business Data Related List] という種類の Web Part がありますので、これを別の Web Part として追加し、[Type] として [Part] を選択してください。さらに、追加した [Business Data Related List] の Web Part で [Edit] - [Connections] - [Get Related Item From] - [(前述で追加した Product の Web Part の名称)] を選択し、Web Part 間に関係を設定してください。
このように設定することで、[Product] から該当の値を選択すると、それと関連した [Part] の一覧が表示されるはずなのですが、すみません、Beta 版のせいか、あるいは私の設定方法が悪いのか、このソースは上手く動作しません。(現在確認中です) (→ 本件は、TR 版で修正されました! 2006/10/01更新


この Association の機能ですが、少し XML の内容が難しいので補足説明しておきますと、以下のように、『 「Product」のEntityの中の「GetPartsForProduct」というMethodを使い、そのMethodで定義されている「Parts」というReturnパラメータを使用しなさい 』 と指定しています。


  <Associations>
    <Association AssociationMethodEntityName="Product" AssociationMethodName="GetPartsForProduct" AssociationMethodReturnParameterName="Parts" Name="ProductsToParts" IsCached="true">
.......


さらに、この GetPartsForProduct メソッドの Parts の Return パラメータの中の XML ソースをみてください。この中で、以下の通り記載されている箇所があり、Entity 「Part」の「PartID」という Identifier と関連させることを意味しています。


  IdentifierEntityName="Part" IdentifierName="PartID"


尚、SQL Server 2005 Express Edition で osql  からトレースファイルを出力して確認したところ、GetPartsForProduct の SQL までは実行されていますが、その後がいっさい呼ばれていないという状況ですので、その原因がわかりましたらまたブログにアップしておきます。


尚、説明から割愛していますが、さらに IDEnumurator というXMLエントリを使って BDC上のデータを検索キーに含めることもできます。また、Excel Service などと同様、普通にフィルター Web Part などと関係させることなどもできます。


この大変面倒なカタログ情報 (XML) の編集作業ですが、やはり手で記載するのは大変ですね。(米国の BDC の開発者の方も音を上げていました。ほんと XML の手での編集はいいかげんにしてほしいです、、、)現在、有志の方により、米国にて複数の編集ツールがフリーでダウンロードできていますが、マイクロソフトとして、将来的に編集ツールなどをリリースする見込みについては、残念ながら記事掲載中の現時点(2006年08月19日)では予定されていない状況です。通常はパッケージ製品のベンダの方など高度開発者の方が使用する仕組みとして想定しており、今のところ手ですべて記載することを想定しています。(マイクロソフトらしくないと思われるかもしれませんが)


以下に最終的に完成した XML ソースをご参考として掲載しておきます。(添付ファイル AdventureWorksDW_Sample4_Associations.xml と同様です)


<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<LobSystem xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://schemas.microsoft.com/office/2006/03/BusinessDataCatalog BDCMetadata.xsd" Type="Database" Version="1.0.0.0" Name="AdventureWorksDW4" xmlns="http://schemas.microsoft.com/office/2006/03/BusinessDataCatalog">
  <LobSystemInstances>
    <LobSystemInstance Name="AdventureWorksDW4">
      <Properties>
        <Property Name="DatabaseAccessProvider" Type="Microsoft.Office.Server.ApplicationRegistry.SystemSpecific.Db.DbAccessProvider">SqlServer</Property>
        <Property Name="RdbConnection Data Source" Type="System.String">TSMATSUZ21\OFFICESERVERS</Property>
        <Property Name="RdbConnection Initial Catalog" Type="System.String">AdventureWorksDW</Property>
        <Property Name="RdbConnection Integrated Security" Type="System.String">SSPI</Property>
      </Properties>
    </LobSystemInstance>
  </LobSystemInstances>
  <Entities>
    <Entity EstimatedInstanceCount="10000" Name="Part">
      <Properties>
        <Property Name="Title" Type="System.String">PartName</Property>
      </Properties>
      <Identifiers>
        <Identifier TypeName="System.Int32" Name="PartID" />
      </Identifiers>
      <Methods>
        <Method Name="GetParts">
          <Properties>
            <Property Name="RdbCommandText" Type="System.String">
       SELECT
        productname,
        productcode,
        partkey,
        partcode,
        partname,
        reorderpoint,
        inventory,
        dealerprice,
        InventoryComfortLevel
       FROM
        partinformation
       WHERE
        productCode like @productCode
      </Property>
            <Property Name="RdbCommandType" Type="System.Data.CommandType, System.Data, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">Text</Property>
          </Properties>
          <FilterDescriptors>
            <FilterDescriptor Type="Wildcard" Name="ByProductCode" />
          </FilterDescriptors>
          <Parameters>
            <Parameter Direction="In" Name="@productCode">
              <TypeDescriptor TypeName="System.String" AssociatedFilter="ByProductCode" Name="ProductCode">
                <DefaultValues>
                  <DefaultValue MethodInstanceName="PartFinderInstance" Type="System.String">WM2K%</DefaultValue>
                  <DefaultValue MethodInstanceName="PartSpecificFinderInstance" Type="System.String">WM2K%</DefaultValue>
                </DefaultValues>
              </TypeDescriptor>
            </Parameter>
            <Parameter Direction="Return" Name="Parts">
              <TypeDescriptor TypeName="System.Data.IDataReader, System.Data, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" IsCollection="true" Name="PartDataReader">
                <TypeDescriptors>
                  <TypeDescriptor TypeName="System.Data.IDataRecord, System.Data, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" Name="PartDataRecord">
                    <TypeDescriptors>
                      <TypeDescriptor TypeName="System.Int32" IdentifierName="PartID" Name="PartKey">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">PartID</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                        <Properties>
                          <Property Name="DisplayByDefault" Type="System.Boolean">false</Property>
                        </Properties>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="PartCode">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">PartCode</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="ProductCode">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">ProductCode</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="PartName">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Name</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                        <Properties>
                          <Property Name="DisplayByDefault" Type="System.Boolean">true</Property>
                        </Properties>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.Int16" Name="ReorderPoint">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Reorder Point</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.Int32" Name="Inventory">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Inventory</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.Int32" Name="InventoryComfortLevel">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Inventory Comfort Level</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                    </TypeDescriptors>
                  </TypeDescriptor>
                </TypeDescriptors>
              </TypeDescriptor>
            </Parameter>
          </Parameters>
          <MethodInstances>
            <MethodInstance Type="Finder" ReturnParameterName="Parts" Name="PartFinderInstance" />
            <MethodInstance Type="SpecificFinder" ReturnParameterName="Parts" Name="PartSpecificFinderInstance" />
          </MethodInstances>
        </Method>
      </Methods>
      <Actions>
        <Action Name="Open order form" Position="1" IsOpenedInNewWindow="true" Url="http://testsite/_layouts/formserver.aspx?xsnlocation=http://testsite/formservertemplates/testform.xsn&amp;openin=browser&amp;PartCode={0}" ImageUrl="">
          <ActionParameters>
            <ActionParameter Name="PartCode" Index="0" />
          </ActionParameters>
        </Action>
      </Actions>
    </Entity>
    <Entity EstimatedInstanceCount="10000" Name="Product">
      <Properties>
        <Property Name="Title" Type="System.String">ProductName</Property>
      </Properties>
      <Identifiers>
        <Identifier TypeName="System.Int32" Name="ProductKey" />
      </Identifiers>
      <Methods>
        <Method Name="GetProducts">
          <Properties>
            <Property Name="RdbCommandText" Type="System.String">
              select * from
                product
              where
                productcode like @productCode and
                productname like @productName and
                productKey &lt;= @maxProductKey and
                productKey &gt;= @minProductKey
            </Property>
            <Property Name="RdbCommandType" Type="System.Data.CommandType, System.Data, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">Text</Property>
          </Properties>
          <FilterDescriptors>
            <FilterDescriptor Type="Wildcard" Name="ByName">
              <Properties>
                <Property Name="UsedForDisambiguation" Type="System.Boolean">true</Property>
              </Properties>
            </FilterDescriptor>
            <FilterDescriptor Type="Wildcard" Name="ByCode" />
            <FilterDescriptor Type="ExactMatch" Name="ByID" />
          </FilterDescriptors>
          <Parameters>
            <Parameter Direction="In" Name="@minProductKey">
              <TypeDescriptor TypeName="System.Int32" IdentifierName="ProductKey" AssociatedFilter="ByID" Name="minProductKey">
                <DefaultValues>
                  <DefaultValue MethodInstanceName="ProductFinderInstance" Type="System.Int32">0</DefaultValue>
                  <DefaultValue MethodInstanceName="ProductSpecificFinderInstance" Type="System.Int32">0</DefaultValue>
                </DefaultValues>
              </TypeDescriptor>
            </Parameter>
            <Parameter Direction="In" Name="@maxProductKey">
              <TypeDescriptor TypeName="System.Int32" IdentifierName="ProductKey" AssociatedFilter="ByID" Name="maxProductKey">
                <DefaultValues>
                  <DefaultValue MethodInstanceName="ProductFinderInstance" Type="System.Int32">99999999</DefaultValue>
                  <DefaultValue MethodInstanceName="ProductSpecificFinderInstance" Type="System.Int32">99999999</DefaultValue>
                </DefaultValues>
              </TypeDescriptor>
            </Parameter>
            <Parameter Direction="In" Name="@productName">
              <TypeDescriptor TypeName="System.String" AssociatedFilter="ByName" Name="ProductName">
                <DefaultValues>
                  <DefaultValue MethodInstanceName="ProductFinderInstance" Type="System.String">%</DefaultValue>
                  <DefaultValue MethodInstanceName="ProductSpecificFinderInstance" Type="System.String">%</DefaultValue>
                </DefaultValues>
              </TypeDescriptor>
            </Parameter>
            <Parameter Direction="In" Name="@productCode">
              <TypeDescriptor TypeName="System.String" AssociatedFilter="ByCode" Name="ProductCode">
                <DefaultValues>
                  <DefaultValue MethodInstanceName="ProductFinderInstance" Type="System.String">%</DefaultValue>
                  <DefaultValue MethodInstanceName="ProductSpecificFinderInstance" Type="System.String">%</DefaultValue>
                </DefaultValues>
              </TypeDescriptor>
            </Parameter>
            <Parameter Direction="Return" Name="Products">
              <TypeDescriptor TypeName="System.Data.IDataReader, System.Data, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" IsCollection="true" Name="ProductDataReader">
                <TypeDescriptors>
                  <TypeDescriptor TypeName="System.Data.IDataRecord, System.Data, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" Name="ProductDataRecord">
                    <TypeDescriptors>
                      <TypeDescriptor TypeName="System.Int32" IdentifierName="ProductKey" Name="ProductKey">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">ProductKey</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                        <Properties>
                          <Property Name="DisplayByDefault" Type="System.Boolean">false</Property>
                        </Properties>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="ProductCode">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">ProductCode</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="ProductName">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Product Name</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                        <Properties>
                          <Property Name="DisplayByDefault" Type="System.Boolean">true</Property>
                        </Properties>
                      </TypeDescriptor>
                    </TypeDescriptors>
                  </TypeDescriptor>
                </TypeDescriptors>
              </TypeDescriptor>
            </Parameter>
          </Parameters>
          <MethodInstances>
            <MethodInstance Type="Finder" ReturnParameterName="Products" Name="ProductFinderInstance" />
            <MethodInstance Type="SpecificFinder" ReturnParameterName="Products" Name="ProductSpecificFinderInstance" />
          </MethodInstances>
        </Method>
        <Method Name="GetPartsForProduct">
          <Properties>
            <Property Name="RdbCommandText" Type="System.String">
              SELECT
                partkey,
                partcode,
                partname,
                reorderpoint,
                inventory,
                dealerprice,
                InventoryComfortLevel
              FROM
                ProductInventoryForPart
              WHERE
                productKey = @ProductKey
            </Property>
            <Property Name="RdbCommandType" Type="System.Data.CommandType, System.Data, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">Text</Property>
          </Properties>
          <Parameters>
            <Parameter Direction="In" Name="@productKey">
              <TypeDescriptor TypeName="System.Int32" IdentifierName="ProductKey" Name="ProductKey" />
            </Parameter>
            <Parameter Direction="Return" Name="Parts">
              <TypeDescriptor TypeName="System.Data.IDataReader, System.Data, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" IsCollection="true" Name="PartDataReader">
                <TypeDescriptors>
                  <TypeDescriptor TypeName="System.Data.IDataRecord, System.Data, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" Name="PartDataRecord">
                    <TypeDescriptors>
                      <TypeDescriptor TypeName="System.Int32" IdentifierEntityName="Part" IdentifierName="PartID" Name="PartKey">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">PartID</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                        <Properties>
                          <Property Name="DisplayByDefault" Type="System.Boolean">false</Property>
                        </Properties>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="PartCode">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">PartCode</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.String" Name="PartName">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Name</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                        <Properties>
                          <Property Name="DisplayByDefault" Type="System.Boolean">true</Property>
                        </Properties>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.Int16" Name="ReorderPoint">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Reorder Point</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.Int32" Name="Inventory">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Inventory</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                      <TypeDescriptor TypeName="System.Int32" Name="InventoryComfortLevel">
                        <LocalizedDisplayNames>
                          <LocalizedDisplayName LCID="1033">Inventory Comfort Level</LocalizedDisplayName>
                        </LocalizedDisplayNames>
                      </TypeDescriptor>
                    </TypeDescriptors>
                  </TypeDescriptor>
                </TypeDescriptors>
              </TypeDescriptor>
            </Parameter>
          </Parameters>
        </Method>
      </Methods>
    </Entity>
  </Entities>
  <Associations>
    <Association AssociationMethodEntityName="Product" AssociationMethodName="GetPartsForProduct" AssociationMethodReturnParameterName="Parts" Name="ProductsToParts" IsCached="true">
      <SourceEntity Name="Product" />
      <DestinationEntity Name="Part" />
    </Association>
  </Associations>
</LobSystem>


 

AdventureWorksDW_BDC.zip

Comments (0)

Skip to main content