Friday, December 27, 2013

SharePoint 2010 Document Property Promotion and Demotion


The Case of the Missing Office Document Properties in SharePoint 2010

Nice article about  Document Property Promotion and Demotion



Property promotion is the functionality in WSS that pulls the document metadata (e.g. Title, Subject, etc) from Office 2003/2007/2010 documents during upload and sets those values to their corresponding column in WSS.  Property demotion is just the opposite, if you update the document properties (like Title) via the WSS UI that property value is written back to the file.  

Basically, with property promotion/demotion, we keep the properties in the document and in WSS in sync.

More info

http://msdn.microsoft.com/en-us/library/office/aa543341(v=office.14).aspx

Wednesday, December 18, 2013

Enable/disable output caching in SharePoint 2010 using PowerShell script

A SharePoint Publishing site can also be configured to make use of the ASP.NET output cache to store rendered ASPX pages in memory. You can only make use of this cache when the Publishing features are activated on your site collection. This means that only publishing pages can be cached.
When a Publishing page is first requested, SharePoint assembles the page dynamically: it first fetches the page layout from the content database and then fetches the contents of the page. The page layout comes from the content database; the data on the page can be data coming from the content database or files already cached in the BLOB cache. Once the page is assembled, the resulting HTML stream is stored in the output cache. On a next request the HTML is served from the cache: the controls are not created, the page life cycle doesn’t start, and no code-behind is executed. The only things that are not covered by the output cache, are images and other resources like JavaScript files and CSS files. These need to be handled by other caching mechanisms.
This way pages are served more quickly and CPU load is reduced on the web front-end servers and on the SQL Server content database because pages won’t have to be reassembled on each request. Output caching is considered as one of the most performance improving techniques.

Here a a link to original article about Output Caching.


Here is a PowerShell script to enable or disable on output caching in SharePoint 2010 site:

$TotalCount = 0;
$UpdatedCount = 0;
#Initiate array for output export
$Results=@();


function SetCacheSettingsOnSite($site)
{
       if ([Microsoft.SharePoint.Publishing.PublishingWeb]::IsPublishingWeb($site.RootWeb))
       {
              $cacheSettings = new-object Microsoft.SharePoint.Publishing.SiteCacheSettingsWriter($site.Url);
        if($disable -eq $true)
             {
                     if($cacheSettings.EnableCache -eq $true)
                     {
                           $cacheSettings.EnableCache = $false;
                           $cacheSettings.SetAnonymousPageCacheProfileId($site,1);
                           $cacheSettings.SetAuthenticatedPageCacheProfileId($site,1);
                           $cacheSettings.Update()
                           if($output -eq $true) {Write-Host "De-activated output cache on site $site"}
                           Set-Variable -Name UpdatedCount -Value ($UpdatedCount+1) -Scope 1;
                           $OutputLog = New-Object PSObject -Property @{SiteUrl=$site.Url;Status="Deactivated";Time=Get-Date}; Set-Variable -Name Results -Value ($Results+=$OutputLog) -Scope 1;
                     }
                     else
                     {
                           if($output -eq $true) {Write-Host "Output cache already de-actived on site $site"}
                           $OutputLog = New-Object PSObject -Property @{SiteUrl=$site.Url;Status="Skipped. Already De-Activated";Time=Get-Date}; Set-Variable -Name Results -Value ($Results+=$OutputLog) -Scope 1;
                     }
              }
              else
              {
             
                     if($cacheSettings.EnableCache -eq $false)
                     {
                           $cacheSettings.EnableCache = $true;     
                           $cacheSettings.EnableDebuggingOutput = $true;
                           $cacheSettings.SetAnonymousPageCacheProfileId($site,1);
                           $cacheSettings.SetAuthenticatedPageCacheProfileId($site,4);
                           $cacheSettings.SetFarmCacheFlushFlag();                      
                           $cacheSettings.Update();
                           if($output -eq $true) {Write-Host "Activated output cache on site $site"}
                           Set-Variable -Name UpdatedCount -Value ($UpdatedCount+1) -Scope 1;
                           $OutputLog = New-Object PSObject -Property @{SiteUrl=$site.Url;Status="Activated";Time=Get-Date}; Set-Variable -Name Results -Value ($Results+=$OutputLog) -Scope 1;
                     }
                     else
                     {
                           if($output -eq $true) {Write-Host "Output cache already active on site $site"}
                           $OutputLog = New-Object PSObject -Property @{SiteUrl=$site.Url;Status="Skipped. Already active";Time=Get-Date}; Set-Variable -Name Results -Value ($Results+=$OutputLog) -Scope 1;
                     }
              }
       }
       $site.Dispose();
}

$Results | select-object SiteUrl, Status, Time | Export-csv -path "CachingActivationResults.csv" -notype
Write-Host "Done. Updated:$UpdatedCount  Total Processed:$TotalCount"  -ForegroundColor Green

$rootSite.Dispose()


Thursday, November 21, 2013

ERROR : Exception calling "AddWebPart" with "3" argument(s): "The file is not checked out. You must first check out this document before making changes


When you try to add web part on the page using  SPLimitedWebPartManager AddWebPart function you get the following error:

ERROR : Exception calling "AddWebPart" with "3" argument(s): "The file is not checked out. You must first check out this document before making changes



The error appears when  the page is checked out AFTER the SPLimitedWebPartManager is 
retrieved.

....................................................

$spWebPartManager = $spWeb.GetLimitedWebPartManager($pageUrl, [System.Web.UI.WebControls.WebParts.PersonalizationScope]::Shared)

$page.CheckOut()
....................................................

So the page must be checked out BEFORE the SPLimitedWebPartManager is retrieved.

$page.CheckOut()


$spWebPartManager = $spWeb.GetLimitedWebPartManager($pageUrl, [System.Web.UI.WebControls.WebParts.PersonalizationScope]::Shared)

Friday, October 25, 2013

Unshelve shelveset created from one branch to another


Unshelve shelveset created from one branch to another

When you need to unshelve to a different branchTFS power tool will help… 

The power tool command /> tfpt.exe unshelve can be handy for the following,
·         Allows a shelveset to be unshelved into a workspace with pending changes.
·         Merges content between local and shelved changes.
·         Allows migration of shelved changes from one branch into another by rewriting server paths.
·         Allows changes from an already-unshelved shelveset to be undone, cleaning up pending adds, and preserving other existing pending changes in the workspace.


Below is a list of features that are installed with the March 2011 Power tool installation.

Once the installation is complete, go to the cmd and type />tfpt.exe

we are interested in />tfpt unshelve to achieve unshelving of a shelve set to a different branch

Syntax
/>tfpt unshelve [shelvesetname[;username]] [/nobackup]
                     [/migrate /source:serverpath /target:serverpath]
shelvesetname          The name of the shelveset to unshelve
/nobackup              Skip the creation of a backup shelveset
/migrate               Rewrite the server paths of the shelved items
                        (for example to unshelve into another branch)
/source:serverpath     Source location for path rewrite (supply with /migrate)
/target:serverpath     Target location for path rewrite (supply with /migrate)
/undo                  Undo pending changes from an unshelved shelveset
/batchsize:num         Set the batch size for server calls (default 500)

Sample
/> tfpt unshelve “MySampleShelveNamel;AD\username” /migrate /source:”$/MyTeamProject/TheOrigionalBranch” /target:”TheDestinationBranch”
Catches
If you get the error => "unable to determine the workspace"

NOTE: Take the latest from your source control and “cd” to a local path that is mapped to the target workspace. Also ensure that the current working directory is mapped, you can run "tf workspace" and see if the target folders are mapped. 

Saturday, October 19, 2013

Files on flash drive changed to shortcut

Hi All,

Recently I had to deal with some type of virus, computer virus J. Usually I don’t have such problems, cause I am IT professional, but my parents do. J The problem with this virus took so much time (all my saturday evening) that I decided to write about these hours of fight, maybe this info saves someone’s time using my experience. 
My father called and said, that he could not open some critical Excel file on USB flash drive. I found some information on this site.

It wasn't problem with flash itself, but it seemed to me that it was a virus.
I had made the following steps:

FIRST STEP

If you did not format your flash drive, then check whether the files are in hidden mode. Then follow these steps:
·         Click on the link below and download the file "AutorunExterminator":
·         Extract it: Double-click on "AutorunExterminator"
·         Plug your pendrive now
·         This will remove the autorun.inf files from your pendrive and also from the drives
·         Click on Start > Run, type cmd and click OK
·         Here it is assumed your pendrive letter is G (change as necessary)
·         Enter this command.
·         attrib -h -r -s /s /d g:\*.*     
·         Press Enter
·         Now check for your files in on the pen drive
·         Now download the Malwarebytes' Anti-Malware from this link:http://en.kioskea.net/download/download-105-malwarebytes-anti-malware
·         Update it and perform a "Full Scan"
·         Note : The default selected option is "Quick Scan"

Here is some nice video: 

It helped me to clean virus from usb, but not to open the file with name  „Рарх>ды.xls”. It seemed that the virus somehow changed the file name with illegal character „>”

When I cliked on file I got a following message:

I used a different approaches, but could not rename the file name. After hours of searching internet, I found out info that files contain short names and can be read by using cmd command DIR /X
Here is this information with a link.

In Windows Command Shell with Short Filenames
The DOS command DIR/X shows short filenames, if they exist on your system.
$ cmd
c:\test> dir /x
 Volume in drive E is NUVOL
 Volume Serial Number is 80D3-A96D

 Directory of e:\tor\test

10/04/2009  05:15 AM    <DIR>                       .
10/04/2009  05:15 AM    <DIR>                       ..
10/04/2009  05:11 AM                 0 CLIP-2~1.MOV clip-2009-10-01 21;26;00.mov
               1 File(s)              0 bytes
               2 Dir(s)   5,201,670,144 bytes free
If they do exist, the REN command will move them to a new name; the new name can be a new (valid) long filename.
c:\test> ren CLIP-2~1.MOV "clip-2009-10-01_21-26-00.mov"
That's how to fix one.
To batch process all of them, you need to 1) grab the short filenames of all the files you want to move; 2) convert your listing into a batch file with the appropriate REN commands; and 3) run the resulting batch script. If you are comfortable with perl (or sed/awk, python, whatever), you can script this yourself, or you can craft it by hand from the listing you made in step 1.
But if DIR/X doesn't show the short filenames, your system has them disabled, and this solution won't help.


SECOND STEP
So I went to USB drive to the directory (using command prompt) to the file location, ran commnad DIR /X to get short filename.
My file short name was „DBF1~1.XLS„ 
H:\data>dir /x
 Volume in drive H has no label.
 Volume Serial Number is 105C-D911
 Directory of H:\data
2013.04.29.  08:07    <DIR>                       .
2013.04.29.  08:07    <DIR>                       ..
2013.10.14.  21:40           186 368 DBF1~1.XLS   Рарх>ды.xls

Then I ran the command H:\data>ren DBF1~1.XLS test.xls

FINAL STEP

And I can open the file.
My father was happy J
Good luck


Thursday, August 29, 2013

How to remove columns from web part view on a page


The code locates a landing page and search for web part called "Shared Documents". If page is not checked out, it checks out the page and delete "Version" column web part view (_UIVersionString)


private void UpdateViewOfWebpart(SPSite createdSite)
        {
            //// Sets the page url where the webpart is located
            string pageUrl = createdSite.RootWeb.RootFolder.WelcomePage;
            string targetwebpartTitle = "Shared Documents";

            //// Elevating permission
            SPSecurity.RunWithElevatedPrivileges(() =>
            {
                //// Creates a new SPSite instance for the sharepoint website
                using (SPSite spsite = new SPSite(createdSite.Url))
                {
                    //// Opens the SPWeb instance based on which the SPSite was initiated
                    using (SPWeb spweb = spsite.OpenWeb())
                    {
                        /// Gets the page SPFile object
                        SPFile pageSPFile = spweb.GetFile(pageUrl);

                        try
                        {
                            //// If file is not checked out then do a check out
                            if (pageSPFile.Level != SPFileLevel.Checkout)
                            {
                                pageSPFile.CheckOut();
                            }

                            //// Gets the SPLimitedWebpartManager instance from the page
                            SPLimitedWebPartManager limitedWebpartManager = pageSPFile.GetLimitedWebPartManager(System.Web.UI.WebControls.WebParts.PersonalizationScope.Shared);

                            //// A temp value to use inside the following for loop
                            string currentWebpartTitle = string.Empty;

                            foreach (System.Web.UI.WebControls.WebParts.WebPart webPart in limitedWebpartManager.WebParts)
                            {
                                //// Ignore the closed webpart
                                if (!webPart.IsClosed)
                                {
                                    //// Reads the webpart title in the iterated loop
                                    currentWebpartTitle = webPart == null ? string.Empty : (webPart.Title == null ? string.Empty : webPart.Title);

                                    //// Checks whether current webpart title in iterated loop is the targeted webpart or not
                                    if (currentWebpartTitle == targetwebpartTitle)
                                    {
                                        //// With the help of reflection gets the View field’s info
                                        System.Reflection.FieldInfo viewFieldInfo = webPart.GetType().GetField("view", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance);

                                        //// Ignore and continue loop if view field is null
                                        if (viewFieldInfo == null)
                                        {
                                            continue;
                                        }

                                        //// Cast the view field’s value which was retrieved using reflection to the SPView
                                        SPView view = viewFieldInfo.GetValue(webPart) as SPView;

                                        if (view.ViewFields.Exists("_UIVersionString"))
                                            view.ViewFields.Delete("_UIVersionString");

                                        /// Updates the view
                                        view.Update();

                                        //// This is optional, need not have to save changes to webpart, but just to confirm
                                        limitedWebpartManager.SaveChanges(webPart);

                                        break;
                                    }
                                }
                            }
                        }
                        catch (Exception ex)
                        {
                            throw ex;
                        }
                        finally
                        {
                            if (pageSPFile.Level == SPFileLevel.Checkout)
                            {
                                pageSPFile.CheckIn("Removed Version column", SPCheckinType.MajorCheckIn);
                            }
                        }

                    }
                }
            });

        }

PowerShell script does the same

$deleteField = "_UIVersionString"
$whereToLook = "Shared Documents"

function HasPageWebPartField()
{
      param
      (
      [Microsoft.SharePoint.SPFile]$Page,
      [Microsoft.SharePoint.SPWeb]$Web
      )          
     
      $localWebVariable = Get-SPWeb -Identity $web.Url     
    $checkWpm = $localWebVariable.GetLimitedWebPartManager($page.Url, [System.Web.UI.WebControls.WebParts.PersonalizationScope]::Shared)
      $checkWp = $checkWpm.WebParts | Where-Object { $_.Title -eq $whereToLook }
      $checkList = $localWebVariable.Lists | Where-Object { $_.Title -eq $whereToLook }
      if ($wp.ViewGUID -ne $null -and $wp.ViewGUID -ne "")
      {
            $checkView = $checkList.Views[[Guid]$checkWp.ViewGUID]
            $returnVal = $checkView.ViewFields.Exists($deleteField)
      }
      else
      {
            $returnVal = $false
      }
      $checkWpm.Dispose()
      $localWebVariable.Dispose()
      return $returnVal
}

$web = Get-SPWeb $_.URL
      
       if ([Microsoft.SharePoint.Publishing.PublishingWeb]::IsPublishingWeb($web))
       {
              [Microsoft.SharePoint.Publishing.PublishingWeb]$publishingWeb = [Microsoft.SharePoint.Publishing.PublishingWeb]::GetPublishingWeb($web)
              $page = $publishingWeb.DefaultPage
              if ($page.CheckedOutDate -eq $null)
              {
                     $hasField = HasPageWebPartField -Page $page -Web $web
                     if ($hasField)
                     {
                     $page.CheckOut()
                     $wpm = $web.GetLimitedWebPartManager($page.Url, [System.Web.UI.WebControls.WebParts.PersonalizationScope]::Shared)
                            $wp = $wpm.WebParts | Where-Object { $_.Title -eq $whereToLook }
                           $list = $web.Lists | Where-Object { $_.Title -eq $whereToLook }
                           $view = $list.Views[[Guid]$wp.ViewGUID]
                           $view.ViewFields.Delete($deleteField)
                           $view.Update()
                           $wpm.SaveChanges($wp)
                           $page.CheckIn("Removed Version column. Update via PowerShell",[Microsoft.SharePoint.SPCheckinType]::MajorCheckIn)
                     }
              }
              else
              {
                     $message = "Web " + $web.Url + " page " + $page.Name + " was checked out - to be processed manually."
                     Write-Host $message -ForegroundColor Red
                     $script:fileContents += ($message)
                     $script:fileContents += ("`r`n")
              }
       }

      $web.Close()