Category Archives: SharePoint 2010

Creating a repeating (looping) workflow in SharePoint 2010

My SharePointBuddy (Sandra Mahan) and I were brainstorming stuff recently, and the topic of SharePoint 2010 looping workflows came up. To the best of my knowledge, you can’t create a workflow in SharePoint Designer (SPD) that will repeat an action for an unspecified number of repetitions (occurrences or days). Basically, the workflow is linear in nature, and it runs from top to bottom.

But what if there was a way to get a workflow to repeat a certain action until a condition caused it to complete?

I think we found one!  A disclaimer up front, though… For all we know, this may be common knowledge, and your reaction might be “well, duh!” In that case, you’re dismissed from reading the rest of this. We just thought it was a cool concept that could work nicely in a number of situations (and with no drawbacks that we know about… yet).

The concept is this… Create a secondary list that triggers workflows that affect your primary list. The primary list item creates a secondary trigger list item, and the secondary trigger list item deletes itself after updating the primary list item (which potentially triggers the creation of another secondary list item, and so on).

Confusing? Sort of… Let’s see if I can flesh out an example here based on my testing.

I have a Non-Disclosure Agreement (NDA) list that tracks the creation and completion of NDAs. When the NDA list item is created, it sits in a status of Pending until a copy of the signed agreement is attached. The status then goes to Completed.

While the status is Pending, the customer wants a reminder to be sent out to the NDA owner every 15 days reminding them to submit a signed agreement. The notices only stop once the NDA list item is marked Completed.

My current (non-repeating) workflow in SPD starts a reminder process when the NDA list item is created. It waits 15 days, then it checks the status. If the status is still Pending, it sends out the reminder email and waits for another 15 days. If the status is Completed, it stops the workflow. Since the workflows in SPD are linear, I have to repeat the reminder email action over and over for each 15 day period. I run it out to 180 days, and then I exit the workflow (I had to draw a line somewhere). It works, but it’s far from elegant.

Now let me rework it using the looping concept…

I still have the NDA list, but I no longer start the reminder workflow when a new NDA is created. I add one more column to the NDA list, and call it Reminder Last Sent Date. The only other relevant column for this concept is the Title field in the NDA list, as that’s what I’ll use as the key to match to my new workflow triggering list.

I create a new list, and I call it NDA Reminder Triggers. The only column in this list that I need is the Title column, which is the key to match back to the NDA list item.

Now for the workflows…

I create a new workflow for the NDA list that is triggered on a created or changed item. The workflow checks the status of the NDA. If the status is Pending, it creates a new NDA Reminder Trigger list item with a Title field that matches the Title field of the NDA, and the workflow exits. If the status is Completed, the workflow exits. The goal here is to make sure there is a NDA Reminder Trigger list item for each NDA item that is in a Pending status.

For the NDA Reminder Trigger list, there is a new workflow that is triggered by a created item. That workflow starts by waiting for 15 days. At the end of 15 days, it checks the status of the NDA list item (matching on the Title field). If the status is Pending, it sends a reminder email to the NDA owner (again, a lookup to the NDA item via the Title field), updates the NDA with the Reminder Last Sent Date field set to Today, and it deletes itself. If the status is Completed, it just deletes itself.

The act of updating the NDA list item with the Reminder Last Sent Date now triggers the NDA list workflow to create a new NDA Reminder Trigger list item. The new NDA Reminder Trigger list item triggers *that* list workflow to wait 15 days before checking the NDA status again. This cycle can repeat as long as needed for the NDA status to be set to Completed.

In my preliminary testing for this idea, it seems to work fine. If I update the NDA list item status while the NDA Reminder Trigger item is waiting in the 15 day workflow, then when the 15 days is up it sees that the status is now Completed, and the NDA Reminder Trigger list item deletes itself. If the NDA list item is updated once the status is Completed, the NDA list workflow doesn’t create a new trigger item.

Thoughts? Comments? Hidden landmines we don’t know about? I’m happy to get your feedback…

Sending SharePoint alerts to a distribution list…

I had an interesting question posed to me recently. Someone wanted to create SharePoint alerts on a document library, and they wanted it scheduled to run weekly on all new items. In addition, they wanted to send the alerts to a distribution list so that they didn’t have to maintain separate alerts for each individual. That all sounded well and good, as editing alerts (other than to just delete and recreate them) is not possible without 3rd-party tools.

I created the alerts and tried to send it to a distribution list we had set up in Active Directory (AD). Unfortunately, the alert emails never showed up for anyone on the list. I tested the alert with it going to me specifically, and that worked fine. So why wasn’t the distribution list working? I’ll admit, I was stumped…

Some research got me to the answer that I didn’t want to hear. Distribution lists in AD can only be used in alerts if they are also set to double as security groups in SharePoint. That’s problematic for us, because our security area doesn’t want distribution list AD groups to also be used for security purposes.

I toyed around with other ideas on how to get the equivalent of a weekly email of new items in a library to send out to a group, but each option had some drawbacks. SharePoint Designer workflows would only send one item at a time, and our SQL Server Reporting Services (SSRS) configuration doesn’t have the email service turned on. The customer could send an email to everyone once a week with the new items in it, but she doesn’t want to have to do that manually.

Bottom line… how can I get the alert feature to work for a distribution list?

My solution was to let SharePoint generate the alert to the customer, and then have the customer set up an Outlook rule to forward it to the distribution group. That way, we have nothing custom that has to be maintained in SharePoint, and she has full control over how often the alert runs and who it goes to.

Following are the instructions I sent her on how to set that up. I’m sharing it here so I won’t forget. 🙂

What I am suggesting is to set the alerts like you had planned (weekly on Wednesday and Friday), and address them to yourself. Then by using Outlook mail rules for those alert emails, you can forward it to a distribution list (or select individuals) of your choosing. Exchange and Outlook will run the rules regardless of whether you’re logged in or not, and people will get the alerts just as if they were individually subscribed. You can maintain the delivery list as it’s your rule, and we don’t have anything extra or custom to support in SharePoint.

 All the other ideas we had (workflows, Reporting Services, views of the last seven days of information) had various side effects that would either require extra work on your part or would mean extra clicks for the reader to see the actual list of articles. This approach maintains the value of the alert listing all the weekly updates, without the need to delete and recreate the alerts for individuals if anything ever changes.

Here’s how I set it up…

Go into the library (Articles Of Interest or New Learnings) and click on the Alert Me > Set alert on this library option: 20150225Image01

 Set up your alert as you normally would, routing it to yourself on whatever schedule is desired: 20150225Image02

 You’ll receive an email saying the alert has been created: 20150225Image03

 Once the alert is triggered the first time, you’ll get an email that lists all the items based on your criteria: 20150225Image04

 When that email comes in the first time, we’ll set a rule for those alerts. Click on Rules > Create Rule: 20150225Image05

 On the Create Rule dialog box, select Advanced Options: 20150225Image06

 Check the entry for the subject line phrase, and click on that phrase at the bottom of the dialog box. We are going to change the phrase: 20150225Image07

 Remove the You have successfully… phrase by clicking the Remove button: 20150225Image08

 Change the phrase to the name of the alert (in this case, Articles Of Interest) and click Add: 20150225Image09

 Once that’s done, click OK: 20150225Image10

 Click OK to proceed to the addressing part of the rule: 20150225Image11

 Select the action to forward the alert to people or a distribution list and click on the people or public group at the bottom of the dialog box: 20150225Image12

 Select your distribution list or the names of the people you want to have get the alert and click OK: 20150225Image13

 Click on Next to go to the Exceptions dialog box: 20150225Image14

 Since there are no exceptions, click Next: 20150225Image15

 Your alert is done. Give it a meaningful name, make sure the rule is turned on, and click Finish: 20150225Image16

 Next time you get the alert, it will come into your inbox like normal: 20150225Image17

 Moments later, that email will be forwarded to the distribution list: 20150225Image18


One potential fix for the SSRS “Thread was being aborted” error…

One potential fix for the SSRS “Thread was being aborted” error….

One potential fix for the SSRS “Thread was being aborted” error…

I’ve been working with SQL Server Reporting Services (SSRS) recently, and it’s been an eye-opener. I can now give my customers some spreadsheets on lists over 5000 items that are updated every day without intervention. It’s a game changer in terms of solutions I can design.

I did run into a frustrating problem, however. After a few days of my scheduled SSRS jobs running fine, I started getting an error: “Thread was being aborted”20150118Image01

There are many blog posts out there on that topic, but none of them seemed to relate to what we were seeing. After playing around a bit, I found that we were likely getting the error due to a time-out error for our job running too long. When I removed the server time limit for that job, things ran fine.

To do that, select “Manage Processing Options” on the report configuration:20150118Image02

In the “Processing Time-out” section, select “Do not limit report processing time-out”:20150118Image03

I’ve since adjusted the “Limit report processing time-out (in seconds) to” setting to 7200 seconds (two hours) so that there is *some* level of control for run-away jobs. Still, it’s nice to know that I can control this with each individual job now.

Internal SharePoint User Group Meeting presentation – SharePoint 2010 List/Library General Settings


This is a presentation for our internal SharePoint User Group on Friday, October 17th, 2014. It is targeted to help them understand the Navigation, Versioning, and Advanced settings in their lists and libraries..

Internal SharePoint User Group presentation – SharePoint Myths Busted

Presented to our internal SharePoint User Group on June 13th, 2014.

Sometimes we run into common questions or misconceptions about SharePoint. This is a tongue-in-cheek way to address these issues and let people know how things actually work.


Internal SharePoint User Group presentation – Searching In SharePoint

This is a presentation I gave to our internal SharePoint User Group on Friday, September 19th, 2014. It was targeted to take them beyond the typical “type in a couple of words and hope for the best because SharePoint search sucks” approach.


My SharePointalooza session slides – Tracking Ethical Conflicts in a Sometimes Unethical World

Here are the slides for my presentation for SharePointalooza in Branson Missouri – 2014/09/13.


What happens when you move from plain text to rich text to enhanced rich text?

I ran into this situation a while back, but I didn’t write down all the details of what happens when, so now it goes out here to my rememory notebook…

So the situation is as follows… I have a number of multi-line text columns that are set at Plain Text. The customer wants to have some formatting applied to them, which is OK (since we’re going from less to more on the formatting issue). But I know there are situations where if you’re going from more to less formatting, you lose some level of detail in the field.

This is a walk-through of what happens as you move the settings up and down…

Creating the column as Plain Text:Image2014091501

Typical text, and how it looks in a view:Image2014091502

Now a change to Rich Text:Image2014091503

The form with the text formatting and a URL:Image2014091504

And how it looks in the view… all formatting shows up:Image2014091505

Now changing it to Enhanced Rich Text:Image2014091506

Added a table, a hyperlink, and a picture:Image2014091507

And again, it all shows up in the view properly:Image2014091508

So far that works like I would expect… now to work back down.

I changed the column from Enhanced Rich Text to Rich Text and got this message:Image2014091509

Looking at the form, I lost my image. I did retain the text in the table, but the table itself is gone. The hyperlink remained:Image2014091510

That basic change also is reflected in what shows in the view:Image2014091511

Finally, I changed the column back to Plain Text and got this message:Image2014091512

Looking at the form, I’ve now lost all the text formatting and the hyperlink. The Bing URL still shows up, but that’s only because the browser is recognizing it and rendering it as a URL. If I put the form in edit mode, it would just be text. Also, the “And A Table” text has gone from being on one line to being on separate lines:Image2014091513

And finally, here’s what it looks like in the view:Image2014091514

Bottom line… you can change a multi-line text column to go to a higher level of function with little issue. But if you start moving down the list, you’ll progressively lose formatting, even though you’ll keep the raw data (except for images and any links to words/images).


Using The Information Management Policy (Specifically The Retention Policy) In SharePoint 2010

The Information Management Policies feature of SharePoint 2010 has some interesting potential in a few ways I hadn’t imagined. I was familiar with setting retention actions to delete, recycle, or move items after a certain time period had passed, but I somehow wasn’t aware that I could also trigger a workflow. I also wasn’t aware of the recurrence option that would repeat the retention action until the next stage was triggered. In other words… would this feature allow me to run nightly/daily/weekly workflows on a list or library option?




To set up a test, I created a custom list with a couple of columns that I could update via a workflow. It contained the title of the list item, a Date Condition column that I would use to trigger the retention policy, and a date the workflow agent was triggered (it would be updated in the workflow):


The workflow was very basic… Whenever it was triggered, it would update the Agent Triggered Date column with the current date/time, and send out an email to the person who created the item:


I then created the Information Management Policy for this list item:



The trigger for this retention policy would be when the current date was greater than the Date Condition column plus 0 days:


Side note: It is highly recommended that you associate Information Management Policies with specific content types, not just a generic Item content type. For test purposes, this list only has the one Item content that it’s using, so I didn’t create a different content type for it.

There are two timer jobs that interact with the Information Management Policies. The first one, titled Information Management Policy, is set by default to run weekly on Friday at 11 pm. It goes through libraries that have policies and figures out if the event portion of the policy is a true condition. If so, it will then set the stage for the second timer job to run against the action portion:


The second timer job is Expiration Policy, and that’s what allows the action portion to run. It’s set by default to run weekly on Saturday at 11 pm:


The two workflows need to run in that order. If you were to just run the Expiration Policy timer job, nothing would ever trigger because the event wouldn’t be set. If you run just the Information Management Policy timer job, then the action will never run (even though the event was true).

First Test Run

My first test run involved triggering an Information Management Policy that did not use recurrence. I used the Run Now feature of the Information Management Policy timer job to run that, then waited approximately 15 minutes and used Run Now on the Expiration Policy timer job. Within approximately 10 minutes, I received my email, showing that the policy had triggered.


I then ran the two timer jobs again, wanting to see if this would re-trigger the email. It does not, as without recurrence the Information Management Policy will only be applied to the document once.

Next Experiment – With Recurrence

My next experiment involved adding recurrence to the Information Management Policy. The question to be answered was whether or not the workflow would continue to run every time the Expiration Policy timer job ran.



Using the Run Now features of the Information Management Policy and Expiration Policy timer jobs, I ran a series of cycles against four items that I had in my custom list. In all cases, the emails got sent out in each cycle, meaning that once the Information Management Policy is triggered to run against the list item, the recurrence portion of the policy will run every time the Expiration Policy timer job runs. It does not go back and try to determine if the event portion of the Information Management Policy is still true. In fact, you can go into the list item and change column values that would make the event condition *not* true, but the Information Management Policy will still continue to run each night because it was already triggered the first time.

In effect, this means that if you set the two timer jobs to run nightly (separated by a couple of hours), you will basically have the ability to automatically run a workflow against a list item on a daily basis without manual intervention or action on the item (provided the event portion of the Information Management Policy has triggered).

So What If I Don’t Want My Workflow Logic To Run Every Night?

So while it’s cool to have that workflow run every night, what if I don’t want anything to happen most of the time? If that’s the case, you need to write logic to stop the workflow if certain conditions exist.

In the prior example, I was sending out an email and updating a date in the list item. I changed the workflow to also update a new column… Initial Email Sent. If that column is set to Yes (which is the case after the workflow runs the first time), the workflow will immediately stop and no additional processing will occur:


The workflow will still be triggered each night based on the recurrence logic in the Information Management Policy. The logic of the workflow will dictate exactly what does and does not happen, though.

What About Multi-Stage Retention Policies?

Since we’ve come this far…

I decided to add a second stage to my Information Management Policy to see if and when that would trigger. Here’s the set-up:


The first stage still runs the email and updates the trigger date. The second stage will run if today is greater than the Condition Date plus one year. The thought was that the first stage would run repeatedly due to recurrence, and then the second stage would trigger if the Condition Date changed.

My test cycles were as follows:

  • I set the Condition Date to two weeks prior (to trigger the policy immediately) and ran the Information Management Policy and Expiration Policy timer jobs via Run Now. I got the email and the Initial Email Sent indicator was set to Yes.
  • I then ran the Expiration Policy timer job again via Run Now to simulate another nightly run. The workflow ran again, and the logic stopped when it checked the Initial Email Sent indicator.
  • For the third and final run, I set the Condition Date to two years prior. I then ran the two timer jobs. Within 30 seconds of the Expiration Policy timer job, the list item had been deleted and moved to the recycle bin. It showed in the Site Collection recycle bin as being deleted by the System Account, not by me as the person who set up the policy or changed the list item.

Gotchas Found In Testing

When I was updating my workflow during testing, I re-published it a couple of times. When I went back into the Information Management Policy, I noticed that the Action portion of the retention policy was still pointing to a previous version of the workflow:


I had to go back into the policy and update the action to point to the most current version in order to get the most recent version of the workflow to run. This is something you need to remember if you change the workflow being used.


This would work well in a scenario where we have list items that need automated reminders a year or so down the road (instead of having active workflows “waiting” for 365 days to run the next step):

  • The initial event on the Information Management Policy could trigger on Created Date plus 0 days (so it starts running right away).
  • The first stage is set to run a reminder email workflow with recurrence happening every 0 days.
  • The workflow would check to see if the current date is greater than the reminder date and then set an indicator when the email first goes out. Other logic (maybe when the form is updated) would remove that indicator if the reminder date changes.
  • The second stage could trigger on an Archive Date being added, and it could move the item to an archive list or trigger an archive workflow with appropriate logic. It would have no recurrence specified, so the Information Policy would be effectively completed by then.

There may be a number of other ways to accomplish this, but this would give us the ability to have “out of the box” workflows that run on a schedule rather than require manual triggering on each individual item.