Sitecore has two different types of drop-down lookup fields that are available: Droplist and Droplink. Both of them function essentially the same way: they point to a Sitecore data item and list its children in a drop-down list for a content editor. This is a great tool because it allows you (as a data designer) to build a nice set of lookup values and not worry that editors will fat-finger these values.
But why are there the two, and what’s the difference between them? Great question. To explain, I’m going to step back and explain the problem they present.
As part of the new website my company is building in Sitecore, we’re creating a large number of lookups that can be used to categorize and classify items in the Sitecore hierarchy. So on each of those item templates, we chose to add a Droplist that points to the list(s) of lookup values. This works great; it automatically generates that nice, tidy list and allows our content editors to quickly and easily categorize items.
The problem came when we began to develop the presentation components for these items and needed to use a field on the lookup value item. To further explain, let’s look at an example. Let’s say our company sells shirts. You can buy our shirts in three colors: Red, Green, and Blue. However, each ink color costs a different amount, so we need to apply a cost multiplier to each color. Our data layout might look like this:
- Color (lookup to Color)
- Cost Multiplier
Once we had this data structure built for them, our content editors went and filled in the three colors and their respective multipliers and all of the different shirts we sell. Then it was time for us to start rendering this data on our website for people to begin buying our shirts. We create a sublayout for the Shirt item display. It will render the title, description, the color name, and the automatically-computed price (shirt price * color cost multiplier). Let’s look at the code:
// Get the current item Item shirtItem = Sitecore.Context.Item; // Get the string fields' values string shirtTitle = shirtItem["Title"]; string shirtDescription = shirtItem["Description"]; string shirtColor = shirtItem["Color"]; // Get the base price and calculate the adjustment based on the color's cost multiplier float shirtBasePrice = float.Parse(shirtItem["Price"]); LookupField shirtColorField = (LookupField)shirtItem.Fields["Color"]; Item colorItem = shirtColorField.TargetItem; float colorCostMultiplier = float.Parse(colorItem["Cost Multiplier"]); float finalShirtPrice = shirtBasePrice * colorCostMultiplier; // Display them on the page (FieldRenderers/Literals/etc)
But this code breaks; we get a NullReferenceException when we try run the colorItem line. Why? Because–and here’s the important part–the Droplist data type only stores the string value of the item that was chosen by the content editor, not the GUID that would allow us to get back to the item and get its other fields. So aside from doing string matching on the name of the item (dangerous), there’s no way to get back to the actual color item that was chosen.
So to resolve this issue, we had to change the color field on the shirt item template to Droplink instead of Droplist, and then re-pick each of the colors for each of the shirts and resave. Then the code above worked great.
Moral of the story: if you think you might need to access more than just the display name of the item being chosen by a lookup, use Droplink, not Droplist.