/// <summary> /// Parse the <see cref="JsonElement"/> to a <see cref="IEdmReference"/>. /// </summary> /// <param name="url">The reference Url string.</param> /// <param name="element">The input JSON element.</param> /// <param name="context">The parser context.</param> /// <returns>null or parsed <see cref="IEdmReference"/>.</returns> internal static CsdlReference ParseReference(string url, JsonElement element, JsonParserContext context) { // The value of each reference object is an object. if (!element.ValidateValueKind(JsonValueKind.Object, context)) { return(null); } IList <CsdlInclude> includes = null; IList <CsdlIncludeAnnotations> includeAnnotations = null; IList <CsdlAnnotation> annotations = new List <CsdlAnnotation>(); element.ParseAsObject(context, (propertyName, propertyValue) => { // The reference object MAY contain the members $Include and $IncludeAnnotations as well as annotations. switch (propertyName) { case "$Include": // The value of $Include is an array. // Array items are objects that MUST contain the member $Namespace and MAY contain the member $Alias. includes = propertyValue.ParseAsArray(context, ParseInclude); break; case "$IncludeAnnotations": // The value of $IncludeAnnotations is an array. // Array items are objects that MUST contain the member $TermNamespace and MAY contain the members $Qualifier and $TargetNamespace. includeAnnotations = propertyValue.ParseAsArray(context, ParseIncludeAnnotations); break; default: // The reference objects MAY contain annotations. SchemaJsonParser.ParseCsdlAnnotation(propertyName, propertyValue, context, annotations); break; } }); CsdlReference reference = new CsdlReference(url, includes ?? Enumerable.Empty <CsdlInclude>(), includeAnnotations ?? Enumerable.Empty <CsdlIncludeAnnotations>(), context.Location()); annotations.ForEach(a => reference.AddAnnotation(a)); return(reference); }
/// <summary> /// Parse the <see cref="JsonElement"/> to a <see cref="IEdmInclude"/>. /// </summary> /// <param name="element">The input JSON element.</param> /// <param name="context">The parser context.</param> /// <returns>null or parsed <see cref="IEdmInclude"/>.</returns> internal static CsdlInclude ParseInclude(JsonElement element, JsonParserContext context) { // Each item in $Include is an object. if (!element.ValidateValueKind(JsonValueKind.Object, context)) { return(null); } string includeNamespace = null; string includeAlias = null; IList <CsdlAnnotation> annotations = new List <CsdlAnnotation>(); element.ParseAsObject(context, (propertyName, propertyValue) => { // Array items are objects that MUST contain the member $Namespace and MAY contain the member $Alias. switch (propertyName) { case "$Alias": // The value of $Alias is a string containing the alias for the included schema. includeAlias = propertyValue.ParseAsString(context); break; case "$Namespace": // The value of $Namespace is a string containing the namespace of the included schema includeNamespace = propertyValue.ParseAsString(context); break; default: // The item objects MAY contain annotations. SchemaJsonParser.ParseCsdlAnnotation(propertyName, propertyValue, context, annotations); break; } }); CsdlInclude include = new CsdlInclude(includeAlias, includeNamespace, context.Location()); annotations.ForEach(a => include.AddAnnotation(a)); return(include); }
/// <summary> /// Parse CSDL-JSON doc into CsdlModel, error messages are stored in <see cref="JsonParserContext"/> /// </summary> /// <param name="jsonReader">The JSON reader.</param> /// <param name="context">The parser context.</param> /// <returns>Null or parsed <see cref="CsdlModel"/>.</returns> internal static CsdlModel ParseCsdlDocument(ref Utf8JsonReader jsonReader, JsonParserContext context) { Debug.Assert(context != null); JsonDocument jsonDocument = GetJsonDocument(ref jsonReader, context); if (jsonDocument == null) { return(null); } // make sure to dispose the JsonDocument. using (jsonDocument) { JsonElement rootElement = jsonDocument.RootElement; // A CSDL JSON document consists of a single JSON object. if (!rootElement.ValidateValueKind(JsonValueKind.Object, context)) { return(null); } // This document object MUST contain the member $Version. Version version = rootElement.ProcessRequiredProperty("$Version", context, ParseVersion); if (version == null) { return(null); } CsdlModel csdlModel = new CsdlModel { CsdlVersion = version }; IList <IEdmReference> references = null; rootElement.ParseAsObject(context, (propertyName, propertyValue) => { switch (propertyName) { case "$Version": // skip, because processed break; case "$EntityContainer": // The value of $EntityContainer is the namespace-qualified name of the entity container of that service. // So far, i don't know how to use it. So skip it. break; case "$Reference": // The document object MAY contain the member $Reference to reference other CSDL documents. references = ParseReferences(propertyValue, context); break; default: // CSDL document also MAY contain members for schemas. // Each schema's value is an object. if (propertyValue.ValueKind == JsonValueKind.Object) { CsdlSchema schema = SchemaJsonParser.ParseCsdlSchema(propertyName, csdlModel.CsdlVersion, propertyValue, context); if (schema != null) { csdlModel.AddSchema(schema); break; } } context.ReportError(EdmErrorCode.UnexpectedElement, Strings.CsdlJsonParser_UnexpectedJsonMember(context.Path, propertyValue.ValueKind)); break; } }); if (references != null) { csdlModel.AddCurrentModelReferences(references); } return(csdlModel); } }