SharePoint の PerformancePoint Services 用に表形式のデータ ソース エディターを作成する

PerformancePoint サービス のカスタムの表形式データ ソース拡張機能のエディター コンポーネントを作成する方法について説明します。

PerformancePoint サービス のカスタムのデータ ソース エディターについて

PerformancePoint サービス では、カスタムのデータ ソース エディターを使用して、カスタムの表形式データ ソースにプロパティをセットすることができます。 エディターの要件と機能の詳細については、「 カスタム PerformancePoint Services オブジェクトのエディター」を参照してください。

以下の手順とコード例は、 カスタム オブジェクト サンプルSampleDataSourceEditor クラスに基づいています。 エディターはシン Web アプリケーションで、エディターを使用して、データ ソースの名前と説明の変更、株式シンボルの入力、プロキシ サーバー アドレスとキャッシュ ファイルの場所の指定を行うことができます。 クラスの完全なコードは、「コード例: カスタムの表形式データ ソースの取得と更新」を参照してください。

サンプル エディターをテンプレートとして使用することをお勧めします。 サンプルは PerformancePoint サービス API のオブジェクトを呼び出す方法を示し、リポジトリ操作 (オブジェクトの作成、更新など) の呼び出しを容易にするヘルパー オブジェクトを提供し、PerformancePoint サービス 開発のためのベスト プラクティスを示します。

カスタムの PerformancePoint サービス 表形式データ ソース用エディターを作成する

  1. PerformancePoint サービス をインストールするか、拡張機能で使用する DLL (手順 3 で表示) をコンピューターにコピーします。 詳細については、「 クラス ライブラリを含む DLL」を参照してください。

  2. Visual Studio で、C# クラス ライブラリを作成します。 拡張機能のためのクラス ライブラリを既に作成している場合、新しい C# クラスを追加します。

    DLL には厳密な名前で署名する必要があります。 さらに、DLL によって参照されたすべてのアセンブリが厳密な名前を持つことを確認してください。 厳密な名前を使用してアセンブリに署名する方法の詳細、および公開/秘密キーのペアを作成する方法の詳細については、「How to: Create a public/private key pair」を参照してください。

  3. プロジェクトに、アセンブリ参照として以下の DLL を追加します。

    • Microsoft.PerformancePoint.Scorecards.Client.dll
    • Microsoft.SharePoint.dll (ヘルパー クラスが使用)

    サンプル エディターには、System.Core.dll、System.Web.dll、System.Web.Services.dll、および System.Xml.Linq.dll へのアセンブリ参照も含まれます。 拡張機能によっては、その他のプロジェクト参照が必要になることがあります。

  4. サンプルから以下のクラスをプロジェクトに追加します。 エディターはこれらのヘルパー クラスを使用して PerformancePoint サービス リポジトリとキャッシュ ファイルを操作します。

    • ExtensionRepositoryHelper.cs
    • DataSourceRepositoryHelper.cs
    • SampleDSCacheHandler.cs
  5. エディター クラスで、 Microsoft.PerformancePoint.Scorecards 名前空間の using ディレクティブを追加します。 拡張機能によっては、その他の using ディレクディブが必要になることがあります。

  6. エディターの実装をサポートする基本クラスから継承します。 サンプル データ ソース エディターは Web アプリケーションであるため、 Page クラスから継承します。 他の実装では、 UserControl クラス、 WebPart クラスなどの基本クラスから派生できます。

  7. ユーザーが表示または変更できるプロパティを表示するコントロールの変数を宣言します。 サンプル データ ソース エディターでは、最初にユーザー インターフェイス コンポーネント (ASPX ページ) で定義されている Web サーバー コントロールの変数を宣言します。 サンプル エディターでは、ユーザーが変更を送信できるボタン コントロールも定義します。 次に、エディターは CreateChildControls() メソッドを呼び出して、コントロールをページで使用できるようにします。

    注:

    エディターは、ユーザー インターフェイスとは別のプログラミング ロジックを定義します。 エディターのユーザー インターフェイス コンポーネントを作成するための説明は、この文書の範囲外となります。

    サンプル データ ソース エディターでは、 Page_Load メソッドで手順 8 から 11 を実行します。 Page_Load は、変数とコントロールの初期化と検証、コントロールの設定、カスタム データ ソースとヘルパー オブジェクトの状態情報の保存にも使用されます。

  8. クエリ文字列からパラメーターを取得し、それらを以下のコード例で示すローカル変数のための値として設定します。

    // The URL of the site collection that contains the PerformancePoint Services repository.
    string server = Request.QueryString[ClickOnceLaunchKeys.SiteCollectionUrl];
    
    // The location of the data source in the repository.
    string itemLocation = Request.QueryString[ClickOnceLaunchKeys.ItemLocation];
    
    // The operation to perform: OpenItem or CreateItem.
    string action = Request.QueryString[ClickOnceLaunchKeys.LaunchOperation];
    

    注:

    クエリ文字列パラメーターの詳細については、「カスタム PerformancePoint Services オブジェクトのエディター」を参照してください。

  9. 以下のコード例で示すように、リポジトリへの呼び出しを行うための DataSourceRepositoryHelper オブジェクトを取得します。

    DataSourceRepositoryHelper = new DataSourceRepositoryHelper();
    
  10. 以下のコード例で示すように、クエリ文字列パラメーターに基づいてデータ ソースの場所を設定します。

    RepositoryLocation repositoryDataSourceLocation = RepositoryLocation.CreateFromUriString(itemLocation);
    
  11. クエリ文字列から実行する操作 ( OpenItem または CreateItem) を取得し、カスタム データ ソースを取得または作成します。

    • カスタム データ ソースを取得するには、 DataSourceRepositoryHelper.Get メソッドを使用します。
    • カスタム データ ソースを作成するには、 DataSource() コンストラクターを使用し、データソースの NameSubTypeId プロパティを定義します。 SubTypeId はデータ ソースの一意の識別子で、PerformancePoint サービス web.config ファイルのカスタム データ ソースの subType 属性と一致する必要があります。

    注:

    サンプルのデータ ソース エディターには、データ ソース オブジェクトを作成するためのロジックが含まれていません。 カスタム オブジェクトの作成例については、「方法: SharePoint でPerformancePoint Services用のレポート エディターを作成する」または「方法: SharePoint でPerformancePoint Servicesのフィルター エディターを作成する」を参照してください。

    if (ClickOnceLaunchValues.OpenItem.Equals(action, StringComparison.OrdinalIgnoreCase))
    {
      // Use the repository-helper object to retrieve the data source.
      datasource = dataSourceRepositoryHelper.Get(repositoryDataSourceLocation);
      if (datasource == null)
      {
        displayError("Could not retrieve the data source for editing.");
        return;
      }
    }
    else
    {
      displayError("Invalid Action.");
      return;
    }
    

    注:

    既定では、ユーザーは PerformancePoint ダッシュボード デザイナーからのみカスタム オブジェクトを作成できます。 ユーザーがダッシュボード デザイナーの外部でカスタム オブジェクトを作成できるようにするには、リポジトリ内のコンテンツ タイプから CreateItem 要求をエディターに送信するメニュー項目を追加する必要があります。 詳細については、「 カスタム PerformancePoint Services オブジェクトのエディター」を参照してください。

    サンプル データ ソース エディターでは、 buttonOK_Click メソッドと CreateCacheFile メソッドで手順 12 と 13 を実行します。 buttonOK_Click、AreAllInputsValid メソッドを呼び出してコントロールの内容を検証したり、カスタム データ ソースとヘルパー オブジェクトの状態情報を取得したりするためにも使用されます。

  12. データ ソースをユーザー定義の変更で更新します。 サンプル データ ソース エディターは DataSourceRepositoryHelper.Update メソッドを呼び出して、リポジトリのデータ ソース オブジェクトの NameDescriptionCustomData プロパティを更新します。 CustomData を使用し、シリアル化されたオブジェクトまたは文字列を格納できます。 サンプル エディターは、これを使用して、ユーザー定義の株式シンボル、株の時価を格納するキャッシュ ファイルの場所、プロキシ サーバーの場所を格納します。

    注:

    ユーザーは、カスタム オブジェクトの名前説明所有者 (責任者) プロパティを編集し、ダッシュボード デザイナーとPerformancePoint Services リポジトリから直接カスタム オブジェクトを削除できます。

  13. データ ソース プロバイダーを呼び出して、列マッピングを定義します (このマッピングが定義されていない場合)。

コード例: SharePoint のカスタムの PerformancePoint サービス表形式データソースの取得と更新

次のコード例で、カスタムの表形式データ ソースの取得と更新を行います。 このコードはエディターの分離コード クラスのもので、[ASPX] ページに定義されたコントロールのプログラミング ロジックを提供します。

このコード例をコンパイルできるようにするには、「PerformancePoint Services で表形式データ ソースのエディター クラスを作成して設定する」で説明しているように開発環境を設定する必要があります。

using System;
using System.IO;
using System.Web.UI;
using System.Web.UI.WebControls;
using Microsoft.PerformancePoint.Scorecards;
using System.Xml.Linq;

namespace Microsoft.PerformancePoint.SDK.Samples.SampleDataSource
{
    // Represents the class that defines the sample data source editor.
    public class SampleDataSourceEditor : Page
    {

        #region Members
        // Declare private variables for the ASP.NET controls defined in the user interface.
        // The user interface is an ASPX page that defines the controls in HTML.
        private TextBox textboxName;
        private TextBox textboxDescription;
        private TextBox textboxStockSymbols;
        private TextBox textboxXMLLocation;
        private TextBox textboxProxy;
        private Label labelErrorMessage;
        private Button buttonOK;
        #endregion

        #region Page methods and events
        // Make the controls available to this class.
        protected override void CreateChildControls()
        {
            base.CreateChildControls();

            if (null == textboxProxy)
                textboxProxy = FindControl("textboxProxy") as TextBox;
            if (null == textboxName)
                textboxName = FindControl("textboxName") as TextBox;
            if (null == textboxDescription)
                textboxDescription = FindControl("textboxDescription") as TextBox;
            if (null == textboxStockSymbols)
                textboxStockSymbols = FindControl("textboxStockSymbols") as TextBox;
            if (null == textboxXMLLocation)
                textboxXMLLocation = FindControl("textboxXMLLocation") as TextBox;
            if (null == labelErrorMessage)
                labelErrorMessage = FindControl("labelErrorMessage") as Label;
            if (null == buttonOK)
                buttonOK = FindControl("buttonOK") as Button;
        }

        // Handles the Load event of the Page control.
        // Methods that use a control variable should call the Control.EnsureChildControls
        // method before accessing the variable for the first time.
        protected void Page_Load(object sender, EventArgs e)
        {
            // Initialize controls the first time the page loads only.
            if (!IsPostBack)
            {
                EnsureChildControls();

                DataSourceRepositoryHelper dataSourceRepositoryHelper = null;
                try
                {
                    // Get information from the query string parameters.
                    string server = Request.QueryString[ClickOnceLaunchKeys.SiteCollectionUrl];
                    string itemLocation = Request.QueryString[ClickOnceLaunchKeys.ItemLocation];
                    string action = Request.QueryString[ClickOnceLaunchKeys.LaunchOperation];

                    // Validate the query string parameters.
                    if (string.IsNullOrEmpty(server) ||
                        string.IsNullOrEmpty(itemLocation) ||
                        string.IsNullOrEmpty(action))
                    {
                        displayError("Invalid URL.");
                        return;
                    }

                    // Retrieve the repository-helper object.
                    dataSourceRepositoryHelper =
                        new DataSourceRepositoryHelper();

                    // Set the data source location.
                    RepositoryLocation repositoryDataSourceLocation = RepositoryLocation.CreateFromUriString(itemLocation);

                    DataSource datasource;

                    // Retrieve the data source object by
                    // using the repository-helper object.
                    if (ClickOnceLaunchValues.OpenItem.Equals(action, StringComparison.OrdinalIgnoreCase))
                    {
                        datasource = dataSourceRepositoryHelper.Get(repositoryDataSourceLocation);
                        if (datasource == null)
                        {
                            displayError("Could not retrieve the data source for editing.");
                            return;
                        }
                    }
                    else
                    {
                        displayError("Invalid Action.");
                        return;

                    }

                    // Save the original data source and helper objects across page postbacks.
                    ViewState["action"] = action;
                    ViewState["datasource"] = datasource;
                    ViewState["datasourcerepositoryhelper"] = dataSourceRepositoryHelper;

                    // Populate the child controls.
                    if (null != datasource.Name)
                        textboxName.Text = datasource.Name.ToString();

                    if (null != datasource.Description)
                        textboxDescription.Text = datasource.Description.ToString();

                    if (null != datasource.CustomData)
                    {
                        string[] splitCustomData = datasource.CustomData.Split('&');
                        if (splitCustomData.Length > 2)
                        {
                            textboxStockSymbols.Text = splitCustomData[0];
                            textboxXMLLocation.Text = splitCustomData[1].Replace(@"\\SampleStockQuotes.xml", string.Empty);
                            textboxProxy.Text = splitCustomData[2];
                        }
                    }
                }
                catch (Exception ex)
                {
                    displayError("An error has occurred. Please contact your administrator for more information.");
                    if (dataSourceRepositoryHelper != null)
                    {
                        // Add the exception detail to the server
                        // event log.
                        dataSourceRepositoryHelper.HandleException(ex);
                    }
                }
            }
        }

        // Handles the Click event of the buttonOK control.
        protected void buttonOK_Click(object sender, EventArgs e)
        {
            EnsureChildControls();

            // Verify that the required fields contain values.
            if (!AreAllInputsValid())
                return;

            // Clear any pre-existing error message.
            labelErrorMessage.Text = string.Empty;

            // Retrieve the data source and helper objects from view state.
            string action = (string)ViewState["action"];
            DataSource datasource = (DataSource)ViewState["datasource"];
            DataSourceRepositoryHelper datasourcerepositoryhelper = (DataSourceRepositoryHelper)ViewState["datasourcerepositoryhelper"];

            // Update the data source object with form changes.
            datasource.Name.Text = textboxName.Text;
            datasource.Description.Text = textboxDescription.Text;

            // Define column mappings if they aren't already defined.
            if (datasource.DataTableMapping.ColumnMappings.Count <= 0)
            {
                datasource.DataTableMapping = WSTabularDataSourceProvider.CreateDataColumnMappings();
            }

            // Save the data source to the repository
            // by using the repository-helper object.
            try
            {
                CreateCacheFile(datasource);

                datasource.Validate();

                if (ClickOnceLaunchValues.OpenItem.Equals(action, StringComparison.OrdinalIgnoreCase))
                {
                    datasourcerepositoryhelper.Update(datasource);
                }
                else
                {
                    displayError("Invalid Action.");
                }
            }
            catch (Exception ex)
            {
                displayError("An error has occurred. Please contact your administrator for more information.");
                if (datasourcerepositoryhelper != null)
                {
                    // Add the exception detail to the server event log.
                    datasourcerepositoryhelper.HandleException(ex);
                }
            }
        }
        #endregion

        #region Helper methods
        // Display the error string in the labelErrorMessage label.
        void displayError(string msg)
        {
            EnsureChildControls();

            labelErrorMessage.Text = msg;

            // Disable the OK button because the page is in an error state.
            buttonOK.Enabled = false;
            return;
        }

        // Validate the text box inputs.
        bool AreAllInputsValid()
        {
            if (string.IsNullOrEmpty(textboxProxy.Text))
            {
                labelErrorMessage.Text = "The proxy server address is required.";
                return false;
            }

            if (string.IsNullOrEmpty(textboxXMLLocation.Text))
            {
                labelErrorMessage.Text = "The location to save the cache file to is required.";
                return false;
            }

            if (string.IsNullOrEmpty(textboxName.Text))
            {
                labelErrorMessage.Text = "A data source name is required.";
                return false;
            }

            if (string.IsNullOrEmpty(textboxStockSymbols.Text))
            {
                labelErrorMessage.Text = "A stock symbol is required.";
                return false;
            }

            return true;
        }

        // Create the XML cache file at the specified location and
        // store it and the stock symbols in the CustomData
        // property of the data source.
        void CreateCacheFile(DataSource datasource)
        {
            string cacheFileLocation = string.Format("{0}\\\\{1}", textboxXMLLocation.Text.TrimEnd('\\\\'),
                                                      "SampleStockQuotes.xml");

            datasource.CustomData = string.Format("{0}&amp;{1}&amp;{2}", textboxStockSymbols.Text, cacheFileLocation, textboxProxy.Text);

            // Check if the cache file already exists.
            if (!File.Exists(cacheFileLocation))
            {
                // Create the cache file if it does not exist.
                XDocument doc = SampleDSCacheHandler.DefaultCacheFileContent;
                doc.Save(cacheFileLocation);
            }
        }
        #endregion
    }
}

次の手順

データ ソース エディター (必要に応じてユーザー インターフェイスを含む) とデータ ソース プロバイダーを作成した後、「方法: PerformancePoint Services拡張機能を手動で登録する」の説明に従って拡張機能をデプロイします

関連項目