InfoPath Forms Services and the xsi:nil in code behind


October 25, 2013 - 12:27, by Steven Van de Craen - 1 Comments

Yesterday I had the requirement to programmatically add and remove the xsi:nil attribute from an InfoPath 2010 browser form hosted in InfoPath Forms Services in SharePoint 2010.

There are several solutions for adding and removing xsi:nil to be found on the internet, but I’ve found only one that works in both browser and InfoPath client forms, and that’s by replacing the node’s OuterXml.

public const string NIL_PREFIX = "xsi";
public const string NIL_LOCALNAME = "nil";
public const string NIL_NAMESPACE = "http://www.w3.org/2001/XMLSchema-instance";
        
public static void RemoveNil(XPathNavigator node)
{
    if (node.MoveToAttribute(NIL_LOCALNAME, NIL_NAMESPACE))
        node.DeleteSelf();
}

public static void ClearAndSetNil(XPathNavigator node)
{
    XmlDocument doc = new XmlDocument();
    doc.LoadXml(node.OuterXml);

    XmlElement nDoc = doc.DocumentElement;

    XmlAttribute attr = doc.CreateAttribute(NIL_PREFIX, NIL_LOCALNAME, NIL_NAMESPACE);
    attr.Value = BoolHelper.True;

    nDoc.Attributes.Append(attr);
    nDoc.InnerText = String.Empty;

    node.ReplaceSelf(nDoc.OuterXml);
}

All other solutions seem to throw the “Schema validation found non-data type errors” error. Note that the xsi:nil attribute is only required for field types that require a value, such as:

  • Whole Number (integer)
  • Decimal (double)
  • Date (date)
  • Time (time)
  • Date and Time (dateTime)

 

Related

» The xsi:nil attribute - http://blogs.msdn.com/b/infopath/archive/2006/11/28/the-xsi-nil-attribute.aspx

» How to: Work with the XPathNavigator and XPathNodeIterator Classes - http://msdn.microsoft.com/en-us/library/office/aa945227.aspx


Word 2013 crashes when opening a document (SharePoint 2013)


April 17, 2013 - 15:32, by Steven Van de Craen - 3 Comments

Since a few weeks I’m experiencing an issue with Microsoft Word 2013 when I try to open a document from SharePoint 2013 (or even downloaded from SharePoint 2013). As soon as it tries to load the Document Information Panel (DIP), it crashes ugly.

Microsoft Word has stopped working

If I change the internals using good old Content Control Toolkit so that the DIP doesn’t use cached data…

Content Control Toolkit

… it opens without loading the DIP or crashes.

Word 2013 DIP unable to load

It might have to do with the Taxonomy (Managed Metadata) fields that we’re using, but still it shouldn’t happen.

I tried Fiddler to see if there were requests being made but nothing turns up, perhaps I need a full network traffic monitor to see all things happening. It happens on a fresh local account as well, so it’s not that my local cache is corrupt or anything.

I’ll wait for the next updates to roll in, and hope they fix it...


External Data integration in Office and SharePoint using BDC or BCS


December 7, 2012 - 13:42, by Steven Van de Craen - 0 Comments

Today I discovered a rather unpleasant change during a migration of SharePoint 2007 to SharePoint 2010.

The customer is still using Office 2007 but is planning on upgrading next year.

Situation

In SharePoint 2007 you had Business Data Connectivity (BDC) to bring external data (think back-end systems) into SharePoint and Office. If you configured a field for External Data on a Document Library, you could see and edit the field value inside the Document Information Panel in Office.

image

After migrating to SharePoint 2010 you get Business Connectivity Services (BCS). This is the successor to BDC focuses on a better integration with SharePoint content. However, some features were discontinued and altered, including the BDC Field Resolver Web Service (/_vti_bin/bdcfieldsresolver.asmx).

In Office 2010 this works a bit different but the result is still the same; you can view and edit values before saving your document to SharePoint.

image

Unfortunately, Office 2007 is unaware of this and will just report the BCS field in the Document Information Panel, making it required (which we configured in the field settings in SharePoint). Submitting the document won’t work as long as the value is blank, but entering a value won’t resolve because it still assumes the BDC Web Services.

image

Error

The error you get when entering a value (and validating it) is:

image

There was an error in the validation code.
Document Information Panel cannot complete this action, because of an error in the form's code.
The following error occurred:

Expected token 'EOF' found 'NUMBER'.

//ns2:-->0<--
File:script.js
Line:169


Unspecified error

Solution

Upgrading to Office 2010 fixes it. No other solutions/workarounds known.


Fixing multiple credential prompts for Office in combination with SharePoint


February 22, 2011 - 10:39, by Steven Van de Craen - 0 Comments

I had seen and tried most of this already, but didn’t know the Network Location bit:

Multiple Authentication (login) Prompts - Office Products with SharePoint

http://mhenthorn.blogspot.com/2011/02/multiple-authentication-login-prompts.html


Office Web Apps - creating new documents


August 16, 2010 - 09:24, by Steven Van de Craen - 0 Comments

The Office Web Apps allow users without Microsoft Office installed to display or work on Word, Excel or PowerPoint files from the browser. It is a separate installation to your SharePoint Farm and controllable by two Site Collection Features:

Office Web Applications Site Collection Features

When active it will render Office 2007/2010 file formats in the browser, without any requirement to a locally installed Office suite.

Excel Web Application

As you notice in the screen there’s no obvious way to create a new document, spreadsheet or presentation. So how would that work ?

The ‘New’ button on libraries has both functionalities; when a local installation of Office is found it will open up the corresponding application, else it will navigate to a page for creating a new file directly from the browser.

Word Web Application:

Word Web Application - New document

Word Web Application - New document (bis)

If you’re using a modified document template, the new document will be based on the modified template.

Excel Web Application:

Excel Web Application - New spreadsheet

If you’re using a modified spreadsheet template, the new document will NOT be based on that.

PowerPoint Web Application:

PowerPoint Web Application - New presentation

PowerPoint Web Application - New presentation (bis)

If you’re using a modified presentation template, the new presentation will be based on the modified template.

It’s a shame Excel behaves differently, but other than that it’s a really nice feature !


Office 2010 Protected View and SharePoint


May 10, 2010 - 10:00, by Steven Van de Craen - 3 Comments

If you’re having trouble with opening from or saving to SharePoint from Word, Excel or PowerPoint 2010 it might be that the Protected View settings are interfering in the process. You might see this when you’re running a SharePoint and Office on the same machine, like in a demo or development environment.

 Word encountered a problem  Word experienced an error trying to open the file

  • Creating a new document from SharePoint: “Word has encountered a problem.”
  • Opening a document from SharePoint: “Word experienced an error trying to open the file.”
  • Saving a document to SharePoint: Dialog will not open on the Document Library, but rather your local Documents folder

A quick fix is to disable the Protected View for “potentially unsafe locations”:

Disable protected view for potentially unsafe locations

Important: This is a per-application setting so do this for Word, Excel and PowerPoint individually !


Office 2007 document templates and Content Types in SharePoint – lessons learned


January 29, 2010 - 15:09, by Steven Van de Craen - 1 Comments

A while ago I stumbled upon a serious design limitation regarding Content Types and centralized document templates. What then followed was a series of testing, phone calls with Microsoft, finding alternative solutions and deep dive into Office Open XML.

Request from the customer

“We want to use MOSS 2007 to create a collaboration site per project for our 400+ projects. These collaboration sites all use the same Content Types and document templates. We want to centrally manage those document templates so that we don’t need to make the same change 400+ times.”

Approach

Due to sizing we architected a solution with a dozen of Site Collections that would each hold a collection of project sites. We ‘Feature’-ized our Content Types and Site Columns so that they could quickly be activated on all Site Collections and used by the child sites. Document templates would be stored in a central document library and we would link to them in the Content Types on the project sites.

First issue

Linking to document templates really doesn’t play well with the Document Information Panel (DIP). I have blogged about this here:

Centralizing Document Templates in a library- Document Information Panel shows incorrect properties

 

We proposed a solution where the document templates in the central library would be pushed to the Content Type resource folder on site level. The code to perform the push would have to connect to the Site Collections, copy the template to the resource folder (http://sitecollectionurl/_cts/contenttypename) and link template and Content Type together.

When a Site Content Type is associated with a List it will be a List Content Type inheriting from the Site Content Type and the document template will be copied to the List Content Type resource folder (http://sitecollectionurl/listurl/Forms/contenttypename).

Second issue

Did I tell you that the column values (metadata) have different values based on the project site ? So when a project site is created we automatically update the List Content Type Column default value with the values for that specific project site. Unfortunately this is not supported when working with Office 2007 file formats because they only react on changes to the Site Column.

Consider the following scenario:

1) Set up a document library with a Content Type that has a text column with a default value
2) Upload a new .doc or .docx as Content Type template
TEST 1) Create a new document:
        .DOC:  the DIP will contain the text column with the default value
        .DOCX: the DIP will contain the text column with the default value
3) In SharePoint, modify the default value of the text column
TEST 2) Create a new document:
        .DOC:  the DIP will contain the text column with the updated default value
        .DOCX: the DIP will contain the text column with the original default value

Microsoft confirmed that this is by design.

Third issue

When designing our document templates with Content Controls mapped to our SharePoint fields we didn’t know that internally in the DOCX file it uses a GUID for mapping the Content Control with the SharePoint Metadata XML. For fields (Site Columns) created in the UI or through API this is the SPWeb.ID of where they were created. For fields created declaratively through Features this is the SPList.ID of where their Content Type is associated to.

So some things to notice

  • Creating a single document template with Content Controls mapped to your declaratively added Fields cannot be used in two different Document Libraries because the Content Controls lose the connection with Field (because the ID of the List is different and not updated in the Content Control)
    • The solution here is to create your fields in the UI or through the API (this could be in a Feature Activating event)
  • Copying a document template across Site Collections means different Web ID’s so it also affects fields created in the UI or the API

Finally

In the end we wrote some wrapper classes for Office 2007 file formats using System.IO.Packaging that would manipulate our document templates once they were copied over to a different Site Collection. We also rewrote our Features to create our Fields through the API (SPWeb.Fields.AddFieldAsXml()).

  1. Remove the SharePoint Metadata XML so that association of the Content Type to a List it would be regenerated automagically
  2. Loop through every Content Control and find to which Field they were mapped using information in it’s XPath. Then we would update the GUID’s in the Content Control to match the SPWeb.ID

Next time I’ll definitely take these design limitations into account. Lessons learned I’d say !


Configure Word 2007 Content Controls with empty Placeholder Text


December 3, 2009 - 17:03, by Steven Van de Craen - 1 Comments

Word 2007 uses Content Controls to display document fields inside the document (eg. the header). These document fields can be standard fields but also your SharePoint Fields.

By default when the value of a Content Control is empty it will display the Placeholder Text between square brackets as follows in a sample document header:

Empty Content Controls

It is possible to change this Placeholder Text by going into Design Mode and replacing the text in the Content Control.

Make sure that you see the Developer tab in the Word Ribbon. If you don’t see it you can turn it on in the Word Options;

Word Options

Open the Developer tab and enable Design Mode;

Word in Design Mode

Now the text displayed in the Content Control is actually that one for the Placeholder Text and can be modified as desired. Once you leave design mode the Content Placeholder will return to displaying the original value and have saved the new Placeholder Text.

Removing all text from the Content Control Placeholder Text will result in an error when leaving Design Mode;

Empty Content Control Error


The closest you can get to making it appear empty is by using a single space character. Once you exit Design Mode you’ll see the result for those fields that have no value set.

Content Controls with content


Centralizing Document Templates in a library: Document Information Panel shows incorrect properties


August 20, 2009 - 09:56, by Steven Van de Craen - 0 Comments

Every once in a while I get the request to manage all document templates centrally in a Document Library. This can easily be done by configuring your Content Types to ‘link’ to the document template by location and then applying those Content Types to lists on several locations.

However there’s a gotcha in Word 2007 with the Document Information Panel.

Consider the following scenario:

  • You have a “MyTemplates” Document Library for storing the Word templates (.doc, .docx)
  • You have a “Documents” Document Library configured with Content Types linking to your templates as noted above. These Content Types have custom metadata (text fields, date fields, lookup fields, etc.)
  • You create a new document with a given Content Type

When the new document opens in Word 2007 the Document Information Panel is showing properties from the “MyTemplates” Document Library instead of your Content Type. Once you save the document it will refresh and show the correct set of properties. If you have required metadata it will prompt you to fill that in before actually saving.

I believe this to be a bug in Word 2007. It has been confirmed by Microsoft that this is a design limitation.

A workaround An alternative solution for some scenario’s could be to set the Content Type of your templates to the target Content Type.

This would of course still not work when you want to use the same template for multiple Content Types.

Definitely something to keep in mind when planning your setup…


Office Automation: extract embedded Word Documents


September 18, 2008 - 14:09, by Steven Van de Craen - 4 Comments

I'm normally not into Office Automation but today I needed to extract all embedded files from a Word Document. Those files were Word, Excel and PDF documents. Luckily the majority were Word documents, because the quick solution I whipped up only works for those types, not for Excel or PDF.

Here's the VBA script that loops through the embedded objects, checks if it's a Word document and goes to save it in a new folder.

Sub ExtractFiles()
'
' ExtractFiles Macro
'
'
Dim shape As InlineShape
Dim folderName As String
Dim a As Document

folderName = Replace(ThisDocument.Name, ".", "_")
MkDir folderName

For Each shape In ThisDocument.InlineShapes
    If (shape.Type = wdInlineShapeEmbeddedOLEObject) And (InStr(LCase(shape.OLEFormat.IconLabel), ".doc") > 0) Then
            shape.OLEFormat.Object.SaveAs (folderName & "\" & shape.OLEFormat.IconLabel)
    End If
Next shape

End Sub


 Next >>