先把问题描述一下:已把AD用户“User1”加到SharePoint站点中,然后进行如下类似操作:将“User1”从SharePoint站点中删除,将“User1”从AD中删除,在AD中增加一个新用户“User1”,在SharePoint站点中增加一个用户“User1”,这时,您会发现很有意思的问题:可能可以成功增加这个用户,但是这个用户始终无法登录到SharePoint站点中;或者根本增加不了这个用户到SharePoint站点中,提示您站点中已经存在这个用户了。
在上次CSDN站点的SharePoint技术聊天活动中,有参与的网友询问了类似的问题,由于当时我在聊天活动中无法给出非常详细的解释,所以只是给出了一个相关的链接。今天用这篇文章详细解释一下。
这个问题出现的原因,是出自SharePoint对于站点用户的存储机制所造成的。SharePoint站点用户信息保存在站点对应的内容数据库的UserInfo表中,如果站点管理员删除了站点中的某个用户,您可能会惊奇的发现,这个用户相应的记录并未从UserInfo表中删除,而只是将“tp_Deleted”这个列的数据进行了设置。(这种机制的原因所在是这条记录可能已经通过外键关联了其他表的其他记录,比如此用户编写的文档,所以将此记录直接删除是不可取的。)
在以后,如果站点管理员将一个同名的用户增加到这个站点中,由于UserInfo表中已经有这条用户记录的存在,所以SharePoint也只是将这条记录的“tp_Deleted”列的数据再进行设置。
这时候,问题就来了。在UserInfo表中,有一个“td_SystemID”列,这个列是用来记录这个用户的Security Identification Number(SID)的。我们在AD中删除一个用户,再新增一个同名用户,这先后两个用户的SID肯定是不同的。而SharePoint使用了这个“td_SystemID”列来识别用户,由于前后两个用户的SID肯定不同,所以SharePoint站点就“不认”在AD中重新增加的这个用户了。
解决方法就是把UserInfo表的“td_SystemID”列的数据和当前AD中的用户信息进行同步。在SqlServer中有一个SUSER_SID()函数,可以返回某用户的SID信息。在Dean的Blog上,他已经给出了一个完整的Sql语句,大家可以直接使用。
顺便题一下,在Deam的Blog上,他也描述了这个问题所造成的另外一个问题:如果我们备份站点的时候,将用户信息也一起备份了下来,在恢复到另外一个AD中时,如果站点用户有同名的现象,也同样会造成SharePoint“不认”这个AD用户。
Sql语句:
DECLARE @login varchar(40), @systemid varbinary(128)
DECLARE curUsers CURSOR LOCAL FOR
SELECT tp_login, tp_systemid FROM userinfo where tp_deleted = 0
OPEN curUsers
FETCH NEXT FROM curUsers INTO @login, @systemid
WHILE @@FETCH_STATUS = 0
BEGIN
PRINT 'Resetting user ' + @login + ' to new SID '
PRINT suser_sid(@login)
UPDATE UserInfo
SET tp_systemid = suser_sid(tp_login) WHERE CURRENT OF curUsers
FETCH NEXT FROM curUsers INTO @login, @systemid
END
CLOSE curUsers
DEALLOCATE curUsers
GO