Freitag, 2. August 2013

Allow multiple of Workflowsubscription on same ListItem

This applies to the new Workflow 2013 Engine:

By default Sharepoint doesn´t allow to have multiple Instances of a Workflow running on the same ListItem.

This gave me headache because I had a Workflow to start when an Item is updated. However, if the Workflow got updated again before the Workflow of the last Update ended, I was not able to start the Workflow again. Even if I canceled the former Workflow it wasn´t possible, because sometimes the cancellation process lasts some seconds and I weren´t able to start a new Workflow, even if the former was in cancelling state. In the End I had no workflow running at all.

However, there is a solution:

If you deploy the Workflow subscription by declarative XML using Visual Studio, you should have somewhere the File "WorkflowStartAssocioation" in the elements.xml of your workflow. If you attach the property:


<Property Name="ManualStartBypassesActivationLimit" Value="1" />

you should be able to start the workflow again (as long as you start the workflow manually by Hand or by Code using EventReceiver).

This works also, if create the Subscription by Code using the SubscriptionService or even update an existing Subscription. There is a Property "ManualStartBypassesActivationLimit" in the Subscription-Object which you can set to true.



Donnerstag, 18. April 2013

Setting the Dataprovider for Resultscriptwebpart programmatically (eg. for setting the QueryTemplate)

For doing that you have to create a instance of the DataProviderScriptWebpart, initialize it with the JsonData from the ResultScriptWebPart. There you can set the Propertiy you need and write the PropertiesJason-Member back to the ResultScriptWebpart.DataProviderJson. And of course save the Webpart finally.


           var resultWebPart =  
             webPartManager.WebParts.Cast<WebPart>()  
                    .FirstOrDefault(  
                      wp => wp is ResultScriptWebPart) as ResultScriptWebPart;  
   
           var querySettings = new DataProviderScriptWebPart  
             {  
               PropertiesJson =  
                 resultWebPart.DataProviderJSON  
             };  
   
           querySettings.Properties["QueryTemplate"] =  
             "{searchboxquery} (contentclass:STS_ListItem OR IsDocument:True)";  
   
           resultWebPart.DataProviderJSON = querySettings.PropertiesJson;  
   
           webPartManager.SaveChanges(resultWebPart);  

But beware: Altough there is a Property DataProviderScriptWebPart.QueryTemplate which you can set, it is not included if you request the DataProviderScriptWebPart.PropertiesJson. You have to set the property using the  Properties-Collection of the object.

(of course you could also simple edit the Json-String itself, but I prefer this way).

Sonntag, 14. April 2013

Filtering a List by Userfield and Username

I recently had an requirement to get all Items of a List for a specific user. Usually that´s not that problem, using Server-side Code you could simply get the users SPUser-Object by SPWeb.EnsureUser and filter the list based on the SPUsers´ ID. However, I had to do that by using the Client Object Model (in detail, the Javascript API). Here the process of doing an async request to get the SPUser-Object and then do another async Request filtering by its ID didn´t make me happy at all, so I thought of another way doing that.

I found a solution by joining the List with the Hidden Userinfo-List, on that Join I was able to do a filter on the username.

Here´s the View-XML for doing that:

 <View>  
      <Joins>  
           <Join Type='INNER' ListAlias='User Information List'>  
                <Eq>  
                     <FieldRef Name='UserField' RefType='Id' />  
                     <FieldRef List='User Information List' Name='ID' />  
                </Eq>  
           </Join>  
      </Joins>  
      <Query>  
           <Where>  
                <Eq>  
                     <FieldRef Name='MyUserName' />  
                     <Value Type='Text'>Domain\UserName</Value>  
                </Eq>  
           </Where>  
      </Query>  
      <ProjectedFields>  
           <Field Name='MyUserName' Type='Lookup' List='User Information List' ShowField='Name' />  
      </ProjectedFields>  
 </View>  

(Beware: You have to do a double-Backslash for between Domain and Username when setting the XML-String to the query, because it removes one of them)

Additionaly you can also set ViewFields, for minimizing the result for faster response