Monday, November 15, 2010

PowerShell: file renaming en-masse

You may have come across the following error message when uploading files in SharePoint:
The file name is invalid or the file is empty. A file name cannot contain any of the following characters: \ / : * ? " < > | # { } % ~ &
But what if you have hundreds or thousands of files that DO include one or more symbols, and you need to move them onto SharePoint?
The following PowerShell script will replace a string in a filename with another string you provide.  It doesn’t alter file extensions or folders.  The script can be executed with command line parameters, however if they are not provided, it will prompt you for input.  The following parameters are used:
  • The directory e.g. “C:\test”
  • The text to find e.g. “&”
  • The replacement text e.g “and”
  • An optional switch that specifies whether to recurse through subfolders: –recurse
An example of how to use this script would be:
  • fileRenamer.ps1 “C:\test” “&” “and” –recurse
If you execute the script with no parameters, it will ask you to enter the directory, find, and replacement values in turn, but it won’t ask for whether you’d like to recurse.  It will default to non recursive.

Error Handling

The only issue this script handles is when the provisional new file name for a file already exists e.g. you are changing Q&A.doc to QandA.doc, and this filename is already in use.  In this instance, the script will notify the user that the rename operation has been cancelled and summary information is added to the end of the script.

Script Output

The script prints its progress to the console, and also provides some summary information at the end:
image

Disclaimer

Use at your own risk. I will not be held responsible for any actions and/or results this script may cause.  If you choose to use this script; test it first, and only run on directories/files with backups as the implications of renaming large numbers of files are serious and the operation cannot be undone.

The Code

Paste this into a new file and save it as “fileRenamer.ps1” or similar.
param(
    [switch]$recurse,
    [string]$directory = $(read-host "Please enter a directory"),
    [string]$find = $(read-host "Please enter a string to find"),
    [string]$replace = $(read-host "Please enter a replacement string")
)

# Startup text
echo "This script will replace words in files of any type.  It will not modify file extensions."
echo ""
echo "WARNING: This action cannot be undone; use at your own risk!"
echo ""

# Setup variables
$modifiedcounter = 0
$counter = 0
$exceptioncounter = 0
$exceptionfilenames = ""
$files = ""

echo "Replacing text '$find' with '$replace' in all filenames..."
echo ""

if ($recurse)
{
    # Grab all files recurse
    $files = get-childitem $directory -include *.* -recurse
}
else
{
    $files = get-childitem $directory *.*
}

foreach ($file in $files) {
    $filename = $file.Name
   
    # Only run if this is a file
    if ($filename.IndexOf('.') -gt 0)
    {
        $name_noextension = $filename.SubString(0, $filename.LastIndexOf('.'))
        $extension = $filename.SubString($filename.LastIndexOf('.'), $filename.Length-$filename.LastIndexOf('.'))

        echo ("Filename:          " + $file.FullName)
        #echo "Extension removed: $name_noextension"
        #echo "Extension:         $extension"
       
        # If there is a match then attempt to rename the file
        if ([regex]::IsMatch($name_noextension, ".*$find.*")) {
            # Change the filename
            $name_noextension = $name_noextension.Replace($find, $replace);
            $newname = $name_noextension += $extension
           
            #echo "New name:          $newname"

            # Test to see whether a file already exists
            if (Test-Path ($file.DirectoryName + "\" + $newname))
            {
                # A file already exists with that filename
                echo ("Action:            A file exists with the name " + ($file.DirectoryName + "\" + $newname) + " so this action has been cancelled.")
                $exceptioncounter++
                $exceptionfilenames += ($file.DirectoryName + "\" + $newname)
            }
            else
            {
                # Rename the file                
                rename-item $file.FullName -newname $newname
                echo "Action:            Filename modified from $filename to $newname."
                $modifiedcounter++
            }
        }
        else
        {
            echo "Action:            None";
        }   

        $counter++
    }
}

# Output the results
echo ""
echo "$modifiedcounter of $counter filenames modified."
echo "Exception count: $exceptioncounter"

# If there were exceptions then output that as well
if ($exceptioncounter -gt 0)
{
    echo ""
    echo "The following files were not modified as files already existed with their provisional new names:"
    echo $exceptionfilenames
}

Read-host "Press enter to quit"

Feedback

Please let me know if you spot any errors in this script or ways in which it could be improved!

Monday, November 8, 2010

SharePoint 2010: RSS settings missing in list settings page

When you view the list settings in the ribbon of a library or list, you may notice that the RSS Feed button is disabled:

image

You’re first port of call may be the List/Library settings page, where you would find the RSS settings link under the Communications area:

image

However, if this is missing, it’s likely that RSS is disabled at the site or site collection level.  Moving up the chain, if you view the site settings you might find an RSS link under Site Administration:

image

If this link is missing, try looking up at the site collection level, where there is another settings page allowing you to enable RSS for the whole site collection:

image

Enable this, then double check your site RSS settings, then you should have an enabled RSS button on your lists and libraries!

image

Wednesday, November 3, 2010

SharePoint 2010 Label Error: The Policy Label Configuration is Invalid

I’ve recently been working a lot around Information Management policies including Labels.  A Label Information Management policy allows you to add force Office users to add a label into a document such as Word or Excel. 
A label is composed of text and fields from your associated content type.  The requirement was to have the following format on the label:
  • {Protection Level} {Caveat}
After saving this policy, I opened a document of my content type in Word and was presented with the following message":
The Policy Label configuration is invalid.  Contact your Policy Administrator
image
Well it turns out you can’t format your label with two content type fields on the same line with only blank space characters in between – hopefully this will be improved in the next update…
The following does work as alternatives:
  • {Protection Level} – {Caveat} (a character in-between the two fields)
  • {Protection Level} \n {Caveat} (note this places the Caveat field on a new line)

Update

Well it turns out you can use the ASCII tab escape character "\t":
  • {Protection Level} \t {Caveat}