CAML Query for Publishing Pages

This blog posting applies to Microsoft Office SharePoint Server 2007.

The "Scheduling Start Date" and "Scheduling End Date" on Page content types created by the Publishing feature work great in default views of Pages libraries: SharePoint filters by these dates automatically.  But when you're using code to return the items from a Pages library--e.g. list.GetItems(query)--you must filter them explicitly by constructing the appropriate query. 

One necessary fact may not be clear: these two date fields use a null value to indicate special dates "Immediately" and "Never" respectively (I know, the SDK says that special date values are used, but it doesn't behave this way).  So, a CAML query to return all Pages by valid Scheduling dates (named Publishing dates internally), including Immediately and Never, is as follows:

<Where>

      <And>

            <Or>

                  <Leq>

                        <FieldRef Name='PublishingStartDate'/>

                        <Value Type='DateTime'>

                              <Today/>

                        </Value>

                  </Leq>

                  <IsNull>

                        <FieldRef Name='PublishingStartDate'/>

                  </IsNull>

            </Or>

            <Or>

                  <Geq>

                        <FieldRef Name='PublishingExpirationDate'/>

                        <Value Type='DateTime'>

                              <Today/>

                        </Value>

                  </Geq>

                  <IsNull>

                        <FieldRef Name='PublishingExpirationDate'/>

                  </IsNull>

            </Or>

      </And>

</Where>

Note, Content Query Web Part filters--the filters that you see in the task pane when you modify the web part--don’t work with these dates. But they wouldn't be that useful even if they did work, since you'd probably need four filters and only three are provided. (Also note, changing the number of filters would be extremely difficult.) 

So if you want to use CQWP in conjunction with these dates, you have two choices. Of course you can use the above technique to filter by the dates using the CAML query. But this means your filters will be disabled for other purposes, and your users may not want that. 

The other choice is to use these dates in the way they were intended! Anything that displays a link to a document in SharePoint, including the CQWP, will obey these publishing dates for users that don’t have the “Edit Items” permission. Since many of your users will probably need this permission, the way to set it up is to use a separate site for the items you want to show according to publishing dates. The "News" site that's created as a subsite of the portal is an excellent example of this. Now, on the News site, put everyone in your organization into the "Visitor" group, and only add news editors into the "Member" group. Then, editors will be able to see items outside of their publication dates, so they can edit them, but everyone else will only see articles that are within the publishing dates. This includes when they are displayed in the CQWP, without having to use CAML queries.