public void Go(ContentstackClient stack, OutputWriter writer) { // https://www.contentstack.com/docs/developers/apis/content-delivery-api/#initial-sync // https://www.contentstack.com/docs/platforms/dot-net/api-reference/api/Contentstack.Core.Models.SyncStack.html SyncStack syncStack = stack.SyncRecursive( null, /*Locale*/ SyncType.All, null, /* ContentTypeUID */ DateTime.MinValue).Result; //WARN: in case of multiple events for an Entry, threads running out of event date sequence could load stale data foreach (JObject entryEvent in syncStack.items) { //WARN: https://stackoverflow.com/questions/271440/captured-variable-in-a-loop-in-c-sharp JObject myEntryEvent = entryEvent; ProcessMessage(stack, myEntryEvent, writer); } string syncToken = syncStack.sync_token; // https://www.contentstack.com/docs/developers/apis/content-delivery-api/#subsequent-sync SyncStack updatesSinceSync = stack.SyncToken(syncToken).Result; writer.Message(this, updatesSinceSync.items.Count() + " update(s) since last sync"); foreach (JObject entryEvent in updatesSinceSync.items) { //WARN: https://stackoverflow.com/questions/271440/captured-variable-in-a-loop-in-c-sharp JObject myEntryEvent = entryEvent; ProcessMessage(stack, myEntryEvent, writer); } }
private void ProcessBatch(int batchNumber, ContentstackCollection <FieldSubsetEntry> entries, string contentTypeUid, OutputWriter writer) { foreach (FieldSubsetEntry entry in entries.Items) { writer.Message(this, $"batch {batchNumber} [{contentTypeUid}] : {entry.Title}"); } }
public void Go( ContentstackClient stack, string assetUid, OutputWriter writer) { Asset asset = stack.Asset(assetUid).Fetch().Result; writer.Message(this, asset.Url + " : " + asset.FileSize); }
private void ProcessMessage(ContentstackClient stack, JObject entryEvent, OutputWriter writer) { string contentTypeUid = entryEvent["content_type_uid"].ToString(); string eventType = entryEvent["type"].ToString(); DateTime eventDate = TimeZoneInfo.ConvertTimeFromUtc( DateTime.Parse(entryEvent["event_at"].ToString()), TimeZoneInfo.Local); string entryUid = null; if (entryEvent["data"].SelectToken("uid") != null) { entryUid = entryEvent["data"]["uid"].ToString(); } switch (eventType) { case "entry_published": // optional (retrieve metadata for media assets) foreach (JValue toReplace in entryEvent.SelectTokens("$..asset")) { string assetId = toReplace.ToString(); // https://www.contentstack.com/docs/developers/apis/content-delivery-api/#get-a-single-asset Asset asset = stack.Asset(assetId).Fetch().GetAwaiter().GetResult(); JObject withJson = new JObject(); withJson["url"] = asset.Url; withJson["filename"] = asset.FileName; toReplace.Replace(withJson); } Entry entry = entryEvent["data"].ToObject <Entry>(JsonSerializer.Create(stack.SerializerSettings)); writer.Message(this, $"{entryUid} [{contentTypeUid}] : {entry.Title}"); break; case "asset_published": case "asset_unpublished": case "asset_deleted": case "content_type_deleted": case "entry_unpublished": case "entry_deleted": default: writer.Message(this, $"{eventDate} : {eventType}"); break; } }
public void Go( ContentstackClient stack, string contentTypeUid, string entryUid, OutputWriter writer) { //TODO: does this really invoke REST API? // https://www.contentstack.com/docs/developers/apis/content-delivery-api/#get-a-single-content-type // https://www.contentstack.com/docs/platforms/dot-net/api-reference/api/Contentstack.Core.Models.ContentType.html ContentType contentType = stack.ContentType(contentTypeUid); // https://www.contentstack.com/docs/developers/apis/content-delivery-api/#get-a-single-entry // https://www.contentstack.com/docs/platforms/dot-net/api-reference/api/Contentstack.Core.Models.Entry.html contentType.Entry(entryUid).Fetch <Entry>().ContinueWith((t) => { Entry entry = t.Result; string message = $"Asynchronous: {entry.Uid} : {entry.Title}"; JObject entryJson = entry.ToJson(); if (entryJson.ContainsKey("url")) { message += " (" + entryJson["url"] + ")"; } writer.Message(this, message); }); Entry entry = contentType.Entry(entryUid).Fetch <Entry>().GetAwaiter().GetResult(); if (entry != null) { string message = $"Synchronous: {entry.Uid} : {entry.Title}"; JObject entryJson = entry.ToJson(); if (entryJson.ContainsKey("url")) { message += " (" + entryJson["url"] + ")"; } writer.Message(this, message); } }
private void ProcessContentType(ContentstackClient stack, string contentTypeUid, OutputWriter writer) { //TODO: paging results with threads? // https://www.contentstack.com/docs/developers/apis/graphql-content-delivery-api/explorer/?api_key=APIKEY&access_token=DELIVERY_TOKEN&environment=ENVIRONMENT string query = "{all_" + contentTypeUid + "{total items{url title system{uid}}}}"; using (HttpClient http = new HttpClient()) { string request = "https://graphql.contentstack.com/stacks/" + stack.GetApplicationKey() + "?access_token=" + stack.GetAccessToken() + "&environment=" + stack.GetEnvironment() + "contentdelivery&query=" + query; int attempt = 0; do { try { JObject fromGraphQl = JObject.Parse(http.GetStringAsync(request).GetAwaiter().GetResult()); int count = Int32.Parse(fromGraphQl["data"]["all_" + contentTypeUid]["total"].ToString()); foreach (JToken group in fromGraphQl.SelectTokens("$.data.all_" + contentTypeUid + ".items")) { JToken myGroup = group; foreach (var entry in myGroup.Children()) { string entryUid = entry.SelectToken("system").SelectToken("uid").ToString(); writer.Message(this, $"{entryUid} [{contentTypeUid}] : {entry["title"]} ({entry["url"]})"); } } attempt = 3; } catch (Exception ex) { writer.Message(this, ex + " : " + ex.Message); } }while (attempt++ < 3); } }
public void Go( ContentstackClient stack, string contentTypeUid, string entryUid, OutputWriter writer) { //TODO: does this really invoke REST API? // https://www.contentstack.com/docs/developers/apis/content-delivery-api/#get-a-single-content-type // https://www.contentstack.com/docs/platforms/dot-net/api-reference/api/Contentstack.Core.Models.ContentType.html ContentType contentType = stack.ContentType(contentTypeUid); // https://www.contentstack.com/docs/developers/apis/content-delivery-api/#get-a-single-entry BasicEntry directEntry = contentType.Entry(entryUid).Fetch <BasicEntry>().GetAwaiter().GetResult(); writer.Message(this, "Direct: " + directEntry.CreatedAt); Entry entry = contentType.Entry(entryUid).Fetch <Entry>().GetAwaiter().GetResult(); JObject entryJson = entry.ToJson(); BasicEntry convertedEntry = entryJson.ToObject <BasicEntry>(JsonSerializer.Create(stack.SerializerSettings)); writer.Message(this, "Converted: " + directEntry.CreatedAt); }
private void ProcessBatch(int batchNumber, ContentstackCollection <Entry> entries, string contentTypeUid, OutputWriter writer) { foreach (Entry entry in entries.Items) { string message = $"batch {batchNumber} [{contentTypeUid}] : {entry.Uid} : {entry.Title}"; if (entry.Object.ContainsKey("url")) { message += " (" + entry.Object["url"] + ")"; } writer.Message(this, message); } }
// private int ContentstackQueryResultLimit { get; } = 100; public void Go(ContentstackClient stack, OutputWriter writer) { // https://www.contentstack.com/docs/developers/apis/content-delivery-api/#get-all-content-types foreach (JObject contentTypeJson in stack.GetContentTypes().GetAwaiter().GetResult()) { string contentTypeUid = contentTypeJson["uid"].ToString(); if (contentTypeJson.SelectToken("$..[?(@.uid=='url')]") == null) { writer.Message(this, contentTypeUid + " does not define URL field; skip."); continue; } new Thread(() => { ProcessContentType(stack, contentTypeUid, writer); }).Start(); } }