Tuesday, November 27, 2012

Adding large numbers of users to a SharePoint group using PowerShell and DisplayName

I'm often asked to add a large number of people to a SharePoint group.  I'm never given the account names - instead, people often copy and paste from Outlook.  This is almost always in the following format:

Surname, Firstname; Surname, Firstname;

The same formatting is used in the SharePoint environment.  What I've done for small numbers of people is to use the standard SharePoint built-in web interface, but this is limited to 256 characters at a time, and is rather slow when working with more data than that.  So, I wrote two PowerShell scripts.  The first converts semicolon-seperated values into an entry on each line.

$x = ''
$x = Get-Content "SemicolonUsers.txt"
$x.replace("; ","`r`n") | out-File "Users.txt"

Quite simple, probably better ways of doing this, but it'll do for now.  Then, the other PowerShell script does the actual work, and outputs errors to Errors.log.


$SiteURL = "http://sharepoint/sitename"
$GroupName = "SharePoint Group Name"
$UserNames = "Users.txt"

function WriteOutputError($message)
{
    $host.UI.RawUI.ForegroundColor = "red"
    Write-Output($message)
    $message |Out-File Errors.log -Append
    $host.UI.RawUI.ForegroundColor = "white"
}

function ConvertUser($user)
{
$date = Get-Date -format T
    $search = New-Object DirectoryServices.DirectorySearcher([ADSI]“”)
    $search.filter = “(&(objectClass=user)(displayName=$user))”
    $results = $search.Findall()
    $count = $search.Findall().Count
    if($count -ne 1) {
        WriteOutputError('' + $date + ': ' + $count + ' results found for ' + $user + ': cannot add.')
    }
    else {
        foreach($result in $results)
        {
        $userEntry = $result.GetDirectoryEntry()
        ### We still have multiple inactive domains, so focus only on the current domain
   $accountName = "DOMAIN\" + $userEntry.sAMAccountName | Out-String
        #Write-Output($date + ': Adding ' + $accountName)
        WriteOutputError(Set-SPUser -Web $SiteURL -Group $GroupName -Identity $accountName)
        }
    }
}

function ConvertUsers
{
process
    {
        foreach($user In $_)
        {
            ConvertUser($user)
        }
    }
}

$date = Get-Date -format T
WriteOutputError('--------------------------------------')
WriteOutputError('' + $date + ": Starting new instance of AddUsers.")
WriteOutputError('' + $date + ": SiteURL: " + $SiteURL)
WriteOutputError('' + $date + ": GroupName: " + $GroupName)
WriteOutputError('--------------------------------------')

$host.UI.RawUI.ForegroundColor = "white"
Get-Content $UserNames | ConvertUsers 
$date = Get-Date -format T
WriteOutputError('--------------------------------------')
WriteOutputError('' + $date + ': Operation completed.')
WriteOutputError('--------------------------------------')
$host.UI.RawUI.ForegroundColor = "gray"

Wednesday, November 21, 2012

Hiding certain fields from document properties using jQuery

I have a document library that uses a few "hidden" fields during its various automated workflows.  However, for some of these fields, I can't mark them as hidden fields in the document library properties, possibly because they're related to a content type.  So I need to find another way to hide them from the user when viewing or editing document properties.

I found a solution on the blog SharePoint Sherpa - SharePoint 2007 – Hiding fields on NewForm.aspx and EditForm.aspx, the easy way - but wanted to use jQuery, so adapted it slightly.  Here is what I came up with.

1. Find the document library's DispForm.aspx and/or EditForm.aspx in the hidden Forms folder. This can be found in SharePoint Designer, selecting All Files for that site, and finding the Forms folder in the correct library.
2. Find the line:
<asp:Content ContentPlaceHolderId="PlaceHolderMain" runat="server">
3. Add the following code:


<script type="text/javascript">

_spBodyOnLoadFunctionNames.push("hideFields");

function hideFields() {

$('.ms-formlabel:contains("Field name 1")').parent().hide();
$('.ms-formlabel:contains("Field name 2")').parent().hide();
$('.ms-formlabel:contains("Field name 3")').parent().hide();
$('.ms-formlabel:contains("Document ID")').parent().hide();

}
</script>

4. Change "Field name 1" to the name of the first field you want to hide.  Do the same for the other lines, and add more lines as required.  (I've chosen to hide Document ID - it's in use throughout our SharePoint site, but I don't want the users to see it in this library)

I'm sure there are ways to further improve this, perhaps by putting the field names into an array, but this will do for now.

Wednesday, November 7, 2012

Removing a document/list web part from a page if the list is empty

I have a web part page which has a few document web parts - the web parts have filters applied so they only show relevant items to that particular user.  However, sometimes there are no items to show, and then the user is shown a box with nothing in it, apart from a typical SharePoint message about how there are no items.  This can look a bit messy.

I finally found a solution, posted by Mike Smith (of Mike Smith's Tech Training Notes), which uses JavaScript to remove the empty web part.  If I had spare time, I would rewrite this in jQuery (as everything else on my SharePoint environment is in jQuery), but it's perfectly functional as it is now.  Thanks Mike, you're a star!