Scheduling content unpublishing

It's often useful to allow content contributors to define the period when a content item will be published. If you are on a Professional plan or higher, you can schedule content publishing directly in Kentico Cloud. If you want to define a date when your content will expire and no longer be available in your app, you need to take additional steps.

Table of contents

    Implementing scheduled unpublishing is a 3 step process:

    1. Add a Publish until date element to the underlying content type.
    2. Add the unpublish dates to the content items.
    3. Inside your app, check the dates and only display those content items that are supposed to be public.

    Let's go through it on a simple example and add this functionality to the Kentico Cloud sample project.

    Our sample apps have an Articles section that displays all published articles. We will make a few changes to the sample project and the sample site to show only articles that are in their publishing period.

    1. Add unpublish dates to the underlying content type

    The content structure of all articles in our project is defined by the Article content type.

    1. From the app menu, choose Content models .
    2. Click the Article content type to open it.
    3. Drag in a Date & time content element from the right.
    4. Name it Publish until.
    5. You can add helpful guidelines for your content contributors, such as The article should be public until this day.

    Adding a Date & time element to a content type

    Pro tip

    If you need to add the same elements to a lot of content types, use Content snippets.
    In this case, you can wrap the Publish until date element in a Publishing period content snippet.

    Update content models inside the app

    To use the newly added unpublish date element inside the sample application, we have to add it to our model class.

    • Java
    public final class Article extends ContentItem { public static final String TYPE = "article"; public Date getPublishUntil() { return publishUntil.getValue(); } ... }
    public final class Article extends ContentItem { public static final String TYPE = "article"; public Date getPublishUntil() { return publishUntil.getValue(); } ... }
    • Swift
    var publishUntil: DateTimeElement? ... public required init?(map: Map){ let mapper = MapElement.init(map: map) publishUntil = mapper.map(elementName: "publish_until", elementType: DateTimeElement.self) ... }
    var publishUntil: DateTimeElement? ... public required init?(map: Map){ let mapper = MapElement.init(map: map) publishUntil = mapper.map(elementName: "publish_until", elementType: DateTimeElement.self) ... }
    • Java
    @ElementMapping("publish_until") ZonedDateTime publishUntil; public ZonedDateTime getPublishUntil() { return publishUntil; } public void setPublishUntil(ZonedDateTime publishUntil) { this.publishUntil = publishUntil; }
    @ElementMapping("publish_until") ZonedDateTime publishUntil; public ZonedDateTime getPublishUntil() { return publishUntil; } public void setPublishUntil(ZonedDateTime publishUntil) { this.publishUntil = publishUntil; }
    • JavaScript
    export class Article extends KenticoCloud.ContentItem { constructor(){ super({ propertyResolver: ((fieldName) => { if (fieldName === "publish_until"){ return "publishUntil"; } ... }), }) } }
    export class Article extends KenticoCloud.ContentItem { constructor(){ super({ propertyResolver: ((fieldName) => { if (fieldName === "publish_until"){ return "publishUntil"; } ... }), }) } }
    • C#
    public const string PublishUntilCodename = "publish_until"; public DateTime? PublishUntil { get; set; }
    public const string PublishUntilCodename = "publish_until"; public DateTime? PublishUntil { get; set; }
    • PHP
    <?php class ArticleModel { public $publishUntil = null; ... }
    <?php class ArticleModel { public $publishUntil = null; ... }
    • TypeScript
    export class Article extends ContentItem { public publishUntil: Fields.DateTimeField; ... }
    export class Article extends ContentItem { public publishUntil: Fields.DateTimeField; ... }

    Note: You can learn more about Using strongly-typed models.

    2. Define unpublish dates in the content items

    Now add the dates to each of your articles.

    1. From the app menu, choose Content & Assets .
    2. Using the filters on the left, select the Article content type to view only articles.
    3. Click an article to edit it.
    4. Fill in the Publish until date element.
    5. Repeat for all articles.

    Prepared dates in the Publish until element

    3. Only display articles that are supposed to be public now

    There are two basic ways to ensure your app only displays articles that should be public:

    • Adding a filter to your application
    • Filtering by date with the Delivery API

    The main difference is that when you modify your application you can add checks for content with empty dates. Filtering by date with the Delivery API retrieves less content and so should be faster, but will exclude items with null values for Publish until.

    Adding a filter to your application

    With this technique, you modify your application to check the publish dates of each content item. Currently, the sample app fetches all Article content items.

    Add a middle step that filters out all articles that aren't supposed to be public at the time.

    • Java
    import com.kenticocloud.delivery_core.*; import com.kenticocloud.delivery_rx.*; import io.reactivex.Observer; import io.reactivex.disposables.Disposable; import io.reactivex.functions.Function; Date now = new Date(); // Prepares an array to hold strongly-typed models List<TypeResolver<?>> typeResolvers = new ArrayList<>(); // Registers the type resolvers typeResolvers.add(new TypeResolver<>(Article.TYPE, new Function<Void, Article>() { @Override public Article apply(Void input) { return new Article(); } })); // Prepares the DeliveryService configuration object String projectId = "14372844-0a5d-434a-8423-605b8a631623"; IDeliveryConfig config = DeliveryConfig.newConfig(projectId) .withTypeResolvers(typeResolvers); // Initializes a DeliveryService for Java projects IDeliveryService deliveryService = new DeliveryService(config); // Gets all articles using a simple request List<Article> articles = deliveryService.<Article>items() .equalsFilter("system.type", "article") .get() .getItems(); List<Article> publishedItems = new ArrayList<>(); for (Article article : articles) { if ( article.getPublishUntil() == null || article.getPublishUntil().after(now)) { publishedItems.add(article); } } // Gets all articles using RxJava2 deliveryService.<Article>items() .equalsFilter("system.type", "article") .getObservable() .subscribe(new Observer<DeliveryItemListingResponse<Article>>() { @Override public void onSubscribe(Disposable d) { } @Override public void onNext(DeliveryItemListingResponse<Article> response) { Date now = new Date(); // Gets the retrieved articles List<Article> articles = response.getItems(); List<Article> publishedItems = new ArrayList<>(); // Filters the articles, keeping those that should be public for (Article article : articles) { if (article.getPublishUntil() == null || article.getPublishUntil().after(now)) { publishedItems.add(article); } } } @Override public void onError(Throwable e) { } @Override public void onComplete() { } });
    import com.kenticocloud.delivery_core.*; import com.kenticocloud.delivery_rx.*; import io.reactivex.Observer; import io.reactivex.disposables.Disposable; import io.reactivex.functions.Function; Date now = new Date(); // Prepares an array to hold strongly-typed models List<TypeResolver<?>> typeResolvers = new ArrayList<>(); // Registers the type resolvers typeResolvers.add(new TypeResolver<>(Article.TYPE, new Function<Void, Article>() { @Override public Article apply(Void input) { return new Article(); } })); // Prepares the DeliveryService configuration object String projectId = "14372844-0a5d-434a-8423-605b8a631623"; IDeliveryConfig config = DeliveryConfig.newConfig(projectId) .withTypeResolvers(typeResolvers); // Initializes a DeliveryService for Java projects IDeliveryService deliveryService = new DeliveryService(config); // Gets all articles using a simple request List<Article> articles = deliveryService.<Article>items() .equalsFilter("system.type", "article") .get() .getItems(); List<Article> publishedItems = new ArrayList<>(); for (Article article : articles) { if ( article.getPublishUntil() == null || article.getPublishUntil().after(now)) { publishedItems.add(article); } } // Gets all articles using RxJava2 deliveryService.<Article>items() .equalsFilter("system.type", "article") .getObservable() .subscribe(new Observer<DeliveryItemListingResponse<Article>>() { @Override public void onSubscribe(Disposable d) { } @Override public void onNext(DeliveryItemListingResponse<Article> response) { Date now = new Date(); // Gets the retrieved articles List<Article> articles = response.getItems(); List<Article> publishedItems = new ArrayList<>(); // Filters the articles, keeping those that should be public for (Article article : articles) { if (article.getPublishUntil() == null || article.getPublishUntil().after(now)) { publishedItems.add(article); } } } @Override public void onError(Throwable e) { } @Override public void onComplete() { } });
    • Swift
    import KenticoCloud let client = DeliveryClient.init(projectId: "14372844-0a5d-434a-8423-605b8a631623") let articlesQueryParameters = QueryBuilder.params().type("article") // More about strongly-typed models https://github.com/Kentico/cloud-sdk-swift#using-strongly-typed-models client.getItems(modelType: Article.self, queryParameters: articleQueryParameters) { (isSuccess, itemsResponse, error) in if isSuccess { if let articles = itemsResponse?.items { let now = Date() // Filters out the articles with no value in Publish until elements var publishedArticles = articles.filter { (($0.publishUntil?.value)! > now) } } } else { if let error = error { print(error) } } }
    import KenticoCloud let client = DeliveryClient.init(projectId: "14372844-0a5d-434a-8423-605b8a631623") let articlesQueryParameters = QueryBuilder.params().type("article") // More about strongly-typed models https://github.com/Kentico/cloud-sdk-swift#using-strongly-typed-models client.getItems(modelType: Article.self, queryParameters: articleQueryParameters) { (isSuccess, itemsResponse, error) in if isSuccess { if let articles = itemsResponse?.items { let now = Date() // Filters out the articles with no value in Publish until elements var publishedArticles = articles.filter { (($0.publishUntil?.value)! > now) } } } else { if let error = error { print(error) } } }
    • Java
    import com.kenticocloud.delivery; DeliveryClient client = new DeliveryClient("14372844-0a5d-434a-8423-605b8a631623"); List<NameValuePair> params = DeliveryParameterBuilder.params() .filterEquals("system.type", "article") .build(); // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models List<ArticleItem> items = client.getItems(ArticleItem.class, params); List<ArticleItem> publishedItems = items.stream() .filter(item -> (item.getPublishUntil() > today || item.getPublishUntil() == null)) .collect(Collectors.toList());
    import com.kenticocloud.delivery; DeliveryClient client = new DeliveryClient("14372844-0a5d-434a-8423-605b8a631623"); List<NameValuePair> params = DeliveryParameterBuilder.params() .filterEquals("system.type", "article") .build(); // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models List<ArticleItem> items = client.getItems(ArticleItem.class, params); List<ArticleItem> publishedItems = items.stream() .filter(item -> (item.getPublishUntil() > today || item.getPublishUntil() == null)) .collect(Collectors.toList());
    • JavaScript
    const KenticoCloud = require("kentico-cloud-delivery); const _ = require("underscore"); // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models class Article extends KenticoCloud.ContentItem { constructor() { super(); } } const deliveryClient = new KenticoCloud.DeliveryClient({ projectId: "14372844-0a5d-434a-8423-605b8a631623", typeResolvers: [ new KenticoCloud.TypeResolver("article", () => new Article) ] }); const d = new Date(); const now = d.toISOString(); deliveryClient.items() .type("article") .getObservable() .subscribe(response => console.log(_.filter(response.items, function (i) { return ((i.PublishUntil > now || i.PublishUntil === undefined || i.PublishUntil === null)) })));
    const KenticoCloud = require("kentico-cloud-delivery); const _ = require("underscore"); // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models class Article extends KenticoCloud.ContentItem { constructor() { super(); } } const deliveryClient = new KenticoCloud.DeliveryClient({ projectId: "14372844-0a5d-434a-8423-605b8a631623", typeResolvers: [ new KenticoCloud.TypeResolver("article", () => new Article) ] }); const d = new Date(); const now = d.toISOString(); deliveryClient.items() .type("article") .getObservable() .subscribe(response => console.log(_.filter(response.items, function (i) { return ((i.PublishUntil > now || i.PublishUntil === undefined || i.PublishUntil === null)) })));
    • C#
    using KenticoCloud.Delivery; // Initializes a content delivery client IDeliveryClient client = DeliveryClientBuilder .WithProjectId("14372844-0a5d-434a-8423-605b8a631623") .Build(); // Gets all articles // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models var response = await client.GetItemsAsync<Article>( new EqualsFilter("system.type", "article") ); var today = System.DateTime.Today; // Filters the articles, keeping those that should be public var itemsToDisplay = response.Items.Where((item) => (item.PublishUntil > today || item.PublishUntil == null)); return View(itemsToDisplay);
    using KenticoCloud.Delivery; // Initializes a content delivery client IDeliveryClient client = DeliveryClientBuilder .WithProjectId("14372844-0a5d-434a-8423-605b8a631623") .Build(); // Gets all articles // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models var response = await client.GetItemsAsync<Article>( new EqualsFilter("system.type", "article") ); var today = System.DateTime.Today; // Filters the articles, keeping those that should be public var itemsToDisplay = response.Items.Where((item) => (item.PublishUntil > today || item.PublishUntil == null)); return View(itemsToDisplay);
    • PHP
    <?php // Defined by Composer to include required libraries require __DIR__ . "/vendor/autoload.php"; use \Datetime; use KenticoCloud\Delivery\DeliveryClient; use KenticoCloud\Delivery\QueryParams; $client = new DeliveryClient("14372844-0a5d-434a-8423-605b8a631623"); $items = $client->getItems((new QueryParams()) ->equals("system.type", "article")); $publishedArticles = array_filter($items->items, function($item){ $now = new DateTime(); return ($item->publishUntil > $now || is_null($item->publishUntil)); });
    <?php // Defined by Composer to include required libraries require __DIR__ . "/vendor/autoload.php"; use \Datetime; use KenticoCloud\Delivery\DeliveryClient; use KenticoCloud\Delivery\QueryParams; $client = new DeliveryClient("14372844-0a5d-434a-8423-605b8a631623"); $items = $client->getItems((new QueryParams()) ->equals("system.type", "article")); $publishedArticles = array_filter($items->items, function($item){ $now = new DateTime(); return ($item->publishUntil > $now || is_null($item->publishUntil)); });
    • Ruby
    require "delivery-sdk-ruby" delivery_client = KenticoCloud::Delivery::DeliveryClient.new project_id: "14372844-0a5d-434a-8423-605b8a631623" delivery_client.items("system.type".eq("article")) .execute do |response| now = DateTime.now.strftime "%Y-%M-%dT%H:%M:%SZ" items_to_display = response.items.select { |i| i.publish_until > now || i.publish_until.nil? } end
    require "delivery-sdk-ruby" delivery_client = KenticoCloud::Delivery::DeliveryClient.new project_id: "14372844-0a5d-434a-8423-605b8a631623" delivery_client.items("system.type".eq("article")) .execute do |response| now = DateTime.now.strftime "%Y-%M-%dT%H:%M:%SZ" items_to_display = response.items.select { |i| i.publish_until > now || i.publish_until.nil? } end
    • TypeScript
    import { ContentItem, DeliveryClient, Fields, TypeResolver } from "kentico-cloud-delivery"; import * as _ from "underscore"; // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models export class Article extends ContentItem { public title: Fields.TextField; public summary: Fields.TextField; public post_date: Fields.DateTimeField; public teaser_image: Fields.AssetsField; public related_articles: Article[]; } const deliveryClient = new DeliveryClient({ projectId: "14372844-0a5d-434a-8423-605b8a631623", typeResolvers: [ new TypeResolver("article", () => new Article) ] }); const d = new Date(); const now = d.toISOString(); deliveryClient.items<Article>() .type("article") .getObservable() .subscribe(response => console.log(_.filter(response.items, function (i) { return ((i.PublishUntil > now || i.PublishUntil === undefined || i.PublishUntil === null)) })));
    import { ContentItem, DeliveryClient, Fields, TypeResolver } from "kentico-cloud-delivery"; import * as _ from "underscore"; // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models export class Article extends ContentItem { public title: Fields.TextField; public summary: Fields.TextField; public post_date: Fields.DateTimeField; public teaser_image: Fields.AssetsField; public related_articles: Article[]; } const deliveryClient = new DeliveryClient({ projectId: "14372844-0a5d-434a-8423-605b8a631623", typeResolvers: [ new TypeResolver("article", () => new Article) ] }); const d = new Date(); const now = d.toISOString(); deliveryClient.items<Article>() .type("article") .getObservable() .subscribe(response => console.log(_.filter(response.items, function (i) { return ((i.PublishUntil > now || i.PublishUntil === undefined || i.PublishUntil === null)) })));

    It's a good idea to check for null values and implicitly show articles with empty date fields. This allows you to create content that never expires.

    That's it. Content contributors can now easily define unpublish dates for their articles.

    Filtering by date with the Delivery API

    With this technique, you filter items directly in the API call using query parameters. The principle is the same. The only difference is that this approach will not display items that have null values for their unpublish dates. Have a look at the example below:

    • Java
    import com.kenticocloud.delivery_core.*; import com.kenticocloud.delivery_rx.*; import io.reactivex.Observer; import io.reactivex.disposables.Disposable; import io.reactivex.functions.Function; String now = new Date().toInstant().toString(); // Prepares an array to hold strongly-typed models List<TypeResolver<?>> typeResolvers = new ArrayList<>(); // Registers the type resolvers typeResolvers.add(new TypeResolver<>(Article.TYPE, new Function<Void, Article>() { @Override public Article apply(Void input) { return new Article(); } })); // Prepares the DeliveryService configuration object String projectId = "14372844-0a5d-434a-8423-605b8a631623"; IDeliveryConfig config = DeliveryConfig.newConfig(projectId) .withTypeResolvers(typeResolvers); // Initializes a DeliveryService for Java projects IDeliveryService deliveryService = new DeliveryService(config); // Gets the articles that should be public using a simple request List<Article> articles = deliveryService.<Article>items() .equalsFilter("system.type", "article") .greaterThanFilter("elements.publish_until", now) .get() .getItems(); // Gets the articles that should be public using RxJava2 deliveryService.<Article>items() .equalsFilter("system.type", "article") .greaterThanFilter("elements.publish_until", now) .getObservable() .subscribe(new Observer<DeliveryItemListingResponse<Article>>() { @Override public void onSubscribe(Disposable d) { } @Override public void onNext(DeliveryItemListingResponse<Article> response) { // Gets the mapped articles List<Article> articles = response.getItems(); } @Override public void onError(Throwable e) { } @Override public void onComplete() { } });
    import com.kenticocloud.delivery_core.*; import com.kenticocloud.delivery_rx.*; import io.reactivex.Observer; import io.reactivex.disposables.Disposable; import io.reactivex.functions.Function; String now = new Date().toInstant().toString(); // Prepares an array to hold strongly-typed models List<TypeResolver<?>> typeResolvers = new ArrayList<>(); // Registers the type resolvers typeResolvers.add(new TypeResolver<>(Article.TYPE, new Function<Void, Article>() { @Override public Article apply(Void input) { return new Article(); } })); // Prepares the DeliveryService configuration object String projectId = "14372844-0a5d-434a-8423-605b8a631623"; IDeliveryConfig config = DeliveryConfig.newConfig(projectId) .withTypeResolvers(typeResolvers); // Initializes a DeliveryService for Java projects IDeliveryService deliveryService = new DeliveryService(config); // Gets the articles that should be public using a simple request List<Article> articles = deliveryService.<Article>items() .equalsFilter("system.type", "article") .greaterThanFilter("elements.publish_until", now) .get() .getItems(); // Gets the articles that should be public using RxJava2 deliveryService.<Article>items() .equalsFilter("system.type", "article") .greaterThanFilter("elements.publish_until", now) .getObservable() .subscribe(new Observer<DeliveryItemListingResponse<Article>>() { @Override public void onSubscribe(Disposable d) { } @Override public void onNext(DeliveryItemListingResponse<Article> response) { // Gets the mapped articles List<Article> articles = response.getItems(); } @Override public void onError(Throwable e) { } @Override public void onComplete() { } });
    • Swift
    import KenticoCloud let client = DeliveryClient.init(projectId: "14372844-0a5d-434a-8423-605b8a631623") // Formats current date & time to ISO-8601 let dateformatter = DateFormatter() dateformatter.dateFormat = "yyyy-MM-dd"T"HH:mm:ss"Z"" let now = dateformatter.string(from: Date()) let customQuery = "items?system.type=article&elements.publish_until[gt]=\(now)" // More about strongly-typed models https://github.com/Kentico/cloud-sdk-swift#using-strongly-typed-models client.getItems(modelType: Article.self, customQuery: customQuery) { (isSuccess, itemsResponse, error) in if isSuccess { if let articles = itemsResponse?.items { // Use your items here } } else { if let error = error { print(error) } } }
    import KenticoCloud let client = DeliveryClient.init(projectId: "14372844-0a5d-434a-8423-605b8a631623") // Formats current date & time to ISO-8601 let dateformatter = DateFormatter() dateformatter.dateFormat = "yyyy-MM-dd"T"HH:mm:ss"Z"" let now = dateformatter.string(from: Date()) let customQuery = "items?system.type=article&elements.publish_until[gt]=\(now)" // More about strongly-typed models https://github.com/Kentico/cloud-sdk-swift#using-strongly-typed-models client.getItems(modelType: Article.self, customQuery: customQuery) { (isSuccess, itemsResponse, error) in if isSuccess { if let articles = itemsResponse?.items { // Use your items here } } else { if let error = error { print(error) } } }
    • Java
    import com.kenticocloud.delivery; DeliveryClient client = new DeliveryClient("14372844-0a5d-434a-8423-605b8a631623"); TimeZone tz = TimeZone.getTimeZone("UTC"); DateFormat df = new SimpleDateFormat("yyyy-MM-dd"T"HH:mm"Z""); df.setTimeZone(tz); String now = df.format(new Date()); List<NameValuePair> params = DeliveryParameterBuilder.params() .filterEquals("system.type", "article") .filterGreaterThan("elements.publish_until", now) .build(); // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models List<ArticleItem> items = client.getItems(ArticleItem.class, params);
    import com.kenticocloud.delivery; DeliveryClient client = new DeliveryClient("14372844-0a5d-434a-8423-605b8a631623"); TimeZone tz = TimeZone.getTimeZone("UTC"); DateFormat df = new SimpleDateFormat("yyyy-MM-dd"T"HH:mm"Z""); df.setTimeZone(tz); String now = df.format(new Date()); List<NameValuePair> params = DeliveryParameterBuilder.params() .filterEquals("system.type", "article") .filterGreaterThan("elements.publish_until", now) .build(); // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models List<ArticleItem> items = client.getItems(ArticleItem.class, params);
    • JavaScript
    const KenticoCloud = require("kentico-cloud-delivery"); // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models class Article extends KenticoCloud.ContentItem { constructor() { super(); } } const deliveryClient = new KenticoCloud.DeliveryClient({ projectId: "14372844-0a5d-434a-8423-605b8a631623", typeResolvers: [ new KenticoCloud.TypeResolver("article", () => new Article) ] }); const d = new Date(); const now = d.toISOString(); deliveryClient.items() .type("article") .greaterThanFilter("elements.publish_until", now) .getObservable() .subscribe(response => console.log(response));
    const KenticoCloud = require("kentico-cloud-delivery"); // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models class Article extends KenticoCloud.ContentItem { constructor() { super(); } } const deliveryClient = new KenticoCloud.DeliveryClient({ projectId: "14372844-0a5d-434a-8423-605b8a631623", typeResolvers: [ new KenticoCloud.TypeResolver("article", () => new Article) ] }); const d = new Date(); const now = d.toISOString(); deliveryClient.items() .type("article") .greaterThanFilter("elements.publish_until", now) .getObservable() .subscribe(response => console.log(response));
    • C#
    // Initializes a content delivery client IDeliveryClient client = DeliveryClientBuilder .WithProjectId("14372844-0a5d-434a-8423-605b8a631623") .Build(); var now = System.DateTime.Now.ToString("yyyy-MM-ddTHH:mm:ssZ"); // Gets articles that should be public // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models DeliveryItemListingResponse<Article> response = await client.GetItemsAsync<Article>( new EqualsFilter("system.type", "article"), new GreaterThanFilter("elements.publish_until", now) ); return View(response.Items);
    // Initializes a content delivery client IDeliveryClient client = DeliveryClientBuilder .WithProjectId("14372844-0a5d-434a-8423-605b8a631623") .Build(); var now = System.DateTime.Now.ToString("yyyy-MM-ddTHH:mm:ssZ"); // Gets articles that should be public // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models DeliveryItemListingResponse<Article> response = await client.GetItemsAsync<Article>( new EqualsFilter("system.type", "article"), new GreaterThanFilter("elements.publish_until", now) ); return View(response.Items);
    • PHP
    <?php // Defined by Composer to include required libraries require __DIR__ . "/vendor/autoload.php"; use \Datetime; use KenticoCloud\Delivery\DeliveryClient; use KenticoCloud\Delivery\QueryParams; $client = new DeliveryClient("14372844-0a5d-434a-8423-605b8a631623");, $now = date_format(new DateTime(),"Y-m-d\TH:i:s\Z"); $items = $client->getItems((new QueryParams()) ->equals("system.type", "article") ->greaterThan("elements.publish_until", $now));
    <?php // Defined by Composer to include required libraries require __DIR__ . "/vendor/autoload.php"; use \Datetime; use KenticoCloud\Delivery\DeliveryClient; use KenticoCloud\Delivery\QueryParams; $client = new DeliveryClient("14372844-0a5d-434a-8423-605b8a631623");, $now = date_format(new DateTime(),"Y-m-d\TH:i:s\Z"); $items = $client->getItems((new QueryParams()) ->equals("system.type", "article") ->greaterThan("elements.publish_until", $now));
    • Ruby
    require "delivery-sdk-ruby" delivery_client = KenticoCloud::Delivery::DeliveryClient.new project_id: "14372844-0a5d-434a-8423-605b8a631623" now = DateTime.now.strftime "%Y-%M-%dT%H:%M:%SZ" delivery_client.items([ "system.type".eq("article"), "elements.publish_until".gt(now) ]) .execute do |response| items = response.items end
    require "delivery-sdk-ruby" delivery_client = KenticoCloud::Delivery::DeliveryClient.new project_id: "14372844-0a5d-434a-8423-605b8a631623" now = DateTime.now.strftime "%Y-%M-%dT%H:%M:%SZ" delivery_client.items([ "system.type".eq("article"), "elements.publish_until".gt(now) ]) .execute do |response| items = response.items end
    • TypeScript
    import { ContentItem, DeliveryClient, Fields, TypeResolver } from "kentico-cloud-delivery"; // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models export class Article extends ContentItem { public title: Fields.TextField; public summary: Fields.TextField; public post_date: Fields.DateTimeField; public teaser_image: Fields.AssetsField; public related_articles: Article[]; } const deliveryClient = new DeliveryClient({ projectId: "14372844-0a5d-434a-8423-605b8a631623", typeResolvers: [ new TypeResolver("article", () => new Article) ] }); const d = new Date(); const now = d.toISOString(); deliveryClient.items<Article>() .type("article") .greaterThanFilter("elements.publish_until", now) .getObservable() .subscribe(response => console.log(response));
    import { ContentItem, DeliveryClient, Fields, TypeResolver } from "kentico-cloud-delivery"; // Create strongly typed models according to https://developer.kenticocloud.com/docs/strongly-typed-models export class Article extends ContentItem { public title: Fields.TextField; public summary: Fields.TextField; public post_date: Fields.DateTimeField; public teaser_image: Fields.AssetsField; public related_articles: Article[]; } const deliveryClient = new DeliveryClient({ projectId: "14372844-0a5d-434a-8423-605b8a631623", typeResolvers: [ new TypeResolver("article", () => new Article) ] }); const d = new Date(); const now = d.toISOString(); deliveryClient.items<Article>() .type("article") .greaterThanFilter("elements.publish_until", now) .getObservable() .subscribe(response => console.log(response));

    Make sure to use the present date and time in a correct ISO 8601 format. You can only use & (logical conjunction) to combine query parameters.

    See Content filtering in the API reference for more details.

    What's next?

    This tutorial showed you how to add unpublish date elements to your content to define the time when it will automatically be unpublished from your app. You can do so inside your application if you want content that doesn't expire, or directly in your API call if you want your content faster and all your content has an expiration date.