星星之火

燎原之势不可挡
  博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

----前言

这段时间项目出在验收阶段,不是很忙,就潜心把SharePoint学一下,不求有多深刻,初衷只是先入门再说。后续会发布一系列的学习总结。主要学习的书籍为《SharePoint2010 最佳实践》,个人觉得这是SharePoint入门级学习最好的书,很多很基础但实用的东西都讲的很详细,读过之后会让人对整个SharePoint有一个更为客观和准确的认识。但是不得不提的是书中的小错误还是很多的,有很多的代码拼写错误/语句逻辑错误,但是总得来说还不错,不影响阅读。

总结的目的主要是用来做学习的记录和备注,方便以后回过头来温习和查阅,希望能给大家带来一些帮助,记录中有不对的地方还请大家多多指正。

 

第1章 SharePoint Foundation开发基础

1.1 SharePoint 2010基础概念

1.1.1 服务器场

简单的理解,服务器场就是一系列服务器的集合。在简单的应用里,SharePoint 2010 的所有功能可以部署在单一的服务器里;在生产环境里,SharePoint 2010的运行环境可以由多台服务器组成一个服务器场,包括Web前端服务器、应用程序服务器(包括爬网服务器、查询服务器等)、数据库服务器。

Web前端服务器:包括处理所有请求的服务器和存储索引的Web服务器,其中处理请求的服务器可以通过负载平衡器进行统一访问定位

应用程序服务器:包括了爬网服务器组、查询服务器组、其他应用程序服务器组(如托管元数据服务、应用程序服务器:Excel计算服务等),以及专属的沙盒解决方案应用程序服务器

数据库服务器:包括了存储爬网后供搜索用的搜索服务器,存储站点集内容的内容数据库服务口,存储其他内容比如管理站点配置数据的其他数据库服务口

1.1.2 Web应用程序

Web应用程序扩展了IIS网站,并因而也具有IIS网站一样独立的运行端口、独立的身份认证体系、独立的应用程序池、单独的web.config文件等,一个Web应用程序通常由若干个网站集组成,SharePoint 2010使用内容数据库来存储网站集,一个内容数据库可以包含若干个网站集。

对从ASP.NET转到SharePoint的开发者来说,可以将SharePoint Web应用程序理解成第一个大规模的 ASP. NET 应用程序,如前文所述,每个SharePoint Web 应用程序都有自己的如同典型的 ASP.NET 应用程序一样的 web.config文件。与 ASP.NET 网站不同的是,每一个网站集并不拥有独立的配置文件,SharePoint Web 应用程序下唯一的一个 web.config为所有该 Web 应用程序下的网站集提供配置信息,即便该 Web 应用程序下面可能有数百个网站集存在。一个典型的 SharePoint 2010 服务器场至少有两个 Web 应用程序,一个是中央管理站点,另外一个开放给普通用户使用。

1.1.3 服务应用程序

SharePoint 2010 引入了服务应用程序的概念,在SharePoint 2010 里,服务应用程序可以在运行于不同的 Web 应用程序下,甚至不同的服务器场的不同站点间共享数据。新的服务应用程序架构也使得SharePoint 2010 性能得到进一步扩展,因为服务应用程序可以安装在独立于 Web 前端服务器的专属应用服务器之上。服务应用程序的一个很重要的特点是它在架构上的是它在架构上的解耦,在简单的服务器场配置里,服务应用程序可以安装在 Web 前端服务器上。在大型的服务器场配置里服务应用程序可以安装在单独的应用程序服务器或者应用程序服务器组里

在SharePoint2010里常见的服务应用程序有以下几个:

商业连接服务

用户档案服务:管理用户档案、组织档案、我的站点、社交标签

搜索服务:

托管元数据服务:

1.1.4 网站集和网站

网站集是一个数据存储和权限分配的独立单位,网站集可以包含若干个网站,每一个网站集都必须建立在某个Web应用程序下面,但是网站不可以单独建立在Web应用程序下面,必须建立在网站集的下面。

网站集的存在有很多种原因,一个是因为其独立的权限控制体系,每个网站集之间的权限都是独立的,站点集(站点集和网站集是同一个概念)管理员拥有网站集的最高权限,他可以在该网站集内创建不同的权限组,创建站点集的时候SharePoint会默认配置三个组,

网站所有者:拥有略低于站点集管理员的权限。  

内容贡献者:可以在网站里创建文档库、列表等内容并具有创建和修改文档等权限。   访问者:拥有在站点集内只读的用户权限

另外一个原因是可以提供站点集别的数据备份和还原

1.1.5 字段类型、网站栏和内容类型

字段类型包括单行文本、多行文本、数字、货币等各种类型,可以将其理解成数据库表的各种字段类型,字段类型可以被添加到列表、文档库等数据存储结构中。字段类型可以扩展。

通过字段类型可以创建栏,栏可以理解为字段类型的实例,在列表里创建的栏只能供对应的列表使用,在网站集级别创建的栏可以供网站集内所有列表、文档库等使用

内容类型是网站栏的集合,内容类型可以理解成一个一个的模板,比如员工内容类型就包括员工姓名、生日、邮件地址等网站栏的模板,网站栏在网站集级别创建,并可以单独添加到每一个列表或者文档库。在SharePoint 2010里引入了外部内容类型的概念,在SharePoint  Designer里可以创建外部内容类型,将外部系统的数据映射到SharePoint里面来。

SharePoint 2010对字段做了功能上的改进,最突出的两点是增加了对字段值唯一性的设置,以及对字段值进行校验设置的功能。通过唯一性设置可以指定在本列内的值必须唯一,如果添加重复值时浏览器会提示内容重复;通过校验功能可以指定在客户端配置字段值的检验规则,比如要求是小写字母等

1.1.6 列表和文档库

列表是SharePoint里用来存储数据的基本结构,列表可以理解为数据库的表,用户可以在列表里面任意添加栏,就如同数据库表的一个列,也可以将已经包含了若干个网站栏的内容类型直接添加到列表里,列表可以同时支持多个内容类型。

在SharePoint里通常可以看到很多种类的列表,比如通知、任务、日历、讨论版、联系人、链接、调查等都是列表的一种

文档库是一种特殊的列表,与列表的主要不同在于文档库的每条记录有且仅有一个文件存在,而列表里可以没有文件或者有若干个文件作为附件存在。文档库和列表都支持版本控制。

文档库也有各种呈现形式,比如表单库、图片库、幻灯片库、维基页面库等都是文档库的一种。

在SharePoint 2007 里所有的文档都是直接存在文档库里或者存在于文档库里的某个文件或者子文件夹里,每个文档都具有自己单独的属性。在SharePoint 2010里引入了文档集的概念,文档集指的是一组属性相同的文档,比如销售类、技术类等文档集具有相同的属性特征,只需要维护一套属性即可,

唯一的文档Id

1.2 SharePoint Foundation的服务端对象模型

1.2.1 概述

SharePoint 2010服务器端对象模型是SharePoint开放给用户的编程接口,对SharePoint的数据访问以及操作都需要通过这些接口来进行访问,从ASP.NET开发转过来的开发者一定要避免直接访问数据库的冲动,所有对SharePoint的定制都需要通过对象模型来操作,尽管有时候直接访问数据库操作数据可以绕开SharePoint产品的限制。

在Visual Studio 2010里开发SharePoint项目有两点尤其需要注意:

第一点是项目配置里一定要选择.NET 3.5作为目标框架

对很多项目类型,Visual Studio 2010默认使用.NET 4.0作为目标框架;

第二点是目标平台要选X64兼容

还有需要注意的地方是,通过服务器端对象模型开发的程序必须在Web前端服务器或者应用程序服务器上才能运行。

1.2.2 代码示例

using Microsoft.SharePoint; 

namespace HelloWorld{    

class Program    {        

static void Main(string[] args)       

{            

const string siteURL = "http://localhost";  

using (SPSite site = new SPSite(siteURL))

{//获取对站点集对象的引用                

SPWeb web = site.RootWeb;//获取对根站点的引用                

foreach (SPList list in web.Lists)

{//遍历根站点下所有的列表

if (!list.Hidden)

{//如果该列表不是隐藏列表

Console.WriteLine(list.Title);

}}}}

 

上述代码会建立对http://localhost网站集的引用,并打开其根站点(网站),紧接着会遍历其中的所有列表,如果该列表是非隐藏列表,则将其标题输出到控制台窗口。注意,在创建对网站集的引用SPSite对象时,一定要在使用完成后对对象予以释放,SPSite使用了很多非托管资源,如果不释放会造成内存的泄露。

SharePoint可以通过代码修改列表、文档库(记住文档库也是一种特殊的列表),设置其属性为Hidden。生效后用户将不会在浏览器窗口看到对相应列表的链接,但用户仍然可以使用绝对URL查看相应列表

1.2.3 站点集和站点

站点集和站点是SharePoint开发容易搞混的两个概念,站点集对应前面所述的网站集,站点对应的是前面所述的网站集下的网站,但是站点集的对象是Microsoft.SharePoint. SPSite,而站点对应的对象是Microsoft.SharePont.SPWeb

只有在创建了站点集对象的引用后才能创建对站点的引用

有如下常用方式:

SPWeb web = site.OpenWeb(“WebURL”); //返回某个指定站点的SPWeb对象 SPWeb web = site.RootWeb; //返回根站点的SPWeb对象

//遍历站点集下的每一个站点

SPSite site = new SPSite(“SiteURL”);

//调用SPSite的AllWebs成员返回所有SPWeb的集合SPWebCollection

foreach(SPWeb web in site.AllWebs){    

Console.WriteLine(“Web site: {0}”, web.Url);    

web.Dispose();//通过AllWebs取得的SPWeb对象要注意释放

}     

 

                      

如果代码运行在SharePoint  Foundation 的环境下,比如运行在某个SharePoint站点画面内的Web部件或者跟某个列表绑定的事件处理等情况下,可以直接调用上下文环境获得对站点集或者站点对象的引用,但请注意从上下文中获得的站点集或站点对象不应释放,否则会造成程序异常运行。

SPSite site = SPContext.Current.Site; //获取当前所在站点集对象

SPWeb web = SPContext.Current.Web; //获取当前所在站点对象

1.2.4 列表和文档库

列表是存储数据的容器,在对象模型里对应的是Microsoft.SharePoint.SPList,列表的集合对象是Microsoft.SharePoint.SPListCollection,假定我们已经获得对SPWeb站点对象的引用Web对象,可以通过以下方法获得对列表对象的引用:

SPListCollection lists = web.lists; //获取站点下的所有列表集合

SPList list = lists[index]; //通过索引获得对列表对象的引用

SPList list = lists[“Announcement”]; //通过列表名获得对对象的引用

//通过列表ID获得对对象的引用

Guid listID = new Guid(“{1893wr25-n900-e230-606b-df14bbi4512}”);

SPList  list = lists[listID]; //通过列表URL获得对对象的引用

SPList list = web.GetListFromUrl[“http://localhost/lists/announcements/allitems.aspx”]; //通过服务器相对路径获得对对象的引用

SPList  list = Web.GetList[“/lists/announcements”];

SharePoint2010 里增加了一个新的方法

Microsoft.SharePoint.SPListCollection.TryGetList (string listTitle),
此方法在获取列表失败后返回NULL,便于之后对返回的列表对象进行判断,是否继续执行代码而不是直接跳到异常处理代码块。 SPListCollection lists = web.lists; SPList list = lists.TryGetList(“Announcements”);

 

如同前面在介绍功能的时候介绍到的,文档库是一种特殊的列表,事实上从对象模型角度,我们更能这么说,查看SharePoint  Foundation  API 文档,我们会发现文档库对象 Microsoft.SharePoint.SPDocumentLibrary正是继承自列表对象Microsoft.SharePoint.SPList。 在大多数的情况下,我们都可以直接通过SPList对象来操作文档库,只有在特殊的情况下,例如下例所示,需要获取某文档库内所有被签出的文件列表的时候,我们才需要用到SPDocumentLibary对象。

SPWeb web = SPContext.Current.Web ;

//注意SPWeb没有直接返回文档库对象的方法,需要先获取

SPList SPList list = web.Lists[“Shared Documents”];

//将列表对象转换成文档库对象

SPDocumentLibrary doclib = (SPDocumentLibrary)list;

//获取所有被签出的文件

IList<SPCheckedOutFile> checkedOutFiles = doclib.CheckedOutFiles;

 

1.2.5 列表项和文件

获取了列表对象后,我们要对存储在列表的数据进行操作了,列表里的数据由一条一条的记录组成,而记录对应的对象就是Microsoft.SharePoint.SPListItem,相应的记录集合对应的对象是Microsoft.SharePoint.SPListItemCollection

SPList list = SPContext.Current.Web.Lists.TryGetList("Announcements");

if (list == null){     

//做一些处理(比如提示错误消息)后返回;    

return;

}

 //创建新的记录

SPListItem newItem = list.Items.Add();

newItem[["Title"] = "标题";

 newItem["Body"] = "正文";

newItem.Update();

//更新记录

SPListItem updateItem = list.Items[0];

updateItem["Title"] = "更新后的标题";

updateItem.Update();

//删除记录 list.Items[0].Delete();

上述代码在获取了列表对象后,针对列表对象做了增加记录、更新记录以及删除记录的三种基本操作。注意到在进行数据的添加或者更新后,要调用SPListItem.Update()方法提交数据更新,
否则对于数据不会被持久化的数据库,在下次读取该数据的时候还是会读到更新前的内容。特别要注意的是对SPList.Items属性的调用,该调用将返回包含所有记录所有字段内容的数据,
在大数据列表中这样的操作将会导致性能上的问题。 如同列表一样,获取列表记录的方法也有多种: SPList list = SPContext.Current.Web.Lists.TryGetList("Announcements"); //通过索引获取列表记录 SPListItem item1 = list.Items[index]; //通过列表记录ID获取记录 SPListItem item2 = list.Items.GetItemById(1); SPListItem item3 = list.GetItemById(1);

 

上述例子中无疑item3 的获取方式要比item2 的获取方式要好,因为它避免了对Items方法的调用,减少了对内存的占用。

在获得列表记录后,可以通过File属性获取文件对象。但是需要留意的一点是,也可以通过SPWeb对象来直接获取文件,理解这一点要明白文档库实际上只是SharePoint站点里的一个抽象层,这就意味着如果要访问文档库里的某个文件,实际上是在访问SharePoint站点里某个指定位置的文件,因此我们可以通过两种方式来对文件进行操作。

首先,我们尝试通过SPList对象来对文件进行操作:

using (SPSite site = new SPSite("http://localhost"))

{    

SPWeb web = site.RootWeb;    

SPList list = web.Lists.TryGetList("Shared Documents");    

if (list == null){        

Console.WriteLine ("Shared Documents not exist!");        

return;    

}    

//读取文档内容到字节集中    

byte[] fileData = System.IO.File.ReadAllBytes(@"c:\test.txt");    

//调用SPFileCollection对象的Add方法上传文档    

SPFile newFile = list.RootFolder.Files.Add("test.txt", fileData);

}

 

上例中我们首先获得了SPList对象,然后通过RootFolder返回列表下的根文件夹对象,再通过其返回所有的文件集合对象SPFileCollection,之后调用SPFileCollectioin.Add (string fileURL, byte[] file)  将文件写入文档库中

接下来是从文档库读取文件的例子:

using (SPSite site = new SPSite("http://localhost"))

{    

SPWeb web = site.RootWeb;    

SPList list = web.Lists.TryGetList("Shared Documents");    

if (list == null)   

{

Console.WriteLine("Shared Documents not exist!");        

return;    

}    

//获得对列表记录的引用    

SPListItem item = list.GetItemById(1);    

//获得SPFile对象的引用    

SPFile file = item.File;    

//将文件内容读到字节集合里    

byte[] fileData = file.OpenBinary();    

//由于该文件是纯文本文件,可以通过逐字的方式输出    

foreach(byte byt1e in fileData)

{         Console.Write(byt1e);     } }

 

1.2.6 开发人员面板

SharePoint 2010的新功能——开发人员面板,这个功能激活后会在画面的下部输出画面加载的细节信息。这个功能对于开发人员还有SharePoint管理人员会有用,它可以帮助分析画面的性能问题等。

这个功能默认是不用激活的,如果需要激活,在SharePoint  2010里,通常建议通过Windows  PowerShell来激活,这里提供一个简单的传统的STSADM方式来激活

可以在

C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\14\BIN找到。 开发人员面板有四种模式,在命令窗口运行STSADM命令可以设置不同的状态。   打开模式:这种模式下每个页面加载时都会在画面下部加载此面板。

命令:stsadm -o setproperty -pn developer

管理模式:这种模式下不会加载此面板。

命令:stsadm -o setproperty -pn developer-dashboard -pv Off  

按需模式:这种模式下在画面下部会显示一个图标,单击此图标可以显示或隐藏开发人员面板。

命令:stsadm -o setproperty -pn developer-dashboard-pv OnDemand  

混合模式:当某些系统计数器指标超过时显示面板。

命令:stsadm-o setproperty-pn developer-dashboard-pv expensiveoperationly

注意,此设置是在服务器场级别的,也就是更改设置以后对一个服务器场内的所有Web应用程序都会起效

1.3 SharePoint解决方案

1.3.1   什么是SharePoint解决方案

通常我们将要部署到生产环境的一系列文件的集合称之为一个解决方案,这个解决方案里面可能会包含诸如Web部件、工作流、列表定义等各种功能。SharePoint最终发布到生产环境部署的通常是一个以wsp为后缀的安装包,这个wsp包可以直接通过管理中心上传并部署,也可以通过命令行以及PowerShell的方式来发布。这样做得好处是我们只需要在一台Web前端服务器做部署,SharePoint会将包内的内容自动分发到需要部署的其他前端服务器以及应用程序服务器上。

SharePoint的WSP解决方案包实际上是一个CAB文件,将文件后缀从.wsp 改为.cab后,我们可以直接单击进去查看包内的详细内容。

1.3.2   了解SharePoint系统根目录结构

       实际上不仅是Layouts,SharePoint的绝大多数系统文件、资源都部署在一个称之为根目录的地方:

   C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\14

   我们稍后会接触到可视化Web部件开发等产生的中间文件,比如用户自定义控件(.ascx)文件、Feature定义文件等都会部署在这个文件夹下的某个子文件夹里。而 对   其中的一些系统文件,比如Layouts下的settings.aspx系统页面的修改都会在整个服 务器场范围内产生影响。因此,一方面对这个文件夹下面已经存在的文件修改一定要 非常谨慎,要考虑到今后微软推出的补丁或者SP有可能会去更可能会去更改这些页面和我们的修改,也因而存在冲突的可能;另一方面,我们在部署自定义的文件时,比如用户控件、图片、自定义字段、Feature等,要按照SharePoint的方式部署在相应的文件夹下

                       

1.3.3  Feature

      要了解SharePoint的解决方案包,很重要的一点是要理解Feature,Feature可以理解为“功能”,我们将需要发布给用户使用的工作流、Web部件等都封装在Feature里,用户可以通过激活该Feature来获得对新功能的使用,也可以通过停用来停止对新功能的使用。

      

一个Feature 定义文件允许包含多个Element清单文件。

 

 

这一章就总结到这里了,主要是让大家对SharePoint有一个层次上的概念和更为客观的认识,所以介绍一下概念型的东西多一些。希望能给大家一些帮助。