SharePoint 2013 Forms: Adding a Drop-down List of Countries (with JavaScript)

A common complaint about the default Contact list form in SharePoint is the prevalence of free-text fields over more structured inputs. Free-text fields for things like City, State, and Country can lead to data inconsistencies.

In the video below, I demonstrate how to swap out the free-text Country field with a drop-down list of countries using JavaScript (and jQuery).

I pull the list of countries in real-time from a free web service. (Note: I’m not sure if it will be free forever, but it is at the moment.)

Here’s a link to the source code:

If you’d like to use the same web service for countries in your own solution, you can grab the web service URL from the code.

How to Check with SharePoint JSOM if File or Folder Exists

Here’s a code snippet showing how to use SharePoint’s JavaScript Object Model (JSOM) to determine whether a file or folder exists:

var ctx = SP.ClientContext.get_current();

// Could also call getFileByServerRelativeUrl() here. Doesn't matter.
// The way this works is identical for files and folders.
var folder = ctx.get_web().getFolderByServerRelativeUrl("/path/to/folder");

ctx.load(folder, "Exists", "Name");

   function() {
      if (folder.get_exists()) {
         // Folder exists and isn't hidden from us. Print its name.
      else {
         console.log("Folder exists but is hidden (security-trimmed) for us.");
   function(s, args) {
      if (args.get_errorTypeName() === "System.IO.FileNotFoundException") {
         // Folder doesn't exist at all.
         console.log("Folder does not exist.");
      else {
         // An unexpected error occurred.
         console.log("Error: " + args.get_message());

The behavior of the client-side object model is slightly different depending whether the file or folder truly doesn’t exist or is just being hidden from us due to security-trimming.

The code snippet above takes this distinction into account and shows you how to check for both conditions.

You can also issue a CAML query against a document library (if that’s where your file/folder lives) to see if an item representing your file/folder exists, but the above snippet is intended to demonstrate the procedure for actual SP.File and SP.Folder objects.

My Top 5 Sites for Finding Remote Development Work

If you’ve ever tried searching for remote work as a developer or designer, you know there’s a TON of garbage to sort through and a lot of worthless sites and job postings out there.

The good news is I’ve been finding remote work online for over six years now, and I’ve learned which sites and strategies tend to produce the best results.

But before I list the sites I recommend, I want to say that I specifically do NOT recommend the “bidding” sites like Freelancer, Elance, oDesk (now called Upwork), Fiverr, etc. Strictly speaking, it’s not impossible to find decent work on those sites, but the odds are against you. The rates tend to be ultra-low and the projects not defined very thoroughly. I don’t use those sites, and I’ve never needed to.

Recruiter Saturation Metric

One metric I’ve included for each of the sites below is what I call “recruiter saturation.” The levels I use are low, medium, and high. The higher the level, the more recruiters use the platform to post jobs they’re trying to staff (typically jobs they found elsewhere and are re-posting to be more accurate).

A higher recruiter saturation isn’t necessarily bad – just good to be aware of so you can account for it. A topic I’m saving for another time is how to find the original job posting (if there is one) for a recruiter-posted job so you can apply directly if you want to. I’ve got a few techniques to help with that.

And now, without further adieu, here’s the list of sites.

StackOverflow Careers

StackOverflow is really good but does require a verification process to prove you’re a real developer. The verification process requires that you either (1) be invited by someone StackOverflow already trusts, or (2) send them links to code you’ve published – such as on GitHub – and they’ll judge you based on activity (commits, pull requests, etc.) and/or code quality. The good news is this keeps a lot of low-quality developers out of the mix and keeps rates fair.

If you can pass the verification process, it’s worth it because the job postings here tend to be good. Since they’re posted directly to StackOverflow, the location filter (to find jobs with a remote/telecommuting option) is actually accurate. Also, the employers here tend to view developers with more respect than on other job sites.

Recruiter Saturation: Low

Authentic Jobs

This is a good site for finding front-end work (UX, design, JavaScript, etc.) though I occasionally see back-end work on there too. I’ve even seen projects around SharePoint and other collaboration/CMS systems.

I haven’t used this site yet to find work, but I did use this site to hire a web designer a few years back. The candidates I heard from were all decent and all had standard market rates.

The search filters don’t directly allow for a remote/telecommuting option, but they do allow for “Freelance” and “Contract” options. When you combine the two, you tend to see remote opportunities pop up in the results. From what I’ve seen, the postings are usually original and pretty good – not the generic kind of posts you see re-posted by tons of recruiters on other sites.

Recruiter Saturation: Low to Medium (I’ll occasionally see a few posts from “CyberCoders” or similar firms)

We Work Remotely (by 37signals)

This used to be known as the “37signals Job Board” but was renamed a while back to “We Work Remotely.”

The good news is this site lists only remote jobs, so filtering on “remote only” or something similar isn’t necessary. There’s even a link you can click as a job hunter to report postings that erroneously say they’re remote when they’re really not. Controls like that keep the quality high.

The bad news is if you specialize in the Microsoft stack, you won’t find much here. The postings tend to lean more towards MEAN, LAMP, Ruby on Rails, etc. But if you’re into those, it’s a good place to find gigs.

Recruiter Saturation: Low


Almost everyone knows the major down-side of this one: it costs money! HOWEVER, if you stay on the home page for several minutes and don’t do anything, you’ll almost always get a popup chat window offering you a steep discount, and then it becomes worth considering (because lining up even one gig would get you a good ROI). As an example, it cost me around $40 (with the discount) to sign up for a whole year, and I use this site a lot because it legitimately saves me time.

The premise of the site is they pre-qualify (to a certain extent) the jobs they list, and the jobs all offer flexible work options like weird hours, telecommuting, etc. The idea – which mostly works – is you save a lot of time sorting through garbage because they do that part for you. The result is a lot of medium-quality (and a few high-quality) gigs. They do indeed weed out a lot of the low-quality garbage.

However, there are a couple of downsides. One is the site’s popularity. Because the audience is large, a lot of large companies who offer “mill” type jobs (many applicants, not-so-great pay) post to the site simply for the exposure. Once you identify those, they’re easy to weed out. Another downside is the vetting process isn’t fool-proof. There are jobs sometimes labeled as “All Telecommute” that aren’t. They’re posted by recruiters, for example, who say within the description (usually near the bottom) that you must work onsite.

Recruiter SaturationMedium to High (depending on category/industry)


You may be surprised I listed this one because it’s one of those pesky “job aggregator” sites.

Believe me, Indeed does have a LOT of garbage, especially when it comes to finding remote work. BUT… there is a way you can eliminate much of that and actually find some decent gigs.

The trick is to frame your search properly. And forget the “Location” filter that Indeed offers. It sucks and isn’t necessary anyway.

Let’s say you’re looking for remote SharePoint developer jobs. You might try a search like “SharePoint developer remote,” right?

With Indeed, about 30% of the results you get back will be legitimate remote gigs. The rest will come back as remote because there’s wording like “no remote workers” in the description. What I do is add a few qualifiers to my query so I end up with something like this:

sharepoint developer remote -“no remote” -“onsite only” -“does not allow remote”

Now the percentage of legitimate remote gigs jumps from 30% to somewhere near 60%. That’s a much better number to work with, and I’ve actually found a few remote gigs on Indeed by doing that. I would typically also add “-W2 only” because I don’t take W2-only contracts, but that may not apply in your case and that’s fine.

The downside with Indeed is it’s an aggregator. There’s a lot of garbage even with smarter search queries. Do your due diligence. For example, if you see a company name you don’t recognize, look it up on Google. See where it’s based, whether it’s a recruiting firm, whether it’s been reviewed on Glassdoor, etc.

Recruiter SaturationHigh (as in “off the scale” high)


So that’s my list. I sometimes use Craigslist too but very rarely. It only works as well as it does because I live near Denver, and Denver is a good place to find startups and smaller companies who use remote workers.

If you know of a good site that I missed, please comment and let me know! Spam comments or attempts to promote your own site will be moderated appropriately.

New Blog Name, New Focus

If you follow this blog at all, you might have noticed that early this year I published a post saying I was moving away from SharePoint and back into general software/app development.

But SharePoint is like quick sand. It sucks you back in. And unfortunately I’m good at working with it, which doesn’t help matters.

So I ended up sticking with SharePoint a while longer than I thought, and I deleted the blog post since it was no longer relevant.

Now fast-forward to August 7, 2015.

SharePoint is now only 50% of the project work I do on a regular basis. That definitely feels like a better balance to me. I still get to help clients with SharePoint like I always have, but I now get to do some other things too to retain my sanity.

New Blog Name

Since I’m no longer just “a SharePoint guy”, I renamed my blog in recognition of that change.

The new blog name is yield return post;, a name which I fear only hard-core C# developers will fully appreciate. Nonetheless, I think it’s clever and am sticking with it. I could’ve gone all nerd-pop-culture on you and called it “The TARDIS” or something, but I thought better of it.

New Focus

The focus of this blog will be broader going forward. Rather than focusing only on SharePoint, I’ll start branching out into other development topics – C#, Knockout JS, responsive design, and whatever else I feel like writing about.

I’m as much a writer as I am a developer, and I’m looking forward to writing about more than SharePoint for a change!

What about

All of my existing content is still here and I’ll still post things about SharePoint occasionally, so if you arrived here via my domain looking for SharePoint content, then don’t worry. Your trek was not in vain.

However, be warned that will only work until November 9, 2015. After that, you’ll need to use to visit this blog!

Nested “Include” clauses with SharePoint JSOM API

Recently I needed to load properties two levels deep when using the JSOM (JavaScript Object Model) API in SharePoint 2013. Since it took me a while to find the syntax for it, I figured I’d save others the trouble and just put it right here.

var ctx = SP.ClientContext.get_current();
var folder = ctx.get_web().getFolderByServerRelativeUrl('/server-relative-path/to/folder');
var subfolders = folder.get_folders();

// Here are the nested "Include" clauses. The first loads the
// 'Name' and 'Files' properties of each SP.Folder object in
// the subfolders collection. The second goes a level deeper
// and loads the 'Name' property of each file in the 'Files'
// collection.
ctx.load(subfolders, 'Include(Name, Files.Include(Name))');

   function() {
      var folderLooper = subfolders.getEnumerator();
      while (folderLooper.moveNext()) {
         var subfolder = folderLooper.get_current();
         var fileLooper = subfolder.get_files().getEnumerator();
         while (fileLooper.moveNext()) {
            var file = fileLooper.get_current();

            // This line would throw a 'property or field not initialized'
            // exception if I hadn't used the nested Includes above to load
            // the 'Name' property of each file in the collection.
   function(sender, args) {
      alert('Error: ' + args.get_message());

Making a SharePoint 2013 Workflow Wait for Document Check-In

I was working on a SharePoint 2013 workflow the other day and turned on the “Start workflow automatically when an item is created” setting so my workflow would run whenever a document was uploaded into a document library.

The caveat is SharePoint runs the workflow immediately upon upload and doesn’t wait for an initial check-in to occur (which is a separate step if your document library has required metadata fields that must be filled out).

I needed a way to make the workflow wait for the initial check-in to occur so all the data would be present that was needed by the workflow.

Since the “Current Item” variable in my workflow included a “Level” field (indicates the check-in status of an item), I initially thought I could use the Wait for Field Change in Current Item action and wait for that field to change to “1.”

However, that didn’t work. The workflow would get stuck at the wait action every single time and never come out of it (even when the level changed to 1). I don’t know why, but for some reason that action doesn’t work as expected with the “Level” field.

The good news is I finally found a solution that worked: using a loop.

As shown in the following screenshot, I added a “Wait for Check-In” loop that checks the value of Current Item:Level once per minute and exits the loop when the value is no longer 255 (checked out).

So far that’s worked consistently.

Workflow loop to wait for check-in