Archives for category: SharePoint

An issue we recently experienced with our SharePoint 2010 document sharing site had to do with List Item ECB Context Menu hover positioning on large document libraries that required you to scroll down to see all items.  When you hover over a list item, the expected behavior is that the context menu would be displayed to the right of the document title, and this is the case for the most part, until you have to scroll down to see a document.  Then when you hover over the item, the context menu appears farther up in the library, as depicted in the following example:

example

Not pretty.  Sad smile

Upon further research, I discovered that this had to do with the fact that SharePoint 2010 attempts to override default browser scrolling.  By reading the following blog article by Kyle Schaeffer, I was able to override SharePoint 2010’s default scrolling behavior, which in turn fixed the above SharePoint list item context menu positioning issue.

Thank you, Kyle!

Advertisements

I recently went through the exercise of upgrading our internal SharePoint environment from 2007 to 2010.  Some of these sites were heavily customized and while we did experience our share of issues, all-in-all it was definitely not as painful as I initially predicted.  And I have to say that my favorite feature of SharePoint 2010 BY FAR is the ability to manage your SharePoint sites and lists using PowerShell.  I cannot adequately described how many times PowerShell has rescued me!

One issue we have had right off the bat had to do with a very large site collection used primarily for collaboration and document storage.  While the site collection was entirely made up of custom team sites, each created from a custom template (or now with SharePoint 2010 a custom solution), this site used a custom master page and is heavily branded.

The site collection contains thousands of sites, each containing multiple document libraries.  Now in SharePoint 2010, when a user attempts to upload a document, a popup dialog is displayed.  Because each of our documents contain a large number of metadata that are required based on the document type, the popup dialog form was long.  Perhaps as an unintended consequence of our branding, the popup dialog was cutting off the bottom part of the form, and our users were not able to successfully upload their documents.

dialog

The quickest way to resolve this is to go into Library Settings –> Advanced Settings, and in the Dialogs section, check No for “Launch forms in a dialog?”.

advancedsettings

By doing this, SharePoint will navigate to a full page to allow you to modify the document attributes.  Perhaps a little too much like SharePoint 2007, but definitely a lot less incident prone and an interface that our SharePoint users are a little more familiar with using.

fullpage

That solution is fine for one-off fixes, but I was faced with the daunting task of making this fix for thousands of document libraries in hundreds of sites.  Surprised smile

That’s where PowerShell comes in.  I was able to write a short little script in PowerShell that iterated all of the sites in my site collections, iterated all of the lists in each site, determined evaluate the document library’s current setting, and update the setting if necessary.

The setting is called NavigateForFormsPages and the value it stores is actually the opposite of what we check in the interface.  For example, if the value is set to False, then the Document Library will open a modal dialog, but if the value is set to True, then the Document Library will open a full page.  So in this case, we want to evaluate each Document Library and make sure the value is set to true.

# retrieve site collection database
# replace SP2010_DB_Content with your content database name
$db = Get-SPContentDatabase SP2010_DB_Content

# iterate all sites in the collection
$db.Sites | Get-SPWeb -limit all | ForEach-Object {

# iterate all lists in the sites
foreach ($list in $_.Lists) {

# evaluate NavigateForFormsPages advanced setting
# if the value is false, we want to set it to true

if (!$list.NavigateForFormsPages)
{
# output the site url, title, and NavigateForFormsPages
# for your record

Write-Host “$($_.url) – $($list.title) – $($list.NavigateForFormsPages)”

        # set the NavigateForFormsPages value to true
$list.NavigateForFormsPages = $true

        # update the list
$list.update()

        # output the site url, title, annd NavigateForFormsPages
# to make sure the value has changed

Write-Host “$($_.url) – $($list.title) – $($list.NavigateForFormsPages)”
}
}}

That’s it!  Smile

I ran into this issue with a heavily branded SharePoint site we recently upgraded to SharePoint 2010.  I noticed the branding elements were being included in the SharePoint dialog.

This is definitely not what we intended for our SharePoint dialogs.  Thankfully, SharePoint makes it easy to strip those elements out by adding the following class to any element you want left out:

<!– use s4-notdlg for any element you do not wish to include –>

Now our dialogs are much cleaner!  Smile

dialog2

When I am populating a data snapshot table with a set of calculations for any given month, I may in some cases blow away any existing records for that month and start with a clean slate.

The only thing that bothered me was that I would end up with huge gaps in my identity keys.  This resets the identity’s seed value, so that the next inserted row will pick up right where the last identity field left off.

I use this a lot for my data snapshot tables, but as a general rule, it’s not a good idea to reseed an identity column in a production table without some serious checks and balances.

Here is the statement, where the item in single quotes is the name of the table you want to RESEED:

DBCC CHECKIDENT (‘my_report_table’, RESEED)

You can also explicitly set the next seed value with this statement:

DBCC CHECKIDENT ('my_report_table', reseed, 1001)

I needed to quickly update a User Profile photo using PowerShell and was running the following code snippet for PowerShell as a farm administrator:
$mySiteUrl = “http://mysite.mydomain.com&#8221;;
$mySiteProperty = “PictureUrl”;
$userAccount = “contoso\rcerda”;
$userPhoto = “http://intranet.mydomain.com/sitecollectionimages/rcerda.jpg&#8221;;
$mySiteHostSite = Get-SPSite $mySiteUrl
$mySiteHostWeb = $mySiteHostSite.OpenWeb()
$serviceContext = Get-SPServiceContext $mySiteHostSite
$profileManager = new-object Microsoft.Office.Server.UserProfiles.UserProfileManager($serviceContext)
$userProfile = $profileManager.GetUserProfile($userAccount)
$userProfile.get_Item($mySiteProperty).Value = $userPhoto;
$userProfile.Commit()
But I kept getting the following cryptic PowerShell error on the highlighted line above: Exception calling “.ctor” with “1” argument(s): “Object reference not set to an instance of an object.”
What?!
The first thing I did was double check my parameters and tried it again about 15 times. Then I got smart and started looking around to see if anyone else encountered this. Turns out they had. The common denominator seemed to be a permissions issue, but I was logged in as a farm administrator.
Well, it turns out that is not enough. To resolve this issue, you need to log into Central Administration and follow these steps:
  1. Choose Application Management à Manage service applications.
  2. Click on the User Profile Service Application to highlight it and choose Permissions.
  3. Explicitly add your farm administrator account to the User Profile Service Application with Full Control.
  4. And whalah! Problem solved.

SharePoint has a nifty feature that integrates with Lync and Exchange to display a person’s presence information, also known as the “skittle”. J This feature allows you to see if the user is currently busy, available, offline, etc. It also allows you to quickly email, Instant Message, call someone directly from Lync.

Unless the web site is production facing, I typically find this feature very useful and typically keep it enabled.

However, you do have the option of disabling it for a web application, which is useful for public facing web sites. If you do not disable it for public facing web sites, anonymous users will likely get the dreaded yellow bar at the top of the web page asking them if Microsoft can use the Name.dll ActiveX control. Not cool.

Disabling Presence Information for a Web Application

You can follow these steps if you want to disable presence information for an entire web application.

  • Go to Central Administration.
  • Select Application Management -> Manage web applications
  • Select the web application and click the General Settings toolbar button.
  • In the section entitled Person Name Actions and Presence Settings -> Enable Additional actions and Online Status for members, choose No.
  • Press OK

 

I recently ran into a circumstance in which I had a list view that contained a lot of records and was set to page at every 250 items. I noticed that the list view was loading pretty slowly and seemed to be pretty bogged down. The reason was that each record contained at least two people (and sometimes as many as 5) and it was taking a long time for the presence information to load. This resulted in the browser to be unresponsive for about 15 seconds while it finished.

For my purposes, being able to display 250 lines at a time was far more important than having the presence information enabled on this list. I decided to increase the list performance by removing the presence information.

It turns out this is pretty easy to do as well.

Disabling Presence Information for a List

  • Go to List Settings.
  • Click on the person field or fields.
  • Notice that the Show Field item defaults to Name (with presence), but includes many additional options. In my case, I changed it to simply Name.
  • Press OK.

SharePoint 2013 comes with a new and improved developer dashboard that allows you to easily monitor:

  • Thread execution time
  • Call stack information and query text for each SQL Server query generated by the page
  • Call stack information for each WCF call
  • URL and job timer information
  • Execution start time
  • SPMonitoredScope statistics

In SharePoint 2013, the developer dashboard is easily accessible from the toolbar.

s

Don’t see the icon? That is because SharePoint 2013 does not enable the Developer dashboard by default. To enable the developer dashboard, run the following in the SharePoint 2013 Management Shell from your SharePoint development environment:

$content = ([Microsoft.SharePoint.Administration.SPWebService]::ContentService)

$appsetting = $content.DeveloperDashboardSettings

$appsetting.DisplayLevel = [Microsoft.SharePoint.Administration.SPDeveloperDashboardLevel]::On

$appsetting.Update()

 

I’ll be honest. I don’t like writing CAML queries. There, I said it…

How about using LINQ instead to access the data in your lists and libraries? It’s really pretty simple.

You can use the SPMetal.exe located in c:\program files\common files\microsoft shared\web server extensions\15\bin to generate both a data context and LINQ classes which you can consume in your SharePoint project. One you do that, you no longer have to write giant ugly text string queries, but can instead focus on managing your SharePoint data with strongly-typed, entity classes.

To use SPMetal to generate the class file you will need to consume into your SharePoint 2013 project, create a batch file (*.bat) in your development environment as follows:

c:\program files\common files\microsoft shared\web server extensions\15\bin\spmetal.exe /web:http://dev.mydevweb.com
/code:”C:\Users\rhutton\Desktop\SPMetal.cs”
pause

When you run your batch file, a class file will be created. If you specified the class file to use the (*.cs) extension, then the data context and classes will be generated using C#. However, if you specify the class file to use a (*.vb) extension, then the data context and classes will be generated using that other language. 😉

SPMetal creates a data context and classes for each of your lists and libraries so you can access them in a strongly-typed, object oriented way.

Capture2.PNG

Now writing queries is super easy, readable, and definitely more maintainable:

Capture.PNG

One of the beautiful things about using LINQ to SharePoint to retrieve data from your lists and libraries is the absolute ease in which you can retrieve data from two or more lists which are joined by lookup fields.

For more information on setting up LINQ to SharePoint in your developmennt environment, check out my blog entitled Using SPMetal to Generate SharePoint 2013 LINQ Classes.

For example, I have two custom lists: Client (which contains ClientName, ClientLogo) and ClientQuote (which contains a Client lookup field, as well as Quote, ContactName, and ContactTitle).

With LINQ to SharePoint, I can easily write a query to retrieve information from both lists and populate a custom object called ClientQuotes:

If I were to use this in a custom web part, I would get the following error: The query uses unsupported elements, such as references to more than one list, or the projection of a complete entity by using EntityRef/EntitySet.

This error can be resolved by one simple adjustment:

What this does is force immediate query evaluation and breaks the query into two steps.

I am in the processing of learning how to use SPMetal to replace those dreaded SPQuery CAML queries. So far, very nice!

If you need more information on using SPMetal to add LINQ to SharePoint to your SharePoint development environment, check out my blog entitled Using SPMetal to Generate SharePoint 2013 LINQ Classes. (This is also relevant to SharePoint 2010)

One scenario I ran into was needing to filter my results on a multi-value lookup column.

In this example, I have two custom lists: Clients and Services. A client may be associated with one or more services, so I created a multi-value lookup column on the Clients list. Now I want to retrieve all Clients which are associated with a Service entitled “Applications”.

One thing I need to do in my LINQ query is be sure to for immediate query evaluation using a .ToList() statement. This will prevent me from getting an “Unsupported Elements, References to More than One List” error. For more information on this, please check out my blog entitled SPMetal List Joins “Unsupported Elements, References to More than One List” Error.

One thing to note is that I am using a data service and returning strongly-typed objects. An alternative to this would be to simply use anonymous types if you wanted to process the results immediately, rather than return it from a method.

publicclassClients

{

public string Title { get; set; }

public string Logo { get; set; }

}

If the List field was simply a lookup field, then filtering with LINQ is very easy and would look something like this:

public IEnumerable<Clients> RetrieveClients()

{

SPMetalDataContext dataContext = new SPMetalDataContext(SPContext.Current.Web.Url);

var query = from client in dataContext.CatapultClients.ToList()

where client.Services.Title = “Applications”

orderby client.Order, client.Title

selectnewClients

{

Title = client.Title,

Logo = client.ClientLogo

};

return query;

}

However, since it is a multi-value lookup field, the filter expects an actual Service object. First I retrieve the Service, and then I pass it in as a filter.

public IEnumerable<Clients> RetrieveClients()

{

SPMetalDataContext dataContext = new SPMetalDataContext(SPContext.Current.Web.Url);

var myService = dataContext.CatapultServices.Where(e => e.Title == “Applications”).ToList().Single();

var query = from client in dataContext.CatapultClients.ToList()

where client.Services.Contains(myService)

orderby client.Order, client.Title

selectnewClients

{

Title = client.Title,

Logo = client.ClientLogo

};

return query;

}