From 88233f8a20553b18867d60f3345249dfb31c6d6a Mon Sep 17 00:00:00 2001 From: Tobias Klika Date: Wed, 1 Apr 2015 02:11:29 +0200 Subject: [PATCH] complete implementation of appmetadata + images --- src/OnePeek.Api/AppMetadataEndpoint.cs | 42 ++++++++++----- src/OnePeek.Api/Extensions/XmlExtensions.cs | 29 ++++++++++ src/OnePeek.Api/OnePeek.Api.csproj | 1 + src/OnePeek.Entities/AppImage.cs | 16 ++++++ src/OnePeek.Entities/AppMetadata.cs | 57 +++++++++++++++++--- src/OnePeek.Entities/AppPublisher.cs | 13 +++-- src/OnePeek.Entities/AppRating.cs | 12 ++--- src/OnePeek.Entities/AppReviews.cs | 4 +- src/OnePeek.Entities/OnePeek.Entities.csproj | 1 + src/OnePeek.WebConsole/HomeModule.cs | 5 +- 10 files changed, 140 insertions(+), 40 deletions(-) create mode 100644 src/OnePeek.Api/Extensions/XmlExtensions.cs create mode 100644 src/OnePeek.Entities/AppImage.cs diff --git a/src/OnePeek.Api/AppMetadataEndpoint.cs b/src/OnePeek.Api/AppMetadataEndpoint.cs index ef3bb6f..f7f3bf7 100644 --- a/src/OnePeek.Api/AppMetadataEndpoint.cs +++ b/src/OnePeek.Api/AppMetadataEndpoint.cs @@ -7,6 +7,8 @@ using System.IO; using System.Threading.Tasks; using System.Xml.Linq; using System.Linq; +using System.Globalization; +using System.Collections.Generic; namespace OnePeek.Api { @@ -23,20 +25,36 @@ namespace OnePeek.Api EndpointUris.GetWindowsPhoneMetadataUri(appId, storeCulture.ToString()) ); - try - { - //string entryXml = XDocument.Parse(xml).Descendants().FirstOrDefault(x => x.Name.LocalName == "entry").ToString(); + IEnumerable xel = XDocument.Parse(xml).Elements().First().Descendants(); - AppMetadata result = Deserialize.Xml(xml); - result.Id = appId; - return result; - } - catch (Exception exc) - { - Debug.WriteLine(exc.Message); - } + // create metadatas + AppMetadata result = Deserialize.Xml(xml); + result.Id = appId; + result.StoreType = store; + result.StoreCultureType = storeCulture; - return null; + // create publisher + result.Publisher = Deserialize.Xml(xml); + result.Publisher.Id = result.Publisher.Urn.Split(':').LastOrDefault(); + + // create rating + result.Rating = Deserialize.Xml(xml); + result.Rating.AverageRating = xel.GetFloat("averageUserRating"); + + // create images + result.Images = Deserialize.Xml(xml); + result.Images.Cleanup(); + result.Images.Screenshots = xel.Where(x => x.Name.LocalName == "screenshot").Select(x => + { + IEnumerable childs = x.Descendants(); + return new AppImage() + { + Urn = childs.Get("id"), + Rotation = childs.GetShort("orientation") + }; + }); + + return result; } diff --git a/src/OnePeek.Api/Extensions/XmlExtensions.cs b/src/OnePeek.Api/Extensions/XmlExtensions.cs new file mode 100644 index 0000000..e37f996 --- /dev/null +++ b/src/OnePeek.Api/Extensions/XmlExtensions.cs @@ -0,0 +1,29 @@ +using System; +using System.Collections.Generic; +using System.Globalization; +using System.Linq; +using System.Xml.Linq; + +namespace OnePeek.Api.Extensions +{ + internal static class XmlExtensions + { + public static string Get(this IEnumerable elements, string name) + { + XElement element = elements.FirstOrDefault(x => x.Name.LocalName == name); + return element != null ? element.Value : String.Empty; + } + + public static float GetFloat(this IEnumerable elements, string name) + { + string value = elements.Get(name); + return !String.IsNullOrEmpty(value) ? float.Parse(value, CultureInfo.InvariantCulture) : 0; + } + + public static short GetShort(this IEnumerable elements, string name) + { + string value = elements.Get(name); + return !String.IsNullOrEmpty(value) ? Int16.Parse(value) : (short)0; + } + } +} diff --git a/src/OnePeek.Api/OnePeek.Api.csproj b/src/OnePeek.Api/OnePeek.Api.csproj index 7fed014..a88fb01 100644 --- a/src/OnePeek.Api/OnePeek.Api.csproj +++ b/src/OnePeek.Api/OnePeek.Api.csproj @@ -47,6 +47,7 @@ + diff --git a/src/OnePeek.Entities/AppImage.cs b/src/OnePeek.Entities/AppImage.cs new file mode 100644 index 0000000..9cd22b8 --- /dev/null +++ b/src/OnePeek.Entities/AppImage.cs @@ -0,0 +1,16 @@ +using System; +using System.Xml.Serialization; +using System.Linq; + +namespace OnePeek.Entities +{ + public class AppImage + { + public string Id { get { return !String.IsNullOrWhiteSpace(Urn) ? Urn.Split(':').LastOrDefault() : null; } } + + [XmlElement("id")] + public string Urn { get; set; } + + public short Rotation { get; set; } + } +} diff --git a/src/OnePeek.Entities/AppMetadata.cs b/src/OnePeek.Entities/AppMetadata.cs index f2e47f3..32069fc 100644 --- a/src/OnePeek.Entities/AppMetadata.cs +++ b/src/OnePeek.Entities/AppMetadata.cs @@ -1,11 +1,19 @@ using System; +using System.Collections; +using System.Collections.Generic; using System.Xml.Serialization; namespace OnePeek.Entities { [XmlRoot("feed")] - public class AppMetadata + public partial class AppMetadata { + public string Id { get; set; } + + public StoreType StoreType { get; set; } + + public StoreCultureType StoreCultureType { get; set; } + [XmlElement("updated")] public DateTime? StoreDataModifiedDate { get; set; } @@ -15,28 +23,61 @@ namespace OnePeek.Entities [XmlElement("id")] public string Urn { get; set; } - public string Id { get; set; } - [XmlElement("releaseDate")] public DateTime ReleaseDate { get; set; } [XmlElement("content")] - public string Summary { get; set; } + public string Text { get; set; } [XmlElement("whatsNew")] - public string UpdateSummary { get; set; } + public string UpdateText { get; set; } + + [XmlElement("iapCount")] + public int IAPCount { get; set; } [XmlElement("visibilityStatus")] public AppVisibilityStatus VisibilityStatus { get; set; } + [XmlElement("privacyPolicyUrl")] + public string PrivacyPolicyUri { get; set; } + + [XmlElement("isUniversal")] + public bool IsUniversal { get; set; } + + public AppMetadataImages Images { get; set; } + public AppPublisher Publisher { get; set; } public AppRating Rating { get; set; } - - [XmlElement("isuniversal")] - public bool IsUniversal { get; set; } } + [XmlRoot("feed")] + public class AppMetadataImages + { + [XmlElement("image")] + public AppImage Logo { get; set; } + + public IEnumerable Screenshots { get; set; } + + [XmlElement("squareImage")] + public AppImage LogoSquare { get; set; } + + [XmlElement("doubleWideImage")] + public AppImage LogoWide { get; set; } + + [XmlElement("backgroundImage")] + public AppImage Background { get; set; } + + public void Cleanup() + { + if (Logo != null && String.IsNullOrEmpty(Logo.Urn)) Logo = null; + if (LogoSquare != null && String.IsNullOrEmpty(LogoSquare.Urn)) LogoSquare = null; + if (LogoWide != null && String.IsNullOrEmpty(LogoWide.Urn)) LogoWide = null; + if (Background != null && String.IsNullOrEmpty(Background.Urn)) Background = null; + } + } + + public enum AppVisibilityStatus { Unknown, diff --git a/src/OnePeek.Entities/AppPublisher.cs b/src/OnePeek.Entities/AppPublisher.cs index d36050f..d64fe30 100644 --- a/src/OnePeek.Entities/AppPublisher.cs +++ b/src/OnePeek.Entities/AppPublisher.cs @@ -1,20 +1,19 @@ -using System; -using System.Xml.Serialization; +using System.Xml.Serialization; namespace OnePeek.Entities { + [XmlRoot("feed")] public class AppPublisher { - [XmlElement("publisherid")] public string Id { get; set; } - [XmlElement("publisherguid")] - public string Uid { get; set; } + [XmlElement("publisherGuid")] + public string Urn { get; set; } [XmlElement("publisher")] public string Name { get; set; } - [XmlElement("publisherurl")] - public Uri Url { get; set; } + [XmlElement("publisherUrl")] + public string Uri { get; set; } } } diff --git a/src/OnePeek.Entities/AppRating.cs b/src/OnePeek.Entities/AppRating.cs index 71112cd..03a7be1 100644 --- a/src/OnePeek.Entities/AppRating.cs +++ b/src/OnePeek.Entities/AppRating.cs @@ -1,19 +1,13 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; -using System.Text; -using System.Threading.Tasks; -using System.Xml.Serialization; +using System.Xml.Serialization; namespace OnePeek.Entities { + [XmlRoot("feed")] public class AppRating { - [XmlElement("averageuserrating")] public float AverageRating { get; set; } - [XmlElement("userratingcount")] + [XmlElement("userRatingCount")] public int RatingCount { get; set; } } } diff --git a/src/OnePeek.Entities/AppReviews.cs b/src/OnePeek.Entities/AppReviews.cs index 38c5294..9e7a36d 100644 --- a/src/OnePeek.Entities/AppReviews.cs +++ b/src/OnePeek.Entities/AppReviews.cs @@ -8,7 +8,7 @@ using System.Xml.Serialization; namespace OnePeek.Entities { [XmlRoot("feed")] - public class AppReviews + public partial class AppReviews { public string Id { get; set; } @@ -29,7 +29,7 @@ namespace OnePeek.Entities } - public class AppReview + public partial class AppReview { public DateTime CreatedDate { get; set; } diff --git a/src/OnePeek.Entities/OnePeek.Entities.csproj b/src/OnePeek.Entities/OnePeek.Entities.csproj index 6a38802..e6a2ccc 100644 --- a/src/OnePeek.Entities/OnePeek.Entities.csproj +++ b/src/OnePeek.Entities/OnePeek.Entities.csproj @@ -37,6 +37,7 @@ + diff --git a/src/OnePeek.WebConsole/HomeModule.cs b/src/OnePeek.WebConsole/HomeModule.cs index 8bf8c19..d58a4be 100644 --- a/src/OnePeek.WebConsole/HomeModule.cs +++ b/src/OnePeek.WebConsole/HomeModule.cs @@ -1,4 +1,5 @@ using Nancy; +using OnePeek.Api; using OnePeek.Entities; using System.IO; @@ -8,8 +9,8 @@ namespace OnePeek.WebConsole { public HomeModule() { - var ratingEndpoint = new Api.AppRatingEndpoint(); - var metaEndpoint = new Api.AppMetadataEndpoint(); + AppRatingEndpoint ratingEndpoint = new AppRatingEndpoint(); + AppMetadataEndpoint metaEndpoint = new AppMetadataEndpoint(); Get["/meta/{id?2532ff45-aa3f-4aba-a266-ed7ec71d47bd}", true] = async (ctx, token) =>