You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@olingo.apache.org by ko...@apache.org on 2014/07/15 12:31:10 UTC
[13/20] git commit: [OLINGO-324] modify json.js#jsonParser function
[OLINGO-324] modify json.js#jsonParser function
Project: http://git-wip-us.apache.org/repos/asf/olingo-odata4-js/repo
Commit: http://git-wip-us.apache.org/repos/asf/olingo-odata4-js/commit/a95a8d33
Tree: http://git-wip-us.apache.org/repos/asf/olingo-odata4-js/tree/a95a8d33
Diff: http://git-wip-us.apache.org/repos/asf/olingo-odata4-js/diff/a95a8d33
Branch: refs/heads/master
Commit: a95a8d336b6e58961447b29536cf8963f4418fd5
Parents: 67c9541
Author: Sven Kobler <sv...@sap.com>
Authored: Fri Jun 20 14:42:05 2014 +0200
Committer: Sven Kobler <sv...@sap.com>
Committed: Fri Jun 20 14:42:05 2014 +0200
----------------------------------------------------------------------
datajs/demo/tester.html | 11 ++
datajs/src/lib/datajs/utils.js | 7 +-
datajs/src/lib/odata.js | 2 +
datajs/src/lib/odata/json-light.js | 175 +++++++++++++++++++++++++-------
datajs/src/lib/odata/json.js | 63 ++++++++++--
5 files changed, 210 insertions(+), 48 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/olingo-odata4-js/blob/a95a8d33/datajs/demo/tester.html
----------------------------------------------------------------------
diff --git a/datajs/demo/tester.html b/datajs/demo/tester.html
index 201920d..e1745d0 100644
--- a/datajs/demo/tester.html
+++ b/datajs/demo/tester.html
@@ -32,6 +32,7 @@
<button id="btnJSON_none">JSON odata.metadata=none</button><br/>
<button id="btnJSON_minimal">JSON odata.metadata=minimal</button><br/>
<button id="btnJSON_full">JSON odata.metadata=full</button><br/>
+ <button id="btnJSON_all">JSON odata.metadata=full with extend to all</button><br/>
<button id="btnMetaData">MetaData</button><br/>
<button id="btnJSONwithMetaData">JSON with MetaData</button><br/>
<div id='resultsArea' data-type="json">
@@ -85,6 +86,16 @@
OData.read(requestUri, success, errorFunc);
});
+ $('#btnJSON_all').on("click", function(){
+ var requestUri = {
+ requestUri : 'http://localhost:4002/tests/endpoints/FoodStoreDataServiceV4.svc/Foods',
+ headers : { Accept : 'application/json;odata.metadata=full' },
+ extendMetadataToLevel : 'all' ,
+ recognizeDates : true
+ };
+ var context = { };
+ OData.read(requestUri, success, errorFunc);
+ });
$('#btnMetaData').on("click", function(){
var oHeaders = {
'Accept': 'text/html,application/xhtml+xml,application/xml,application/json;odata.metadata=full',
http://git-wip-us.apache.org/repos/asf/olingo-odata4-js/blob/a95a8d33/datajs/src/lib/datajs/utils.js
----------------------------------------------------------------------
diff --git a/datajs/src/lib/datajs/utils.js b/datajs/src/lib/datajs/utils.js
index 51f73be..bd4f287 100644
--- a/datajs/src/lib/datajs/utils.js
+++ b/datajs/src/lib/datajs/utils.js
@@ -1,4 +1,4 @@
-/*
+/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
@@ -519,6 +519,10 @@ var concatJsonValueArray = function (data, concatData) {
return data;
};
+var endsWith = function (input, search) {
+ return input.indexOf(search, input.length - search.length) !== -1;
+};
+
// DATAJS INTERNAL START
exports.activeXObject = activeXObject;
exports.assigned = assigned;
@@ -544,6 +548,7 @@ exports.convertByteArrayToHexString = convertByteArrayToHexString;
exports.getJsonValueArraryLength = getJsonValueArraryLength;
exports.sliceJsonValueArray = sliceJsonValueArray;
exports.concatJsonValueArray = concatJsonValueArray;
+exports.endsWith = endsWith;
// DATAJS INTERNAL END
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/olingo-odata4-js/blob/a95a8d33/datajs/src/lib/odata.js
----------------------------------------------------------------------
diff --git a/datajs/src/lib/odata.js b/datajs/src/lib/odata.js
index 47cc503..297a339 100644
--- a/datajs/src/lib/odata.js
+++ b/datajs/src/lib/odata.js
@@ -138,6 +138,7 @@ exports.request = function (request, success, error, handler, httpClient, metada
// Augment the request with additional defaults.
request.recognizeDates = utils.defined(request.recognizeDates, odataJson.jsonHandler.recognizeDates);
+ request.extendMetadataToLevel = utils.defined(request.extendMetadataToLevel, odataJson.jsonHandler.extendMetadataToLevel);
request.callbackParameterName = utils.defined(request.callbackParameterName, odataNet.defaultHttpClient.callbackParameterName);
request.formatQueryString = utils.defined(request.formatQueryString, odataNet.defaultHttpClient.formatQueryString);
request.enableJsonpCallback = utils.defined(request.enableJsonpCallback, odataNet.defaultHttpClient.enableJsonpCallback);
@@ -146,6 +147,7 @@ exports.request = function (request, success, error, handler, httpClient, metada
var context = {
metadata: metadata,
recognizeDates: request.recognizeDates,
+ extendMetadataToLevel : request.extendMetadataToLevel,
callbackParameterName: request.callbackParameterName,
formatQueryString: request.formatQueryString,
enableJsonpCallback: request.enableJsonpCallback,
http://git-wip-us.apache.org/repos/asf/olingo-odata4-js/blob/a95a8d33/datajs/src/lib/odata/json-light.js
----------------------------------------------------------------------
diff --git a/datajs/src/lib/odata/json-light.js b/datajs/src/lib/odata/json-light.js
index 9c4c079..17c2cba 100644
--- a/datajs/src/lib/odata/json-light.js
+++ b/datajs/src/lib/odata/json-light.js
@@ -69,12 +69,28 @@ var parseDuration = oDataUtils.parseDuration;
// CONTENT START
-var PAYLOADTYPE_OBJECT = "o";
var PAYLOADTYPE_FEED = "f";
-var PAYLOADTYPE_PRIMITIVE = "p";
+var PAYLOADTYPE_ENTRY = "e";
+var PAYLOADTYPE_PROPERTY = "p";
+var PAYLOADTYPE_ENTITY_REF_LINK = "erl";
+var PAYLOADTYPE_ENTITY_REF_LINKS = "erls";
+var PAYLOADTYPE_VALUE = "v";
+var PAYLOADTYPE_BINARY_VALUE = "bv";
var PAYLOADTYPE_COLLECTION = "c";
var PAYLOADTYPE_SVCDOC = "s";
-var PAYLOADTYPE_LINKS = "l";
+var PAYLOADTYPE_METADOC = "m";
+var PAYLOADTYPE_ERROR = "err";
+var PAYLOADTYPE_BATCH = "b";
+var PAYLOADTYPE_PARAMETER = "para";
+var PAYLOADTYPE_IND_PROPERTY = "ip";
+var PAYLOADTYPE_DELTA = "d";
+var PAYLOADTYPE_ASYNC = "a";
+
+
+var DELTATYPE_FEED = "f";
+var DELTATYPE_DELETED_ENTRY = "de";
+var DELTATYPE_LINK = "l";
+var DELTATYPE_DELETED_LINK = "dl";
var odataNs = "odata";
var odataAnnotationPrefix = odataNs + ".";
@@ -1036,57 +1052,93 @@ var jsonLightMakePayloadInfo = function (kind, type) {
return { kind: kind, type: type || null };
};
-var jsonLightPayloadInfo = function (data, model, inferFeedAsComplexType) {
- /// <summary>Infers the information describing the JSON light payload from its metadata annotation, structure, and data model.</summary>
- /// <param name="data" type="Object">Json light response payload object.</param>
- /// <param name="model" type="Object">Object describing an OData conceptual schema.</param>
- /// <param name="inferFeedAsComplexType" type="Boolean">True if a JSON light payload that looks like a feed should be treated as a complex type property instead.</param>
- /// <remarks>
- /// If the arguments passed to the function don't convey enough information about the payload to determine without doubt that the payload is a feed then it
- /// will try to use the payload object structure instead. If the payload looks like a feed (has value property that is an array or non-primitive values) then
- /// the function will report its kind as PAYLOADTYPE_FEED unless the inferFeedAsComplexType flag is set to true. This flag comes from the user request
- /// and allows the user to control how the library behaves with an ambigous JSON light payload.
- /// </remarks>
- /// <returns type="Object">
- /// Object with kind and type fields. Null if there is no metadata annotation or the payload info cannot be obtained..
- /// </returns>
+/**/
+var parseContextUriFragment = function( fragment ) {
+ var ret = {};
+
+ ret.deltaKind = undefined;
+ if (utils.endsWith(fragment, '/$entity')) {
+ fragment = fragment.substring(fragment.lenght - 8);
+ } else if (utils.endsWith(fragment, '/$delta')) {
+ ret.deltaKind = DELTATYPE_FEED;
+ fragment = fragment.substring(fragment.lenght - 7);
+ } else if (utils.endsWith(fragment, '/$deletedEntity')) {
+ ret.deltaKind = DELTATYPE_DELETED_ENTRY;
+ fragment = fragment.substring(fragment.lenght - 15);
+ } else if (utils.endsWith(fragment, '/$link')) {
+ ret.deltaKind = DELTATYPE_LINK;
+ fragment = fragment.substring(fragment.lenght - 6);
+ } else if (utils.endsWith(fragment, '/$deletedLink')) {
+ ret.deltaKind = DELTATYPE_DELETED_LINK;
+ fragment = fragment.substring(fragment.lenght - 13);
+ }
+
+ if (utils.endsWith(fragment,")")) {
+ //remove the query function, cut fragment to matching '('
+ var index = fragment.lenght - 2 ;
+ for ( var rCount = 1; rcount > 0 && index > 0; --index) {
+ if ( fragment.charAt(index)=='(') {
+ rCount ++;
+ } else if ( fragment.charAt(index)==')') {
+ rCount --;
+ }
+ }
- var metadataUri = data[contextUrlAnnotation];
- if (!metadataUri || typeof metadataUri !== "string") {
- return null;
- }
+ if (index == 0) {
+ //TODO throw error
+ }
- var fragmentStart = metadataUri.lastIndexOf("#");
- if (fragmentStart === -1) {
- return jsonLightMakePayloadInfo(PAYLOADTYPE_SVCDOC);
- }
+ var previous = fragment.substring(0, index + 1);
- var elementStart = metadataUri.indexOf("@Element", fragmentStart);
- var fragmentEnd = elementStart - 1;
- if (fragmentEnd < 0) {
- fragmentEnd = metadataUri.indexOf("?", fragmentStart);
- if (fragmentEnd === -1) {
- fragmentEnd = metadataUri.length;
+ if (previous !== 'Collection') { // Don't treat Collection(Edm.Type) as SelectExpand segment
+ var selectExpandStr = fragment.substring(index+2, fragment.lenght - 1);
+ var keyPattern = /^(?:-{0,1}\d+?|\w*'.+?'|[A-F0-9]{8}(?:-[A-F0-9]{4}){3}-[A-F0-9]{12}|.+?=.+?)$/;
+ var matches = keyPattern.exec(selectExpandStr);
+ if ( matches ) {
+ //TODO throw error
+ }
+
+ ret.selectQueryOptionString = selectExpandStr;
+ fragment = previous;
}
- }
- var fragment = metadataUri.substring(fragmentStart + 1, fragmentEnd);
- if (fragment.indexOf("/$links/") > 0) {
- return jsonLightMakePayloadInfo(PAYLOADTYPE_LINKS);
}
+ ret.detectedPayloadKind = undefined;
+ if (fragment.indexOf('/') === -1 ) {
+ if (fragment.length === 0) {
+ // Capter 10.1
+ ret.detectedPayloadKind = PAYLOADTYPE_SVCDOC;
+ } else if (fragment === 'Edm.Null') {
+ // Capter 10.15
+ ret.detectedPayloadKind = PAYLOADTYPE_PROPERTY;
+ ret.isNullProperty = true;
+ } else if (fragment === 'Collection($ref)') {
+ // Capter 10.11
+ ret.detectedPayloadKind = PAYLOADTYPE_ENTITY_REF_LINKS;
+ } else if (fragment === '$ref') {
+ // Capter 10.12
+ ret.detectedPayloadKind = PAYLOADTYPE_ENTITY_REF_LINK;
+ } else {
+ //TODO check for navigation resource
+ }
+ }
+
+ // split fragment at '/'
+ //TODO changes
var fragmentParts = fragment.split("/");
if (fragmentParts.length >= 0) {
var qualifiedName = fragmentParts[0];
var typeCast = fragmentParts[1];
if (jsonLightIsPrimitiveType(qualifiedName)) {
- return jsonLightMakePayloadInfo(PAYLOADTYPE_PRIMITIVE, qualifiedName);
+ ret.detectedPayloadKind = PAYLOADTYPE_VALUE;
+ return ret;
}
if (isCollectionType(qualifiedName)) {
- return jsonLightMakePayloadInfo(PAYLOADTYPE_COLLECTION, qualifiedName);
+ return ret;
}
var entityType = typeCast;
@@ -1107,7 +1159,7 @@ var jsonLightPayloadInfo = function (data, model, inferFeedAsComplexType) {
}
var info;
- if (elementStart > 0) {
+ if (d > 0) {
info = jsonLightMakePayloadInfo(PAYLOADTYPE_OBJECT, entityType);
info.entitySet = entitySet;
info.functionImport = functionImport;
@@ -1135,7 +1187,52 @@ var jsonLightPayloadInfo = function (data, model, inferFeedAsComplexType) {
return jsonLightMakePayloadInfo(PAYLOADTYPE_OBJECT, qualifiedName);
}
- return null;
+};
+
+var jsonLightPayloadInfo = function (data, model) {
+ /// <summary>Infers the information describing the JSON light payload from its metadata annotation, structure, and data model.</summary>
+ /// <param name="data" type="Object">Json light response payload object.</param>
+ /// <param name="model" type="Object">Object describing an OData conceptual schema.</param>
+ /// <remarks>
+ /// If the arguments passed to the function don't convey enough information about the payload to determine without doubt that the payload is a feed then it
+ /// will try to use the payload object structure instead. If the payload looks like a feed (has value property that is an array or non-primitive values) then
+ /// the function will report its kind as PAYLOADTYPE_FEED unless the inferFeedAsComplexType flag is set to true. This flag comes from the user request
+ /// and allows the user to control how the library behaves with an ambigous JSON light payload.
+ /// </remarks>
+ /// <returns type="Object">
+ /// Object with kind and type fields. Null if there is no metadata annotation or the payload info cannot be obtained..
+ /// </returns>
+
+ var metadataUri = data[contextUrlAnnotation];
+ if (!metadataUri || typeof metadataUri !== "string") {
+ return null;
+ }
+
+ var fragmentStart = metadataUri.lastIndexOf("#");
+ if (fragmentStart === -1) {
+ return jsonLightMakePayloadInfo(PAYLOADTYPE_SVCDOC);
+ }
+
+ var d = metadataUri.indexOf("@Element", fragmentStart);
+ var fragmentEnd = elementStart - 1;
+
+ if (fragmentEnd < 0) {
+ fragmentEnd = metadataUri.indexOf("?", fragmentStart);
+ if (fragmentEnd === -1) {
+ fragmentEnd = metadataUri.length;
+ }
+ }
+
+ var fragment = metadataUri.substring(fragmentStart + 1, fragmentEnd);
+ if (fragment.indexOf("/$links/") > 0) {
+ return jsonLightMakePayloadInfo(PAYLOADTYPE_LINKS);
+ }
+
+ var ret = parseContextUriFragment(fragment);
+
+ return;
+
+
};
var jsonLightReadPayload = function (data, model, recognizeDates, inferFeedAsComplexType, contentTypeOdata) {
http://git-wip-us.apache.org/repos/asf/olingo-odata4-js/blob/a95a8d33/datajs/src/lib/odata/json.js
----------------------------------------------------------------------
diff --git a/datajs/src/lib/odata/json.js b/datajs/src/lib/odata/json.js
index 28e71fd..c33104d 100644
--- a/datajs/src/lib/odata/json.js
+++ b/datajs/src/lib/odata/json.js
@@ -257,6 +257,7 @@ var jsonParser = function (handler, text, context) {
} catch(err) {
payloadFormat = 1;
}
+ payloadFormat = (payloadFormat === undefined) ? 1 : payloadFormat;
var demandedFormat = 1;//minmal
try {
@@ -264,6 +265,9 @@ var jsonParser = function (handler, text, context) {
} catch(err) {
demandedFormat = 1;
}
+ demandedFormat = (demandedFormat === undefined) ? 1 : demandedFormat;
+
+ //return jsonLightReadPayload(json, model, recognizeDates, inferJsonLightFeedAsObject, context.contentType.properties['odata.metadata']);
if ( payloadFormat >= demandedFormat) {
if (recognizeDates) {
@@ -273,7 +277,8 @@ var jsonParser = function (handler, text, context) {
}
} else {
if (payloadFormat === 2) { //full, no metadata in context required
- //insert the missing type information for strings
+ //insert the missing type information for strings, bool, etc.
+ //guess type for nummber as defined in the odata-json-format-v4.0.doc specification
return extendMetadataFromPayload(json,context,recognizeDates);
} else if (payloadFormat === 1) { //minmal
if (utils.isArray(context.metadata)) {
@@ -288,18 +293,60 @@ var jsonParser = function (handler, text, context) {
}
}
- //return jsonLightReadPayload(json, model, recognizeDates, inferJsonLightFeedAsObject, context.contentType.properties['odata.metadata']);
+
};
var convertPrimitivetypesGeneric = function(json,context) {
- return json;
-}
-var extendMetadataFromPayload = function(json,context,recognizeDates) {
- return json;
-}
+
+};
+
+
+var addType = function(data, name, value ) {
+ var fullName = name+'@odata.type';
+
+ if ( data[fullName] === undefined) {
+ data[fullName] = value;
+ }
+};
+
+var extendMetadataFromPayload = function(data,context,recognizeDates) {
+ if ( utils.isObject(data) ) {
+
+ for (var key in data) {
+ if (data.hasOwnProperty(key)) {
+ if (key.indexOf('@') === -1) {
+ if (utils.isArray(data[key])) {
+ for ( var i = 0; i < data[key].length; ++i) {
+ extendMetadataFromPayload(data[key][i], context, recognizeDates);
+ }
+ } else if (utils.isObject(data[key])) {
+ if (data[key] !== null) {
+ extendMetadataFromPayload(data[key],context, recognizeDates);
+ }
+ } else {
+ var type = typeof data[key];
+ if ( type === 'string' ) {
+ addType(data,key,'#String');
+ } else if (type ==='boolean') {
+ addType(data,key,'#Bool');
+ } else if (type ==='number') {
+ if ( data[key] % 1 === 0 ) {
+ addType(data,key,'#Integer');
+ } else {
+ addType(data,key,'#Decimal');
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+ return data;
+};
+
var extendMetadataFromContext = function(json,context,recognizeDates) {
return json;
-}
+};
var jsonToString = function (data) {