共用方式為


逐步解說:擴充 SharePoint 專案項目類型

您可以使用 [商務資料連接模型] 專案項目在 SharePoint 中建立商務資料連接 (BDC) 服務的模型。根據預設,當您使用此專案項目建立模型時,模型中的資料不會對使用者顯示。您也必須在 SharePoint 中建立外部清單,才能讓使用者檢視資料。

在此逐步解說中,您將建立 [商務資料連接模型] 專案項目的擴充功能。開發人員可以使用擴充功能在顯示 BDC 模型資料的專案中建立外部清單。本逐步解說將示範下列工作:

  • 建立執行兩項主要工作的 Visual Studio 擴充功能:

    • 它會產生顯示 BDC 模型資料的外部清單。擴充功能會使用 SharePoint 專案系統的物件模型產生定義清單的 Elements.xml 檔。此外還會將檔案加入至專案,以便隨 BDC 模型一併部署。

    • 它會將捷徑功能表項目加入至 [方案總管] 中的 [商務資料連接模型] 專案項目。開發人員按一下此功能表項目,就可以產生 BDC 模型的外部清單。

  • 建置 Visual Studio Extension (VSIX) Package 以部署擴充組件。

  • 測試擴充功能。

必要條件

開發電腦上需要下列元件才能完成此逐步解說:

了解下列概念有助於完成此逐步解說 (但非必要):

  • Microsoft SharePoint Server 2010 中的 BDC 服務。如需詳細資訊,請參閱 BDC 架構 (英文)。

  • BDC 模型的 XML 結構描述。如需詳細資訊,請參閱 BDC 模型基礎結構 (英文)。

建立專案

若要完成這個逐步解說,您必須建立兩個專案:

  • VSIX 專案,用於建立 VSIX 套件以部署專案項目擴充功能。

  • 類別庫專案,用於實作專案項目擴充功能。

從建立這些專案開始進行此逐步解說。

若要建立 VSIX 專案

  1. 啟動 Visual Studio。

  2. 在功能表列上,選擇 [檔案], [新增], [Project]。

  3. 在 [新增專案] 對話方塊中,展開 [Visual C#] 或 [ Visual Basic] 節點,然後選取 [擴充性] 節點。

    注意事項注意事項

    為,當您安裝 Visual Studio SDK, [擴充性] 有節點的。如需詳細資訊,請參閱本主題稍早討論的<必要條件>一節。

  4. 在[新增專案] 對話方塊的頂端,選取 [.NET Framework 4.5]。

    SharePoint 工具擴充功能需要這版的 .NET Framework 功能。

  5. 選取 [VSIX 專案] 範本。

  6. 在 [Name]方塊中,輸入 GenerateExternalDataLists專案,然後選取 [確定] 按鈕。

    Visual Studio 會將 [GenerateExternalDataLists] 專案加入至 [方案總管]。

  7. 如果 source.extension.vsixmanifest 檔案不會自動開啟,請開啟它在 GenerateExternalDataLists 專案的捷徑功能表,然後選取 [開啟]

  8. 確認 source.extension.vsixmanifest 檔案具有非空白項目 (輸入 Contoso 作者) 欄位,請儲存檔案並關閉它。

若要建立擴充功能專案

  1. 在 [方案總管],開啟 [GenerateExternalDataLists]方案節點的捷徑功能表,選擇[新增],然後選取 [新增專案]。

    注意事項注意事項

    在 Visual Basic 專案中,方案節點只有在已選取General, Projects and Solutions, Options Dialog Box中的 [永遠顯示方案] 核取方塊時,才會出現在 [方案總管] 中。

  2. 在 [新增專案] 對話方塊中,展開 [Visual C#] 或 [ Visual Basic] 節點,然後選取 [視窗] 節點。

  3. 在對話方塊的頂端,選取 [.NET Framework 4.5]。

  4. 在專案範本清單中,選取 [類別庫]。

  5. 在 [Name]方塊中,輸入 BdcProjectItemExtension,然後選取 [確定] 按鈕。

    Visual Studio 會將 [BdcProjectItemExtension] 專案加入至方案,然後開啟預設的 Class1 程式碼檔。

  6. 從專案刪除 Class1 程式碼檔。

設定擴充功能專案

在您撰寫程式碼建立專案項目擴充功能之前,請先將程式碼檔案和組件參考加入至擴充功能專案。

若要設定專案

  1. 在 [BdcProjectItemExtension] 專案中,加入名稱如下的兩個程式碼檔:

    • ProjectItemExtension

    • GenerateExternalDataLists

  2. 選取 BdcProjectItemExtension 專案,然後,在功能表列上,選擇[Project], [新增參考]。

  3. 在 [組件] 節點底下,選取[Framework] 節點並選取下列組件中的核取方塊:

    • System.ComponentModel.Composition

    • WindowsBase

  4. 在 [組件] 節點底下,選取節點, [延伸] 為下列組件然後選取核取方塊:

    • Microsoft.VisualStudio.SharePoint
  5. 選擇 [確定] 按鈕。

定義專案項目擴充功能

建立類別,該類別會定義 [商務資料連接模型] 專案項目的擴充功能。為定義擴充功能,此類別會實作 ISharePointProjectItemTypeExtension 介面。在您要擴充現有專案項目的類型時實作此介面。

若要定義專案項目擴充功能

  • 下列程式碼貼入 ProjectItemExtension 程式碼檔案。

    注意事項注意事項

    加入這個程式碼之後,專案會出現一些編譯錯誤。在後續步驟中加入程式碼時,這些錯誤將不存在。

    Imports Microsoft.VisualStudio.SharePoint
    Imports System.ComponentModel.Composition
    
    Namespace Contoso.SharePointProjectItemExtensions.GenerateExternalDataLists
    
        ' Export attribute: Enables Visual Studio to discover and load this extension.
        ' SharePointProjectItemType attribute: Specifies the ID of the project item to extend.
        ' GenerateExternalDataListsExtension class: Defines the extension for the BDC project item.
        '     The other part of the partial class contains the logic for generating the external data lists. 
        <Export(GetType(ISharePointProjectItemTypeExtension))> _
        <SharePointProjectItemType("Microsoft.VisualStudio.SharePoint.BusinessDataConnectivity")> _
        Partial Friend Class GenerateExternalDataListsExtension
            Implements ISharePointProjectItemTypeExtension
    
            ' Creates the new shortcut menu item that the user clicks to generate the external data lists.
            Private Sub Initialize(ByVal SharePointProjectItemType As ISharePointProjectItemType) _
                Implements ISharePointProjectItemTypeExtension.Initialize
                AddHandler SharePointProjectItemType.ProjectItemMenuItemsRequested,
                    AddressOf SharePointProjectItemMenuItemsRequested
            End Sub
    
            Private Sub SharePointProjectItemMenuItemsRequested(ByVal Sender As Object, _
                ByVal e As SharePointProjectItemMenuItemsRequestedEventArgs)
                Dim generateListMenuItem As IMenuItem = e.ViewMenuItems.Add("Generate External Data List")
                AddHandler generateListMenuItem.Click, AddressOf GenerateExternalDataLists_Execute
            End Sub
        End Class
    End Namespace
    
    using Microsoft.VisualStudio.SharePoint;
    using System.ComponentModel.Composition;
    
    namespace Contoso.SharePointProjectItemExtensions.GenerateExternalDataLists
    {
        // Enables Visual Studio to discover and load this extension.
        [Export(typeof(ISharePointProjectItemTypeExtension))]
    
        // Specifies the ID of the project item to extend.
        [SharePointProjectItemType("Microsoft.VisualStudio.SharePoint.BusinessDataConnectivity")]
    
        // Defines the extension for the BDC project item. The other part of the partial class contains
        // the logic for generating the external data lists. 
        internal partial class GenerateExternalDataListsExtension : ISharePointProjectItemTypeExtension
        {
            // Implements IProjectItemTypeExtension.Initialize. Creates the new shortcut menu item that
            // the user clicks to generate the external data lists.
            public void Initialize(ISharePointProjectItemType projectItemType)
            {
                projectItemType.ProjectItemMenuItemsRequested += ProjectItemMenuItemsRequested;
            }
    
            private void ProjectItemMenuItemsRequested(object sender, SharePointProjectItemMenuItemsRequestedEventArgs e)
            {
                e.ViewMenuItems.Add("Generate External Data List").Click += GenerateExternalDataLists_Execute;
            }
        }
    }
    

建立外部資料清單

加入 GenerateExternalDataListsExtension 類別的部分定義,該類別會為 BDC 模型中的每一個實體建立外部資料清單。若要建立外部資料清單,此程式碼會先透過剖析 BDC 模型檔中 XML 資料的方式,讀取 BDC 模型中的實體資料。然後會根據 BDC 模型建立清單執行個體,並且將此清單執行個體加入至專案。

若要建立外部資料清單

  • 下列程式碼貼入 GenerateExternalDataLists 程式碼檔案。

    Imports Microsoft.VisualStudio.SharePoint
    Imports Microsoft.VisualBasic
    Imports System
    Imports System.Collections.Generic
    Imports System.IO
    Imports System.Linq
    Imports System.Text
    Imports System.Xml.Linq
    
    Namespace Contoso.SharePointProjectItemExtensions.GenerateExternalDataLists
    
        ' Creates the external data lists for the BDC item. The other part of the partial class 
        ' defines the BDC project item extension.
        Partial Friend Class GenerateExternalDataListsExtension
    
            Private Const ModelFileNameString As String = "ModelFileName"
            Private Const EXTENSION_BDCM As String = ".bdcm"
            Private Const NamespaceString As String = "https://schemas.microsoft.com/windows/2007/BusinessDataCatalog"
            Private Shared ReadOnly BdcNamespace As XNamespace = XNamespace.Get(NamespaceString)
    
            ' Generates an external data list for each Entity in the BDC model. This event handler is called
            ' when the developer clicks the shortcut menu item that the extension adds to the BDC project item.
            Private Sub GenerateExternalDataLists_Execute(ByVal Sender As Object, ByVal e As MenuItemEventArgs)
    
                Dim projectItem As ISharePointProjectItem = CType(e.Owner, ISharePointProjectItem)
                Dim bdcmFile As ISharePointProjectItemFile = GetModelFile(projectItem)
    
                Dim doc As XDocument = XDocument.Load(bdcmFile.FullPath)
                Dim skippedEntities As List(Of XElement) = New List(Of XElement)()
    
                ' Try to generate an external data list for each entity defined in the BDC model file.
                For Each entity As XElement In doc.Root.Elements(BdcNamespace + "LobSystems").Elements( _
                    BdcNamespace + "LobSystem").Elements(BdcNamespace + "Entities").Elements(BdcNamespace + "Entity")
    
                    If False = GenerateExternalDataList(projectItem, entity) Then
                        skippedEntities.Add(entity)
                    End If
                Next
    
                ' Report skipped entities.
                If skippedEntities.Count <> 0 Then
                    Dim entityNameList As StringBuilder = Nothing
                    skippedEntities.ForEach(Function(entity As XElement)
                                                If (entityNameList Is Nothing) Then
                                                    entityNameList = New StringBuilder()
                                                Else
                                                    entityNameList.AppendLine(",")
                                                End If
                                                entityNameList.Append(entity.Attribute("Name").Value)
                                            End Function)
    
                    Dim message As String = String.Format("The following Entities were skipped because " &
                        "either a LobSystemInstance, SpecificFinder, or Finder was not found for them. \r\n{0}", _
                        entityNameList)
                    projectItem.Project.ProjectService.Logger.WriteLine(message, LogCategory.Warning)
                End If
            End Sub
    
            ' Gets the ISharePointProjectItemFile object for the BDC model file.
            Private Function GetModelFile(ByVal projectItem As ISharePointProjectItem) As ISharePointProjectItemFile
    
                Dim modelFileName As String = Nothing
                If projectItem.FeatureProperties.TryGetValue(ModelFileNameString, modelFileName) Then
                    modelFileName = Path.GetFileName(modelFileName)
                    Return (From file In projectItem.Files _
                            Where String.Compare(file.Name, modelFileName, StringComparison.OrdinalIgnoreCase) = 0 _
                            Select file).FirstOrDefault()
                Else
                    ' If we can't find the ModelFileName through the FeatureProperties, 
                    ' get the first file that has a '.bdcm' extension
                    Return (From file In projectItem.Files _
                            Where file.Name.EndsWith(EXTENSION_BDCM, StringComparison.OrdinalIgnoreCase) _
                            Select file).FirstOrDefault()
                End If
            End Function
    
            ' Boilerplate XML for the new list instance that is based on the BDC model.
            Private Const externalDataListContent As String = _
                "<?xml version=""1.0"" encoding=""utf-8""?>" & vbCrLf & _
                "        <Elements https://schemas.microsoft.com/sharepoint/"">" & vbCrLf & _
                "          <ListInstance Title=""$EntityName$DataList""" & vbCrLf & _
                "                        OnQuickLaunch=""TRUE""" & vbCrLf & _
                "                        TemplateType=""104""" & vbCrLf & _
                "                        FeatureId=""$SharePoint.Feature.Id$""" & vbCrLf & _
                "                        Url=""Lists/$EntityName$DataList""" & vbCrLf & _
                "                        Description=""Default List for $EntityName$."">" & vbCrLf & _
                "            <DataSource>" & vbCrLf & _
                "              <Property Name=""LobSystemInstance"" Value=""$LobSystemInstance$"" />" & vbCrLf & _
                "              <Property Name=""EntityNamespace"" Value=""$EntityNamespace$"" />" & vbCrLf & _
                "              <Property Name=""Entity"" Value=""$EntityName$"" />" & vbCrLf & _
                "              <Property Name=""SpecificFinder"" Value=""$SpecificFinder$"" />" & vbCrLf & _
                "              <Property Name=""Finder"" Value=""$Finder$"" />" & vbCrLf & _
                "            </DataSource>" & vbCrLf & _
                "          </ListInstance>" & vbCrLf & _
                "        </Elements>"
    
            ' Tries to generate an external data list for the specified BDC model project item and entity.
            Private Function GenerateExternalDataList(ByVal projectItem As ISharePointProjectItem, ByVal entity As XElement) As Boolean
    
                Dim lobSystemInstanceName As String = GetLobSystemInstanceName(entity)
                Dim specificFinderName As String = GetSpecificFinderName(entity)
                Dim finderName As String = GetFinderName(entity)
                Dim entityName As String = entity.Attribute("Name").Value
    
                If String.IsNullOrEmpty(lobSystemInstanceName) Or String.IsNullOrEmpty(specificFinderName) Or _
                    String.IsNullOrEmpty(finderName) Then
                    Return False
                End If
    
                Dim newExternalDataListName As String = entityName & "DataList"
                Dim existingProjectItem As ISharePointProjectItem = (From existingItem As ISharePointProjectItem In projectItem.Project.ProjectItems
                                                    Where existingItem.Name = newExternalDataListName
                                                    Select existingItem).FirstOrDefault()
    
                ' Add a new list instance and populate it with data from the BDC model.
                If existingProjectItem Is Nothing Then
                    Dim newExternalDataList As ISharePointProjectItem = projectItem.Project.ProjectItems.Add(newExternalDataListName, _
                        "Microsoft.VisualStudio.SharePoint.ListInstance")
    
                    Dim newExternalDataListString As String = externalDataListContent
                    newExternalDataListString = newExternalDataListString.Replace("$EntityName$", entityName)
                    newExternalDataListString = newExternalDataListString.Replace("$LobSystemInstance$", lobSystemInstanceName)
                    newExternalDataListString = newExternalDataListString.Replace("$EntityNamespace$", entity.Attribute("Namespace").Value)
                    newExternalDataListString = newExternalDataListString.Replace("$SpecificFinder$", specificFinderName)
                    newExternalDataListString = newExternalDataListString.Replace("$Finder$", finderName)
    
                    Dim elementsXmlPath As String = Path.Combine(newExternalDataList.FullPath, "Elements.xml")
                    File.WriteAllText(elementsXmlPath, newExternalDataListString)
                    Dim elementsFile As ISharePointProjectItemFile = newExternalDataList.Files.AddFromFile(elementsXmlPath)
                    elementsFile.DeploymentType = DeploymentType.ElementManifest
                End If
    
                Return True
            End Function
    
            Private Function GetLobSystemInstanceName(ByVal entity As XElement) As String
    
                Dim lobSystemInstances As XElement = entity.Parent.Parent.Element(BdcNamespace + "LobSystemInstances")
                If lobSystemInstances IsNot Nothing Then
                    Dim lobSystemInstance As XElement = lobSystemInstances.Elements(BdcNamespace + "LobSystemInstance").FirstOrDefault()
                    If lobSystemInstance IsNot Nothing Then
                        Return lobSystemInstance.Attribute("Name").Value
                    End If
                End If
                Return Nothing
            End Function
    
            Private Function GetSpecificFinderName(ByVal entity As XElement) As String
                Return GetMethodInstance(entity, "SpecificFinder")
            End Function
    
            Private Function GetFinderName(ByVal entity As XElement) As String
                Return GetMethodInstance(entity, "Finder")
            End Function
    
            Private Function GetMethodInstance(ByVal entity As XElement, ByVal methodInstanceType As String) As String
                Dim methods As XElement = entity.Element(BdcNamespace + "Methods")
                If methods IsNot Nothing Then
                    For Each method As XElement In methods.Elements(BdcNamespace + "Method")
                        Dim methodInstances As XElement = method.Element(BdcNamespace + "MethodInstances")
                        If methodInstances IsNot Nothing Then
                            For Each methodInstance As XElement In methodInstances.Elements(BdcNamespace + "MethodInstance")
                                If methodInstance.Attribute("Type").Value = methodInstanceType Then
                                    Return methodInstance.Attribute("Name").Value
                                End If
                            Next
                        End If
                    Next
                End If
                Return Nothing
            End Function
    
        End Class
    End Namespace
    
    using Microsoft.VisualStudio.SharePoint;
    using System;
    using System.Collections.Generic;
    using System.IO;
    using System.Linq;
    using System.Text;
    using System.Xml.Linq;
    
    namespace Contoso.SharePointProjectItemExtensions.GenerateExternalDataLists
    {
        // Creates the external data lists for the BDC item. The other part of the partial class 
        // defines the BDC project item extension.
        internal partial class GenerateExternalDataListsExtension
        {
            private const string ModelFileNameString = "ModelFileName";
            private const string EXTENSION_BDCM = ".bdcm";
            private const string NamespaceString = "https://schemas.microsoft.com/windows/2007/BusinessDataCatalog";
            private static readonly XNamespace BdcNamespace = XNamespace.Get(NamespaceString);
    
            // Generates an external data list for each Entity in the BDC model. This event handler is called
            // when the developer clicks the shortcut menu item that the extension adds to the BDC project item.
            private void GenerateExternalDataLists_Execute(object sender, MenuItemEventArgs e)
            {
                ISharePointProjectItem projectItem = (ISharePointProjectItem)e.Owner;
                ISharePointProjectItemFile bdcmFile = GetModelFile(projectItem);
    
                XDocument doc = XDocument.Load(bdcmFile.FullPath);
                List<XElement> skippedEntities = new List<XElement>();
    
                // Try to generate an external data list for each entity defined in the BDC model file.
                foreach (XElement entity in doc.Root.Elements(BdcNamespace + "LobSystems").Elements(
                    BdcNamespace + "LobSystem").Elements(BdcNamespace + "Entities").Elements(BdcNamespace + "Entity"))
                {
                    if (!GenerateExternalDataList(projectItem, entity))
                    {
                        skippedEntities.Add(entity);
                    }
                }
    
                // Report skipped entities.
                if (skippedEntities.Count != 0)
                {
                    StringBuilder entityNameList = null;
                    skippedEntities.ForEach(delegate(XElement entity)
                    {
                        if (entityNameList == null)
                        {
                            entityNameList = new StringBuilder();
                        }
                        else
                        {
                            entityNameList.AppendLine(",");
                        }
                        entityNameList.Append(entity.Attribute("Name").Value);
                    });
    
                    string message = string.Format("The following Entities were skipped because either a LobSystemInstance, " +
                        "SpecificFinder, or Finder was not found for them. \r\n{0}", entityNameList);
                    projectItem.Project.ProjectService.Logger.WriteLine(message, LogCategory.Warning);
                }
            }
    
            // Gets the ISharePointProjectItemFile object for the BDC model file.
            private ISharePointProjectItemFile GetModelFile(ISharePointProjectItem projectItem)
            {
                string modelFileName;
                if (projectItem.FeatureProperties.TryGetValue(ModelFileNameString, out modelFileName))
                {
                    modelFileName = Path.GetFileName(modelFileName);
                    return (from file in projectItem.Files
                            where string.Compare(file.Name, modelFileName, StringComparison.OrdinalIgnoreCase) == 0
                            select file).FirstOrDefault();
                }
                else
                {
                    // if we can't find the ModelFileName through the FeatureProperties, 
                    // get the first file that has a '.bdcm' extension
                    return (from file in projectItem.Files
                            where file.Name.EndsWith(EXTENSION_BDCM, StringComparison.OrdinalIgnoreCase)
                            select file).FirstOrDefault();
                }
            }
    
            // Boilerplate XML for the new list instance that is based on the BDC model.
            private const string externalDataListContent =
                @"<?xml version=""1.0"" encoding=""utf-8""?>
                <Elements https://schemas.microsoft.com/sharepoint/"">
                  <ListInstance Title=""$EntityName$DataList""
                                OnQuickLaunch=""TRUE""
                                TemplateType=""104""
                                FeatureId=""$SharePoint.Feature.Id$""
                                Url=""Lists/$EntityName$DataList""
                                Description=""Default List for $EntityName$."">
                    <DataSource>
                      <Property Name=""LobSystemInstance"" Value=""$LobSystemInstance$"" />
                      <Property Name=""EntityNamespace"" Value=""$EntityNamespace$"" />
                      <Property Name=""Entity"" Value=""$EntityName$"" />
                      <Property Name=""SpecificFinder"" Value=""$SpecificFinder$"" />
                      <Property Name=""Finder"" Value=""$Finder$"" />
                    </DataSource>
                  </ListInstance>
                </Elements>";
    
            // Tries to generate an external data list for the specified BDC model project item and entity.
            private bool GenerateExternalDataList(ISharePointProjectItem projectItem, XElement entity)
            {
                string lobSystemInstanceName = GetLobSystemInstanceName(entity);
                string specificFinderName = GetSpecificFinderName(entity);
                string finderName = GetFinderName(entity);
                string entityName = entity.Attribute("Name").Value;
    
                if (string.IsNullOrEmpty(lobSystemInstanceName) || string.IsNullOrEmpty(specificFinderName) || 
                    string.IsNullOrEmpty(finderName))
                {
                    return false;
                }
    
                string newExternalDataListName = entityName + "DataList";
                ISharePointProjectItem existingProjectItem = (from ISharePointProjectItem existingItem in projectItem.Project.ProjectItems
                                                    where existingItem.Name == newExternalDataListName
                                                    select existingItem).FirstOrDefault();
    
                // Add a new list instance and populate it with data from the BDC model.
                if (existingProjectItem == null)
                {
                    ISharePointProjectItem newExternalDataList = projectItem.Project.ProjectItems.Add(newExternalDataListName, 
                        "Microsoft.VisualStudio.SharePoint.ListInstance");
    
                    string newExternalDataListString = externalDataListContent;
                    newExternalDataListString = newExternalDataListString.Replace("$EntityName$", entityName);
                    newExternalDataListString = newExternalDataListString.Replace("$LobSystemInstance$", lobSystemInstanceName);
                    newExternalDataListString = newExternalDataListString.Replace("$EntityNamespace$", entity.Attribute("Namespace").Value);
                    newExternalDataListString = newExternalDataListString.Replace("$SpecificFinder$", specificFinderName);
                    newExternalDataListString = newExternalDataListString.Replace("$Finder$", finderName);
    
                    string elementsXmlPath = Path.Combine(newExternalDataList.FullPath, "Elements.xml");
                    File.WriteAllText(elementsXmlPath, newExternalDataListString);
                    ISharePointProjectItemFile elementsFile = newExternalDataList.Files.AddFromFile(elementsXmlPath);
                    elementsFile.DeploymentType = DeploymentType.ElementManifest;
                }
    
                return true;
            }
    
            private string GetLobSystemInstanceName(XElement entity)
            {
                XElement lobSystemInstances = entity.Parent.Parent.Element(BdcNamespace + "LobSystemInstances");
                if (lobSystemInstances != null)
                {
                    XElement lobSystemInstance = lobSystemInstances.Elements(BdcNamespace + "LobSystemInstance").FirstOrDefault();
                    if (lobSystemInstance != null)
                    {
                        return lobSystemInstance.Attribute("Name").Value;
                    }
                }
                return null;
            }
    
            private string GetSpecificFinderName(XElement entity)
            {
                return GetMethodInstance(entity, "SpecificFinder");
            }
    
            private string GetFinderName(XElement entity)
            {
                return GetMethodInstance(entity, "Finder");
            }
    
            private string GetMethodInstance(XElement entity, string methodInstanceType)
            {
                XElement methods = entity.Element(BdcNamespace + "Methods");
                if (methods != null)
                {
                    foreach (XElement method in methods.Elements(BdcNamespace + "Method"))
                    {
                        XElement methodInstances = method.Element(BdcNamespace + "MethodInstances");
                        if (methodInstances != null)
                        {
                            foreach (XElement methodInstance in methodInstances.Elements(BdcNamespace + "MethodInstance"))
                            {
                                if (methodInstance.Attribute("Type").Value == methodInstanceType)
                                {
                                    return methodInstance.Attribute("Name").Value;
                                }
                            }
                        }
                    }
                }
    
                return null;
            }
        }
    }
    

檢查點

在逐步解說中進行至此處時,專案項目擴充功能的所有程式碼都會位於專案中。建置方案,以確定專案在編譯時未發生任何錯誤。

若要建置方案

  • 在功能表列上,選擇, [組建][建置方案]。

建立 VSIX 套件以部署專案項目擴充功能

若要部署擴充功能,請在您的方案中使用 VSIX 專案,以建立 VSIX 套件。首先,修改 VSIX 專案包含的 source.extension.vsixmanifest 檔案,來設定 VSIX 套件。接著,建置方案來建立 VSIX 套件。

若要設定和建立 VSIX 套件

  1. 在 [方案總管],開啟 source.extension.vsixmanifest 檔案的捷徑功能表在 GenerateExternalDataLists 專案,然後選取 [開啟]。

    Visual Studio 會在資訊清單編輯器中開啟檔案。source.extension.vsixmanifest 檔案是所有 VSIX 套件所需要 extension.vsixmanifest 檔案的基準。如需這個檔案的詳細資訊,請參閱VSIX 擴充結構描述參考

  2. 在 [產品名稱]方塊中,輸入 外部資料清單產生器。

  3. 在 [作者]方塊中,輸入 Contoso。

  4. 在 [Description]方塊中,輸入 商務資料連接可以用來產生外部資料的模型專案項目的擴充功能清單。

  5. 在編輯器中 [資產] 索引標籤上,選取 [新增] 按鈕。

    [將新的屬性] 對話方塊隨即出現。

  6. 在 [型別] 清單中,選取 [Microsoft.VisualStudio.MefComponent]。

    注意事項注意事項

    這個值對應於 extension.vsixmanifest 檔案中的 MefComponent 項目。這個項目指定 VSIX 套件中的擴充組件名稱。如需詳細資訊,請參閱MEFComponent Element

  7. 在 [Source] 清單中,選取 [在目前方案中的專案]。

  8. 在 [Project] 清單中,選取 [BdcProjectItemExtension],然後選取 [確定] 按鈕。

  9. 在功能表列上,選擇, [組建][建置方案]。

  10. 確定專案在編譯和建置無誤。

  11. 確定 GenerateExternalDataLists 專案的建置輸出資料夾現已包含 GenerateExternalDataLists.vsix 檔。

    根據預設,建置輸出資料夾為 ..\bin\Debug 資料夾,其位於專案檔案包含的資料夾下。

測試專案項目擴充功能

您現在可以測試專案項目擴充功能。首先,在 Visual Studio 的實驗執行個體中開始偵錯擴充功能專案。然後,使用 Visual Studio 實驗執行個體中的擴充功能來產生 BDC 模型的外部清單。最後,在 SharePoint 網站上開啟外部清單,確認其功能正常。

若要啟動對擴充功能的偵錯

  1. 如果需要,以管理認證的重新啟動 Visual Studio,然後開啟 GenerateExternalDataLists 方案。

  2. 在 BdcProjectItemExtension 專案,開啟 ProjectItemExtension 程式碼檔案,然後將中斷點加入至 Initialize 方法的程式碼。

  3. 開啟 GenerateExternalDataLists 程式碼檔案,然後將中斷點加入至 GenerateExternalDataLists_Execute 方法的第一行程式碼。

  4. 您可以選擇 F5 鍵開始偵錯,或在功能表列上,選擇, [偵錯][啟動偵錯]。

    Visual Studio 會將擴充功能安裝至 %UserProfile%\AppData\Local\Microsoft\VisualStudio\10.0Exp\Extensions\Contoso\External Data List Generator\1.0,並啟動 Visual Studio 的實驗執行個體。您將會在 Visual Studio 的這個執行個體中測試專案項目。

若要測試擴充功能

  1. 在 Visual Studio 的實驗執行個體,在功能表列上,選擇 [檔案], [新增], [Project]。

  2. 在 [新增專案] 對話方塊中,展開 [範本] 節點,展開 Visual C# 節點,展開 [SharePoint] 節點,然後選取 [2010]。

  3. 在對話方塊的頂端,確定 .NET Framework 3.5 已選取。Microsoft SharePoint Server 2010 的專案需要此版本的 .NET Framework。

  4. 在專案範本清單中,選取 [SharePoint 2010 專案]。

  5. 在 [Name]方塊中,輸入 SharePointProjectTestBDC,然後選取 [確定] 按鈕。

  6. 在 [SharePoint 自訂精靈中,輸入要用於偵錯的網站 URL,選取 [部署為陣列方案],然後選取 [完成] 按鈕。

  7. SharePointProjectTestBDC 開啟專案的捷徑功能表,選擇[新增],然後選取 [新項目]。

  8. 將 NewItem – SharePointProjectTestBDC 對話方塊中,展開安裝的語言節點,展開 [SharePoint] 節點。

  9. 選取 [2010] 節點,然後選取 [商務資料連接模型 (僅限陣列方案)]範本。

  10. 在 [Name]方塊中,輸入 TestBDCModel,然後選取 [新增] 按鈕。

  11. 確認在另一個 Visual Studio 執行個體中的程式碼在 ProjectItemExtension 程式碼檔案的 Initialize 方法之集合中的中斷點停止。

  12. 在 Visual Studio 停止執行個體,請選取 [F5]機碼,或在功能表列上,選擇[偵錯], [繼續] 繼續偵錯專案。

  13. 在 Visual Studio 的實驗執行個體中,選取 [F5]索引鍵,或在功能表列上,選擇, [偵錯][啟動偵錯] ,建置、部署和執行 [TestBDCModel]項目。

    這個瀏覽器開啟為指定偵錯的 SharePoint 網站的預設網頁。

  14. 確認 [快速啟動] 區域中的 [清單] 部分不包含根據專案中預設 BDC 模型的清單。您必須先使用 SharePoint 使用者介面或使用專案項目擴充功能建立外部資料清單。

  15. 結束這個瀏覽器。

  16. 在中開啟 TestBDCModel 專案的 Visual Studio 執行個體中,開啟 [TestBDCModel]節點的捷徑功能表中 [方案總管],然後選取 [產生外部資料清單]。

  17. 確認在另一個 Visual Studio 執行個體中的程式碼則是在的中斷點停止您在 GenerateExternalDataLists_Execute 方法的集合。選取 [F5]索引鍵,或在功能表列上,選擇[偵錯], [繼續] 繼續偵錯專案。

  18. Visual Studio 的實驗執行個體將會命名為 TestBDCModel 專案的 [Entity1DataList]的清單執行個體,且執行個體,也會產生名為清單執行個體的 [Feature2]的功能。

  19. 選取 [F5]索引鍵,或在功能表列上,選擇, [偵錯][啟動偵錯] ,建置、部署和執行 TestBDCModel 專案。

    這個瀏覽器開啟為偵錯使用 SharePoint 網站的預設網頁。

  20. 在快速啟動區中 [清單] 部分,選取 [Entity1DataList]清單。

  21. 確認清單包含名為 Identifier1 和訊息的資料行,除了具有 identifier1 則是的項目之外和 Hello World 訊息值。

    [商務資料連接模型] 專案範本產生提供這些資料的預設 BDC 模型。

  22. 結束這個瀏覽器。

清理開發電腦

在您完成測試專案項目擴充功能之後,從 SharePoint 網站移除外部清單和 BDC 模型,並且從 Visual Studio 移除專案項目擴充功能。

若要從 SharePoint 網站移除外部資料清單

  1. 在 SharePoint 網站上的快速啟動區,選取 [Entity1DataList]清單。

  2. 在 SharePoint 網站的功能區,請選取 [清單] 索引標籤。

  3. 在 [清單] 索引標籤上,按一下 [設定] 群組中,選取 [清單設定]。

  4. 在 [使用權限和管理] 下,選取 [刪除這個清單],然後選取 [確定] 確認您要傳送至資源回收筒] 清單。

  5. 結束這個瀏覽器。

若要從 SharePoint 網站移除 BDC 模型

  • 在 Visual Studio 的實驗執行個體,在功能表列上,選擇 [組建], [撤銷]。

    Visual Studio 會從 SharePoint 網站移除 BDC 模型。

若要從 Visual Studio 移除專案項目擴充功能

  1. 在 Visual Studio 的實驗執行個體,在功能表列上,選擇, [工具][副檔名和更新]。

    [副檔名和更新] 對話方塊隨即開啟。

  2. 在擴充功能清單中,選取 [外部資料清單產生器],然後選取 [解除安裝] 按鈕。

  3. 在出現的對話方塊中,選取 [] 確認您要解除安裝擴充功能。

  4. 選取 [立即重新啟動] 完成解除安裝。

  5. 關閉 Visual Studio (GenerateExternalDataLists 方案已開啟) 的實驗執行個體和執行個體的兩個執行個體。

請參閱

概念

擴充 SharePoint 專案系統

其他資源

建立商務資料連接模型

設計商務資料連接模型