@sap/cds-compiler 2.12.0 → 2.15.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +221 -15
- package/bin/cdsc.js +125 -50
- package/bin/cdsse.js +2 -2
- package/doc/CHANGELOG_BETA.md +13 -6
- package/doc/CHANGELOG_DEPRECATED.md +22 -6
- package/doc/NameResolution.md +21 -16
- package/lib/api/main.js +47 -84
- package/lib/api/options.js +5 -6
- package/lib/api/validate.js +6 -11
- package/lib/backends.js +15 -23
- package/lib/base/dictionaries.js +0 -8
- package/lib/base/error.js +26 -0
- package/lib/base/keywords.js +7 -17
- package/lib/base/location.js +9 -4
- package/lib/base/message-registry.js +114 -18
- package/lib/base/messages.js +101 -90
- package/lib/base/model.js +2 -63
- package/lib/base/optionProcessorHelper.js +177 -123
- package/lib/checks/annotationsOData.js +12 -33
- package/lib/checks/arrayOfs.js +1 -34
- package/lib/checks/cdsPersistence.js +2 -1
- package/lib/checks/enricher.js +17 -1
- package/lib/checks/invalidTarget.js +3 -1
- package/lib/checks/managedWithoutKeys.js +3 -1
- package/lib/checks/selectItems.js +4 -4
- package/lib/checks/sql-snippets.js +27 -26
- package/lib/checks/types.js +1 -1
- package/lib/checks/validator.js +6 -11
- package/lib/compiler/assert-consistency.js +6 -3
- package/lib/compiler/base.js +1 -0
- package/lib/compiler/builtins.js +19 -6
- package/lib/compiler/checks.js +23 -60
- package/lib/compiler/cycle-detector.js +1 -1
- package/lib/compiler/define.js +1151 -0
- package/lib/compiler/extend.js +1000 -0
- package/lib/compiler/finalize-parse-cdl.js +237 -0
- package/lib/compiler/index.js +107 -39
- package/lib/compiler/kick-start.js +190 -0
- package/lib/compiler/moduleLayers.js +4 -4
- package/lib/compiler/populate.js +1227 -0
- package/lib/compiler/propagator.js +114 -46
- package/lib/compiler/resolve.js +1521 -0
- package/lib/compiler/shared.js +126 -65
- package/lib/compiler/tweak-assocs.js +535 -0
- package/lib/compiler/utils.js +197 -33
- package/lib/edm/.eslintrc.json +5 -0
- package/lib/edm/annotations/genericTranslation.js +38 -24
- package/lib/edm/annotations/preprocessAnnotations.js +2 -2
- package/lib/edm/csn2edm.js +219 -100
- package/lib/edm/edm.js +302 -230
- package/lib/edm/edmPreprocessor.js +554 -419
- package/lib/edm/edmUtils.js +138 -44
- package/lib/gen/Dictionary.json +100 -19
- package/lib/gen/language.checksum +1 -1
- package/lib/gen/language.interp +11 -1
- package/lib/gen/language.tokens +86 -83
- package/lib/gen/languageLexer.interp +10 -1
- package/lib/gen/languageLexer.js +860 -833
- package/lib/gen/languageLexer.tokens +78 -75
- package/lib/gen/languageParser.js +5765 -4480
- package/lib/json/csnVersion.js +10 -11
- package/lib/json/from-csn.js +15 -3
- package/lib/json/to-csn.js +126 -68
- package/lib/language/docCommentParser.js +4 -4
- package/lib/language/genericAntlrParser.js +123 -5
- package/lib/language/language.g4 +355 -156
- package/lib/language/multiLineStringParser.js +5 -5
- package/lib/main.d.ts +486 -59
- package/lib/main.js +41 -9
- package/lib/model/api.js +3 -1
- package/lib/model/csnRefs.js +252 -156
- package/lib/model/csnUtils.js +384 -297
- package/lib/model/enrichCsn.js +71 -29
- package/lib/model/revealInternalProperties.js +29 -8
- package/lib/model/sortViews.js +2 -1
- package/lib/modelCompare/compare.js +23 -18
- package/lib/optionProcessor.js +63 -26
- package/lib/render/manageConstraints.js +35 -32
- package/lib/render/toCdl.js +897 -947
- package/lib/render/toHdbcds.js +205 -257
- package/lib/render/toSql.js +264 -225
- package/lib/render/utils/common.js +136 -25
- package/lib/render/utils/sql.js +4 -3
- package/lib/render/utils/stringEscapes.js +111 -0
- package/lib/sql-identifier.js +1 -1
- package/lib/transform/.eslintrc.json +5 -0
- package/lib/transform/db/.eslintrc.json +3 -1
- package/lib/transform/db/applyTransformations.js +35 -12
- package/lib/transform/db/assertUnique.js +1 -1
- package/lib/transform/db/associations.js +104 -306
- package/lib/transform/db/cdsPersistence.js +2 -2
- package/lib/transform/db/constraints.js +58 -53
- package/lib/transform/db/expansion.js +60 -33
- package/lib/transform/db/flattening.js +582 -104
- package/lib/transform/db/groupByOrderBy.js +3 -1
- package/lib/transform/db/transformExists.js +66 -13
- package/lib/transform/db/views.js +11 -7
- package/lib/transform/draft/.eslintrc.json +38 -0
- package/lib/transform/{db/draft.js → draft/db.js} +6 -5
- package/lib/transform/draft/odata.js +227 -0
- package/lib/transform/forHanaNew.js +109 -208
- package/lib/transform/forOdataNew.js +59 -212
- package/lib/transform/localized.js +46 -26
- package/lib/transform/odata/toFinalBaseType.js +85 -11
- package/lib/transform/odata/typesExposure.js +147 -199
- package/lib/transform/odata/utils.js +2 -2
- package/lib/transform/transformUtilsNew.js +44 -33
- package/lib/transform/translateAssocsToJoins.js +3 -20
- package/lib/transform/universalCsn/.eslintrc.json +36 -0
- package/lib/transform/universalCsn/coreComputed.js +172 -0
- package/lib/transform/universalCsn/universalCsnEnricher.js +737 -0
- package/lib/transform/universalCsn/utils.js +63 -0
- package/lib/utils/moduleResolve.js +13 -6
- package/lib/utils/objectUtils.js +30 -0
- package/package.json +1 -1
- package/share/messages/README.md +26 -0
- package/share/messages/message-explanations.json +2 -1
- package/share/messages/syntax-expected-integer.md +37 -0
- package/lib/compiler/definer.js +0 -2361
- package/lib/compiler/resolver.js +0 -3079
- package/lib/transform/odata/attachPath.js +0 -96
- package/lib/transform/odata/expandStructKeysInAssociations.js +0 -59
- package/lib/transform/odata/generateForeignKeyElements.js +0 -261
- package/lib/transform/odata/referenceFlattener.js +0 -290
- package/lib/transform/odata/sortByAssociationDependency.js +0 -105
- package/lib/transform/odata/structuralPath.js +0 -72
- package/lib/transform/odata/structureFlattener.js +0 -171
- package/lib/transform/universalCsnEnricher.js +0 -237
package/lib/edm/edmUtils.js
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
const { setProp } = require('../base/model');
|
|
3
3
|
const { isBuiltinType, isEdmPropertyRendered } = require('../model/csnUtils');
|
|
4
|
+
const { escapeString, hasControlCharacters, hasUnpairedUnicodeSurrogate } = require("../render/utils/stringEscapes");
|
|
4
5
|
|
|
5
6
|
/* eslint max-statements-per-line:off */
|
|
6
7
|
function validateOptions(_options)
|
|
@@ -22,7 +23,7 @@ function validateOptions(_options)
|
|
|
22
23
|
options.odataForeignKeys = options.toOdata.odataForeignKeys;
|
|
23
24
|
if(options.toOdata.odataV2PartialConstr)
|
|
24
25
|
options.odataV2PartialConstr = options.toOdata.odataV2PartialConstr;
|
|
25
|
-
// global flag that indicates
|
|
26
|
+
// global flag that indicates whether or not FKs shall be rendered in general
|
|
26
27
|
// V2/V4 flat: yes
|
|
27
28
|
// V4/struct: depending on odataForeignKeys
|
|
28
29
|
options.renderForeignKeys =
|
|
@@ -123,7 +124,7 @@ function isSingleton(entityCsn) {
|
|
|
123
124
|
|
|
124
125
|
function isEntity(artifact)
|
|
125
126
|
{
|
|
126
|
-
return
|
|
127
|
+
return artifact.kind === 'entity';
|
|
127
128
|
}
|
|
128
129
|
|
|
129
130
|
function isParameterizedEntity(artifact) {
|
|
@@ -138,15 +139,15 @@ function isStructuredArtifact(artifact) {
|
|
|
138
139
|
|
|
139
140
|
// Return true if 'artifact' is a real structured type (not an entity)
|
|
140
141
|
function isStructuredType(artifact) {
|
|
141
|
-
return
|
|
142
|
+
return artifact.kind === 'type' && isStructuredArtifact(artifact);
|
|
142
143
|
}
|
|
143
144
|
|
|
144
145
|
function isDerivedType(artifact) {
|
|
145
|
-
return
|
|
146
|
+
return artifact.kind === 'type' && !isStructuredArtifact(artifact);
|
|
146
147
|
}
|
|
147
148
|
|
|
148
149
|
function isActionOrFunction(artifact) {
|
|
149
|
-
return
|
|
150
|
+
return artifact.kind === 'action' || artifact.kind === 'function';
|
|
150
151
|
}
|
|
151
152
|
|
|
152
153
|
function resolveOnConditionAndPrepareConstraints(csn, assocCsn, messageFunctions) {
|
|
@@ -179,7 +180,7 @@ function resolveOnConditionAndPrepareConstraints(csn, assocCsn, messageFunctions
|
|
|
179
180
|
const originAssocCsn = resolveOriginAssoc(csn, (assocCsn._originalTarget || assocCsn._target), partnerPath);
|
|
180
181
|
const parentName = assocCsn.$abspath[0];
|
|
181
182
|
const parent = csn.definitions[parentName];
|
|
182
|
-
if(originAssocCsn) {
|
|
183
|
+
if(originAssocCsn && originAssocCsn.$abspath) {
|
|
183
184
|
const originParentName = originAssocCsn.$abspath[0];
|
|
184
185
|
if(parent.$mySchemaName && originAssocCsn._originalTarget !== parent && originAssocCsn._target !== parent) {
|
|
185
186
|
isBacklink = false;
|
|
@@ -253,7 +254,7 @@ function resolveOnConditionAndPrepareConstraints(csn, assocCsn, messageFunctions
|
|
|
253
254
|
{
|
|
254
255
|
let lhs = expr[pos-1];
|
|
255
256
|
let rhs = expr[pos+1];
|
|
256
|
-
if(
|
|
257
|
+
if(arg === '=')
|
|
257
258
|
{
|
|
258
259
|
assocCsn._constraints.termCount++;
|
|
259
260
|
if(lhs.ref && rhs.ref) // ref is a path
|
|
@@ -400,7 +401,7 @@ function finalizeReferentialConstraints(csn, assocCsn, options, info)
|
|
|
400
401
|
if(options.isV2() && intersect(renderedKeys, remainingPrincipalRefs).length !== renderedKeys.length)
|
|
401
402
|
if(options.odataV2PartialConstr) {
|
|
402
403
|
info('odata-spec-violation-constraints',
|
|
403
|
-
['definitions', assocCsn._parent.name, 'elements', assocCsn.name], {
|
|
404
|
+
['definitions', assocCsn._parent.name, 'elements', assocCsn.name], { version: '2.0' });
|
|
404
405
|
}
|
|
405
406
|
else {
|
|
406
407
|
assocCsn._constraints.constraints = {};
|
|
@@ -438,7 +439,7 @@ function finalizeReferentialConstraints(csn, assocCsn, options, info)
|
|
|
438
439
|
if(options.isV2() && intersect(renderedKeys, remainingPrincipalRefs).length !== renderedKeys.length) {
|
|
439
440
|
if(options.odataV2PartialConstr) {
|
|
440
441
|
info('odata-spec-violation-constraints',
|
|
441
|
-
['definitions', assocCsn._parent.name, 'elements', assocCsn.name], {
|
|
442
|
+
['definitions', assocCsn._parent.name, 'elements', assocCsn.name], { version: '2.0' } );
|
|
442
443
|
}
|
|
443
444
|
else {
|
|
444
445
|
assocCsn._constraints.constraints = {};
|
|
@@ -466,7 +467,7 @@ function finalizeReferentialConstraints(csn, assocCsn, options, info)
|
|
|
466
467
|
return (elt &&
|
|
467
468
|
elt.type &&
|
|
468
469
|
(!options.isFlatFormat || options.isFlatFormat && isBuiltinType(elt.type)) &&
|
|
469
|
-
!
|
|
470
|
+
!(elt.type === 'cds.Association' || elt.type === 'cds.Composition') &&
|
|
470
471
|
isEdmPropertyRendered(elt, options));
|
|
471
472
|
}
|
|
472
473
|
}
|
|
@@ -521,12 +522,14 @@ function determineMultiplicity(csn)
|
|
|
521
522
|
return [srcCardinality, tgtCardinality];
|
|
522
523
|
}
|
|
523
524
|
|
|
524
|
-
function mapCdsToEdmType(csn, messageFunctions, isV2=false, isMediaType=false)
|
|
525
|
+
function mapCdsToEdmType(csn, messageFunctions, isV2=false, isMediaType=false, location=undefined)
|
|
525
526
|
{
|
|
527
|
+
if(location === undefined)
|
|
528
|
+
location = csn.$path;
|
|
526
529
|
const { error } = messageFunctions || { error: ()=>true };
|
|
527
530
|
let cdsType = csn.type;
|
|
528
531
|
if(cdsType === undefined) {
|
|
529
|
-
error(null,
|
|
532
|
+
error(null, location, `no type found`);
|
|
530
533
|
return '<NOTYPE>';
|
|
531
534
|
}
|
|
532
535
|
if(!isBuiltinType(cdsType))
|
|
@@ -556,7 +559,7 @@ function mapCdsToEdmType(csn, messageFunctions, isV2=false, isMediaType=false)
|
|
|
556
559
|
// other: date/time, boolean
|
|
557
560
|
'cds.Date': 'Edm.Date',
|
|
558
561
|
'cds.Time': 'Edm.TimeOfDay',
|
|
559
|
-
// For a very long time it was unclear
|
|
562
|
+
// For a very long time it was unclear whether or not to map the Date types to a different Edm Type in V2,
|
|
560
563
|
// no one has ever asked about it in the meantime. The falsy if is just there to remember the eventual mapping.
|
|
561
564
|
'cds.DateTime': 'Edm.DateTimeOffset', // (isV2 && false) ? 'Edm.DateTime'
|
|
562
565
|
'cds.Timestamp': 'Edm.DateTimeOffset', // (isV2 && false) ? 'Edm.DateTime'
|
|
@@ -581,7 +584,7 @@ function mapCdsToEdmType(csn, messageFunctions, isV2=false, isMediaType=false)
|
|
|
581
584
|
*/
|
|
582
585
|
}[cdsType];
|
|
583
586
|
if (edmType == undefined) {
|
|
584
|
-
error(null,
|
|
587
|
+
error(null, location, { type: cdsType }, `No EDM type available for $(TYPE)`);
|
|
585
588
|
}
|
|
586
589
|
if(isV2)
|
|
587
590
|
{
|
|
@@ -589,9 +592,6 @@ function mapCdsToEdmType(csn, messageFunctions, isV2=false, isMediaType=false)
|
|
|
589
592
|
edmType = 'Edm.DateTime';
|
|
590
593
|
if (edmType === 'Edm.TimeOfDay')
|
|
591
594
|
edmType = 'Edm.Time';
|
|
592
|
-
if(['cds.hana.ST_POINT', 'cds.hana.ST_GEOMETRY'].includes(cdsType)) {
|
|
593
|
-
error(null, csn.$path, { type: cdsType }, `OData V2 does not support Geometry data types, $(TYPE) can't be mapped`);
|
|
594
|
-
}
|
|
595
595
|
}
|
|
596
596
|
else // isV4
|
|
597
597
|
{
|
|
@@ -605,31 +605,32 @@ function mapCdsToEdmType(csn, messageFunctions, isV2=false, isMediaType=false)
|
|
|
605
605
|
function addTypeFacets(node, csn)
|
|
606
606
|
{
|
|
607
607
|
const isV2 = node.v2;
|
|
608
|
+
const decimalTypes = {'cds.Decimal':1, 'cds.DecimalFloat':1, 'cds.hana.SMALLDECIMAL':1};
|
|
608
609
|
if (csn.length != null)
|
|
609
|
-
node.MaxLength
|
|
610
|
+
node.setEdmAttribute('MaxLength', csn.length);
|
|
610
611
|
if (csn.scale !== undefined)
|
|
611
|
-
node.Scale
|
|
612
|
+
node.setEdmAttribute('Scale', csn.scale);
|
|
612
613
|
// else if (csn.type === 'cds.hana.SMALLDECIMAL' && !isV2)
|
|
613
|
-
// node.Scale = 'floating';
|
|
614
|
+
// node._edmAttributes.Scale = 'floating';
|
|
614
615
|
|
|
615
616
|
if (csn.precision != null)
|
|
616
|
-
node.Precision
|
|
617
|
+
node.setEdmAttribute('Precision', csn.precision);
|
|
617
618
|
// else if (csn.type === 'cds.hana.SMALLDECIMAL' && !isV2)
|
|
618
619
|
// node.Precision = 16;
|
|
619
|
-
else if (csn.type === 'cds.Timestamp' && node.Type === 'Edm.DateTimeOffset')
|
|
620
|
-
node.Precision
|
|
621
|
-
if(
|
|
620
|
+
else if (csn.type === 'cds.Timestamp' && node._edmAttributes.Type === 'Edm.DateTimeOffset')
|
|
621
|
+
node.setEdmAttribute('Precision', 7);
|
|
622
|
+
if(csn.type in decimalTypes) {
|
|
622
623
|
if(isV2) {
|
|
623
624
|
// no prec/scale or scale is 'floating'/'variable'
|
|
624
|
-
if(!(csn.precision || csn.scale) ||
|
|
625
|
+
if(!(csn.precision || csn.scale) || (csn.scale === 'floating' || csn.scale === 'variable')) {
|
|
625
626
|
node.setXml( { 'sap:variable-scale': true } );
|
|
626
|
-
|
|
627
|
+
node.removeEdmAttribute('Scale');
|
|
627
628
|
}
|
|
628
629
|
}
|
|
629
630
|
else {
|
|
630
631
|
// map both floating and variable to => variable
|
|
631
|
-
if(node.Scale === 'floating')
|
|
632
|
-
node.Scale
|
|
632
|
+
if(node._edmAttributes.Scale === 'floating')
|
|
633
|
+
node.setEdmAttribute('Scale', 'variable');
|
|
633
634
|
if(!csn.precision && !csn.scale)
|
|
634
635
|
// if Decimal has no p, s set scale 'variable'
|
|
635
636
|
node.setXml( { Scale: 'variable' } ); // floating is V4.01
|
|
@@ -637,9 +638,9 @@ function addTypeFacets(node, csn)
|
|
|
637
638
|
}
|
|
638
639
|
// Unicode unused today
|
|
639
640
|
if(csn.unicode)
|
|
640
|
-
node.Unicode
|
|
641
|
+
node.setEdmAttribute('Unicode', csn.unicode);
|
|
641
642
|
if(csn.srid)
|
|
642
|
-
node.SRID
|
|
643
|
+
node.setEdmAttribute('SRID', csn.srid);
|
|
643
644
|
}
|
|
644
645
|
|
|
645
646
|
|
|
@@ -664,19 +665,111 @@ function isODataSimpleIdentifier(identifier){
|
|
|
664
665
|
return identifier && identifier.match(regex);
|
|
665
666
|
}
|
|
666
667
|
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
|
|
671
|
-
|
|
672
|
-
|
|
673
|
-
|
|
674
|
-
|
|
675
|
-
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
|
|
668
|
+
/**
|
|
669
|
+
* Escape the given string for attribute values. We follow the spec as
|
|
670
|
+
* described in §2.3 <https://www.w3.org/TR/xml/#NT-AttValue>:
|
|
671
|
+
*
|
|
672
|
+
* AttValue ::= '"' ([^<&"] | Reference)* '"'
|
|
673
|
+
* | "'" ([^<&'] | Reference)* "'"
|
|
674
|
+
*
|
|
675
|
+
* This function assumes that the attribute value is surrounded by double quotes ("),
|
|
676
|
+
* hence single quotes are not escaped.
|
|
677
|
+
*
|
|
678
|
+
* Note that even though certain special characters such as newline (LF) are allowed,
|
|
679
|
+
* they may be normalized to something different. For example LF is normalized
|
|
680
|
+
* to a space. Therefore we need to escape it.
|
|
681
|
+
* See §3.3.3 <https://www.w3.org/TR/xml/#AVNormalize>.
|
|
682
|
+
*
|
|
683
|
+
* Furthermore, control characters need to be escaped, see §2.2:
|
|
684
|
+
* <https://www.w3.org/TR/xml/#charsets>
|
|
685
|
+
* We also encode LF (#xA), etc. because of XML normalization in XML parsers.
|
|
686
|
+
*
|
|
687
|
+
* @param {string} str
|
|
688
|
+
* @returns {string}
|
|
689
|
+
*/
|
|
690
|
+
function escapeStringForAttributeValue(str) {
|
|
691
|
+
if (typeof str !== 'string')
|
|
692
|
+
return str;
|
|
693
|
+
|
|
694
|
+
if (!/[&<"]/.test(str) && !hasControlCharacters(str) && !hasUnpairedUnicodeSurrogate(str))
|
|
695
|
+
return str;
|
|
696
|
+
|
|
697
|
+
str = escapeString(str, {
|
|
698
|
+
'&': '&',
|
|
699
|
+
'<': '<',
|
|
700
|
+
'"': '"',
|
|
701
|
+
control: encodeNonCharacters,
|
|
702
|
+
unpairedSurrogate: encodeNonCharacters,
|
|
703
|
+
});
|
|
704
|
+
|
|
705
|
+
// Notes
|
|
706
|
+
// -----
|
|
707
|
+
// According to the specification, "§2.11: End-of-Line Handling", we should normalize line endings:
|
|
708
|
+
// > ... by translating both the two-character sequence #xD #xA and any #xD that is not
|
|
709
|
+
// > followed by #xA to a single #xA character.
|
|
710
|
+
// However, line endings were already normalized in the CDL parser.
|
|
711
|
+
// If we were to normalize it again, it would be work done twice, possibly resulting in
|
|
712
|
+
// unwanted normalization (once is expected, twice is not).
|
|
713
|
+
// If we were to ever change this, use this RegEx:
|
|
714
|
+
// /\r\n?|\n/g => '
'
|
|
715
|
+
|
|
716
|
+
return str;
|
|
717
|
+
}
|
|
718
|
+
|
|
719
|
+
/**
|
|
720
|
+
* Escape the given string for element content. We follow the spec as
|
|
721
|
+
* described in §3.1 <https://www.w3.org/TR/xml/#NT-content>:
|
|
722
|
+
*
|
|
723
|
+
* content ::= CharData? ((element | Reference | CDSect | PI | Comment) CharData?)*
|
|
724
|
+
* CharData ::= [^<&]* - ([^<&]* ']]>' [^<&]*)
|
|
725
|
+
*
|
|
726
|
+
* i.e., we need to escape '<', '&' as well as `>` if it is preceded by `]]`.
|
|
727
|
+
* See also $2.4: “'>' MUST be replaced for compatibility reasons if it appears as ]]>”
|
|
728
|
+
*
|
|
729
|
+
* Furthermore, control characters need to be escaped, see §2.2:
|
|
730
|
+
* <https://www.w3.org/TR/xml/#charsets>
|
|
731
|
+
* We also encode LF (#xA), etc. because of XML normalization in XML parsers.
|
|
732
|
+
*
|
|
733
|
+
* In contrast to `escapeStringForAttributeValue()`, newlines do
|
|
734
|
+
* not need to be escaped.
|
|
735
|
+
*
|
|
736
|
+
* @param {string} str
|
|
737
|
+
* @returns {string}
|
|
738
|
+
*/
|
|
739
|
+
function escapeStringForText(str) {
|
|
740
|
+
if (typeof str !== 'string')
|
|
741
|
+
return str;
|
|
742
|
+
|
|
743
|
+
if (!/[&<>]/.test(str) && !hasControlCharacters(str) && !hasUnpairedUnicodeSurrogate(str))
|
|
744
|
+
return str;
|
|
745
|
+
|
|
746
|
+
str = escapeString(str, {
|
|
747
|
+
'&': '&',
|
|
748
|
+
'<': '<',
|
|
749
|
+
control: encodeNonCharacters,
|
|
750
|
+
unpairedSurrogate: encodeNonCharacters,
|
|
751
|
+
});
|
|
752
|
+
|
|
753
|
+
// Note: You can test this with <https://www.w3schools.com/xml/xml_validator.asp>:
|
|
754
|
+
// This sequence is allowed in attribute values but not element content.
|
|
755
|
+
str = str.replace(/]]>/g, ']]>');
|
|
756
|
+
|
|
757
|
+
return str;
|
|
758
|
+
}
|
|
759
|
+
|
|
760
|
+
/**
|
|
761
|
+
* Control characters need to be escaped, see §2.2:
|
|
762
|
+
* <https://www.w3.org/TR/xml/#charsets>
|
|
763
|
+
*
|
|
764
|
+
* Char ::= #x9 | #xA | #xD | [#x20-#xD7FF] | [#xE000-#xFFFD] | [#x10000-#x10FFFF]
|
|
765
|
+
* --> any Unicode character, excluding the surrogate blocks, FFFE, and FFFF.
|
|
766
|
+
*
|
|
767
|
+
* @param {number} codePoint
|
|
768
|
+
* @returns {string}
|
|
769
|
+
*/
|
|
770
|
+
function encodeNonCharacters(codePoint) {
|
|
771
|
+
const hex = codePoint.toString(16).toUpperCase();
|
|
772
|
+
return `&#x${hex};`;
|
|
680
773
|
}
|
|
681
774
|
|
|
682
775
|
// return the path prefix of a given name or if no prefix available 'root'
|
|
@@ -728,7 +821,8 @@ module.exports = {
|
|
|
728
821
|
mapCdsToEdmType,
|
|
729
822
|
addTypeFacets,
|
|
730
823
|
isODataSimpleIdentifier,
|
|
731
|
-
|
|
824
|
+
escapeStringForAttributeValue,
|
|
825
|
+
escapeStringForText,
|
|
732
826
|
getSchemaPrefix,
|
|
733
827
|
getBaseName
|
|
734
828
|
}
|
package/lib/gen/Dictionary.json
CHANGED
|
@@ -409,6 +409,7 @@
|
|
|
409
409
|
"Capabilities.MediaLocationUpdateSupported": {
|
|
410
410
|
"Type": "Core.Tag",
|
|
411
411
|
"AppliesTo": [
|
|
412
|
+
"EntityType",
|
|
412
413
|
"Property"
|
|
413
414
|
]
|
|
414
415
|
},
|
|
@@ -657,7 +658,8 @@
|
|
|
657
658
|
"Type": "Common.FieldControlType",
|
|
658
659
|
"AppliesTo": [
|
|
659
660
|
"Property",
|
|
660
|
-
"Record"
|
|
661
|
+
"Record",
|
|
662
|
+
"EntityType"
|
|
661
663
|
]
|
|
662
664
|
},
|
|
663
665
|
"Common.ExceptionCategory": {
|
|
@@ -1024,7 +1026,9 @@
|
|
|
1024
1026
|
]
|
|
1025
1027
|
},
|
|
1026
1028
|
"Common.RecursiveHierarchy": {
|
|
1027
|
-
"Type": "Common.RecursiveHierarchyType"
|
|
1029
|
+
"Type": "Common.RecursiveHierarchyType",
|
|
1030
|
+
"$deprecated": true,
|
|
1031
|
+
"$deprecationText": "Use terms [Aggregation.RecursiveHierarchy](https://github.com/oasis-tcs/odata-vocabularies/blob/main/vocabularies/Org.OData.Aggregation.V1.md#RecursiveHierarchy) and [Hierarchy.RecursiveHierarchy](https://github.com/SAP/odata-vocabularies/blob/main/vocabularies/Hierarchy.md#RecursiveHierarchy) instead"
|
|
1028
1032
|
},
|
|
1029
1033
|
"Common.CreatedAt": {
|
|
1030
1034
|
"Type": "Edm.DateTimeOffset",
|
|
@@ -1066,7 +1070,8 @@
|
|
|
1066
1070
|
"Common.mediaUploadLink": {
|
|
1067
1071
|
"Type": "Edm.String",
|
|
1068
1072
|
"AppliesTo": [
|
|
1069
|
-
"Property"
|
|
1073
|
+
"Property",
|
|
1074
|
+
"EntityType"
|
|
1070
1075
|
],
|
|
1071
1076
|
"$experimental": true
|
|
1072
1077
|
},
|
|
@@ -1279,6 +1284,7 @@
|
|
|
1279
1284
|
"Core.MediaType": {
|
|
1280
1285
|
"Type": "Edm.String",
|
|
1281
1286
|
"AppliesTo": [
|
|
1287
|
+
"EntityType",
|
|
1282
1288
|
"Property",
|
|
1283
1289
|
"Term",
|
|
1284
1290
|
"TypeDefinition",
|
|
@@ -1317,6 +1323,7 @@
|
|
|
1317
1323
|
"Core.AutoExpand": {
|
|
1318
1324
|
"Type": "Core.Tag",
|
|
1319
1325
|
"AppliesTo": [
|
|
1326
|
+
"EntityType",
|
|
1320
1327
|
"NavigationProperty",
|
|
1321
1328
|
"Property"
|
|
1322
1329
|
]
|
|
@@ -1375,8 +1382,49 @@
|
|
|
1375
1382
|
"Core.GeometryFeature": {
|
|
1376
1383
|
"Type": "Core.GeometryFeatureType"
|
|
1377
1384
|
},
|
|
1378
|
-
"
|
|
1379
|
-
"Type": "
|
|
1385
|
+
"DataIntegration.Extractable": {
|
|
1386
|
+
"Type": "Edm.Boolean",
|
|
1387
|
+
"AppliesTo": [
|
|
1388
|
+
"EntitySet"
|
|
1389
|
+
]
|
|
1390
|
+
},
|
|
1391
|
+
"DataIntegration.OriginalDataType": {
|
|
1392
|
+
"Type": "Edm.String",
|
|
1393
|
+
"AppliesTo": [
|
|
1394
|
+
"Property"
|
|
1395
|
+
]
|
|
1396
|
+
},
|
|
1397
|
+
"DataIntegration.OriginalName": {
|
|
1398
|
+
"Type": "Edm.String"
|
|
1399
|
+
},
|
|
1400
|
+
"DataIntegration.ConversionExit": {
|
|
1401
|
+
"Type": "Edm.String",
|
|
1402
|
+
"AppliesTo": [
|
|
1403
|
+
"Property"
|
|
1404
|
+
]
|
|
1405
|
+
},
|
|
1406
|
+
"DataIntegration.SourceSystem": {
|
|
1407
|
+
"Type": "Edm.String",
|
|
1408
|
+
"AppliesTo": [
|
|
1409
|
+
"Container"
|
|
1410
|
+
]
|
|
1411
|
+
},
|
|
1412
|
+
"DataIntegration.DeltaMethod": {
|
|
1413
|
+
"Type": "DataIntegration.DeltaMethodType",
|
|
1414
|
+
"AppliesTo": [
|
|
1415
|
+
"EntitySet"
|
|
1416
|
+
]
|
|
1417
|
+
},
|
|
1418
|
+
"Graph.traceId": {
|
|
1419
|
+
"Type": "Edm.String",
|
|
1420
|
+
"$experimental": true
|
|
1421
|
+
},
|
|
1422
|
+
"Graph.Details": {
|
|
1423
|
+
"Type": "Graph.DetailsType",
|
|
1424
|
+
"$experimental": true
|
|
1425
|
+
},
|
|
1426
|
+
"Hierarchy.RecursiveHierarchy": {
|
|
1427
|
+
"Type": "Hierarchy.RecursiveHierarchyType",
|
|
1380
1428
|
"AppliesTo": [
|
|
1381
1429
|
"EntityType"
|
|
1382
1430
|
],
|
|
@@ -1388,6 +1436,17 @@
|
|
|
1388
1436
|
"Record"
|
|
1389
1437
|
]
|
|
1390
1438
|
},
|
|
1439
|
+
"JSON.Schema": {
|
|
1440
|
+
"Type": "JSON.JSON",
|
|
1441
|
+
"AppliesTo": [
|
|
1442
|
+
"EntityType",
|
|
1443
|
+
"Parameter",
|
|
1444
|
+
"Property",
|
|
1445
|
+
"ReturnType",
|
|
1446
|
+
"Term",
|
|
1447
|
+
"TypeDefinition"
|
|
1448
|
+
]
|
|
1449
|
+
},
|
|
1391
1450
|
"Measures.ISOCurrency": {
|
|
1392
1451
|
"Type": "Edm.String",
|
|
1393
1452
|
"AppliesTo": [
|
|
@@ -1699,7 +1758,8 @@
|
|
|
1699
1758
|
"UI.IsImage": {
|
|
1700
1759
|
"Type": "Core.Tag",
|
|
1701
1760
|
"AppliesTo": [
|
|
1702
|
-
"Property"
|
|
1761
|
+
"Property",
|
|
1762
|
+
"EntityType"
|
|
1703
1763
|
],
|
|
1704
1764
|
"$experimental": true
|
|
1705
1765
|
},
|
|
@@ -1707,7 +1767,8 @@
|
|
|
1707
1767
|
"Type": "Core.Tag",
|
|
1708
1768
|
"AppliesTo": [
|
|
1709
1769
|
"Property",
|
|
1710
|
-
"PropertyValue"
|
|
1770
|
+
"PropertyValue",
|
|
1771
|
+
"Parameter"
|
|
1711
1772
|
]
|
|
1712
1773
|
},
|
|
1713
1774
|
"UI.Placeholder": {
|
|
@@ -1892,14 +1953,14 @@
|
|
|
1892
1953
|
]
|
|
1893
1954
|
},
|
|
1894
1955
|
"Validation.OpenPropertyTypeConstraint": {
|
|
1895
|
-
"Type": "Collection(
|
|
1956
|
+
"Type": "Collection(Validation.SingleOrCollectionType)",
|
|
1896
1957
|
"AppliesTo": [
|
|
1897
1958
|
"ComplexType",
|
|
1898
1959
|
"EntityType"
|
|
1899
1960
|
]
|
|
1900
1961
|
},
|
|
1901
1962
|
"Validation.DerivedTypeConstraint": {
|
|
1902
|
-
"Type": "Collection(
|
|
1963
|
+
"Type": "Collection(Validation.SingleOrCollectionType)",
|
|
1903
1964
|
"AppliesTo": [
|
|
1904
1965
|
"EntitySet",
|
|
1905
1966
|
"Singleton",
|
|
@@ -2695,6 +2756,7 @@
|
|
|
2695
2756
|
"EditAction": "Common.QualifiedName",
|
|
2696
2757
|
"NewAction": "Common.QualifiedName",
|
|
2697
2758
|
"AdditionalNewActions": "Collection(Common.QualifiedName)",
|
|
2759
|
+
"ShareAction": "Common.QualifiedName",
|
|
2698
2760
|
"PreparationAction": "Common.QualifiedName",
|
|
2699
2761
|
"ValidationFunction": "Common.QualifiedName"
|
|
2700
2762
|
}
|
|
@@ -2733,7 +2795,9 @@
|
|
|
2733
2795
|
"ExternalNodeKeyProperty": "Edm.PropertyPath",
|
|
2734
2796
|
"NodeDescendantCountProperty": "Edm.PropertyPath",
|
|
2735
2797
|
"NodeDrillStateProperty": "Edm.PropertyPath"
|
|
2736
|
-
}
|
|
2798
|
+
},
|
|
2799
|
+
"$deprecated": true,
|
|
2800
|
+
"$deprecationText": "Use terms [Aggregation.RecursiveHierarchy](https://github.com/oasis-tcs/odata-vocabularies/blob/main/vocabularies/Org.OData.Aggregation.V1.md#RecursiveHierarchy) and [Hierarchy.RecursiveHierarchy](https://github.com/SAP/odata-vocabularies/blob/main/vocabularies/Hierarchy.md#RecursiveHierarchy) instead"
|
|
2737
2801
|
},
|
|
2738
2802
|
"Common.NumericMessageSeverityType": {
|
|
2739
2803
|
"$kind": "TypeDefinition",
|
|
@@ -3115,22 +3179,31 @@
|
|
|
3115
3179
|
"UnderlyingType": "Edm.String",
|
|
3116
3180
|
"MaxLength": "128"
|
|
3117
3181
|
},
|
|
3118
|
-
"
|
|
3182
|
+
"DataIntegration.DeltaMethodType": {
|
|
3183
|
+
"$kind": "EnumType",
|
|
3184
|
+
"IsFlags": "true",
|
|
3185
|
+
"Members": [
|
|
3186
|
+
"INSERT",
|
|
3187
|
+
"UPDATE",
|
|
3188
|
+
"DELETE"
|
|
3189
|
+
]
|
|
3190
|
+
},
|
|
3191
|
+
"Graph.DetailsType": {
|
|
3119
3192
|
"$kind": "ComplexType",
|
|
3120
3193
|
"Properties": {
|
|
3121
|
-
"
|
|
3122
|
-
"
|
|
3123
|
-
"target": "Edm.String",
|
|
3124
|
-
"parameters": "Collection(Graph.binding)",
|
|
3125
|
-
"filter": "Collection(Graph.binding)"
|
|
3194
|
+
"url": "Edm.String",
|
|
3195
|
+
"body": "JSON.JSON"
|
|
3126
3196
|
},
|
|
3127
3197
|
"$experimental": true
|
|
3128
3198
|
},
|
|
3129
|
-
"
|
|
3199
|
+
"Hierarchy.RecursiveHierarchyType": {
|
|
3130
3200
|
"$kind": "ComplexType",
|
|
3131
3201
|
"Properties": {
|
|
3132
|
-
"
|
|
3133
|
-
"
|
|
3202
|
+
"ExternalKeyProperty": "Edm.PropertyPath",
|
|
3203
|
+
"DescendantCountProperty": "Edm.PropertyPath",
|
|
3204
|
+
"DrillStateProperty": "Edm.PropertyPath",
|
|
3205
|
+
"SiblingRankProperty": "Edm.PropertyPath",
|
|
3206
|
+
"PreorderRankProperty": "Edm.PropertyPath"
|
|
3134
3207
|
},
|
|
3135
3208
|
"$experimental": true
|
|
3136
3209
|
},
|
|
@@ -3140,6 +3213,10 @@
|
|
|
3140
3213
|
"width": "Edm.String"
|
|
3141
3214
|
}
|
|
3142
3215
|
},
|
|
3216
|
+
"JSON.JSON": {
|
|
3217
|
+
"$kind": "TypeDefinition",
|
|
3218
|
+
"UnderlyingType": "Edm.Stream"
|
|
3219
|
+
},
|
|
3143
3220
|
"Measures.DurationGranularityType": {
|
|
3144
3221
|
"$kind": "TypeDefinition",
|
|
3145
3222
|
"UnderlyingType": "Edm.String"
|
|
@@ -3894,6 +3971,10 @@
|
|
|
3894
3971
|
"path": "Edm.NavigationPropertyPath",
|
|
3895
3972
|
"target": "Edm.NavigationPropertyPath"
|
|
3896
3973
|
}
|
|
3974
|
+
},
|
|
3975
|
+
"Validation.SingleOrCollectionType": {
|
|
3976
|
+
"$kind": "TypeDefinition",
|
|
3977
|
+
"UnderlyingType": "Edm.String"
|
|
3897
3978
|
}
|
|
3898
3979
|
}
|
|
3899
3980
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
351a6ed427f91f2eef4d8e9a2e11dd17
|