@azure-tools/typespec-rust 0.37.0 → 0.38.1
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/dist/src/codegen/clients.d.ts.map +1 -1
- package/dist/src/codegen/clients.js +51 -30
- package/dist/src/codegen/clients.js.map +1 -1
- package/dist/src/codegen/helpers.d.ts.map +1 -1
- package/dist/src/codegen/helpers.js +3 -0
- package/dist/src/codegen/helpers.js.map +1 -1
- package/dist/src/codegen/models.js +36 -46
- package/dist/src/codegen/models.js.map +1 -1
- package/dist/src/codegen/unions.js +7 -18
- package/dist/src/codegen/unions.js.map +1 -1
- package/dist/src/codegen/use.d.ts +2 -1
- package/dist/src/codegen/use.d.ts.map +1 -1
- package/dist/src/codegen/use.js +14 -8
- package/dist/src/codegen/use.js.map +1 -1
- package/dist/src/codemodel/client.d.ts +2 -1
- package/dist/src/codemodel/client.d.ts.map +1 -1
- package/dist/src/codemodel/client.js.map +1 -1
- package/dist/src/codemodel/method.d.ts +2 -0
- package/dist/src/codemodel/method.d.ts.map +1 -1
- package/dist/src/codemodel/method.js +1 -0
- package/dist/src/codemodel/method.js.map +1 -1
- package/dist/src/codemodel/types.d.ts +13 -6
- package/dist/src/codemodel/types.d.ts.map +1 -1
- package/dist/src/codemodel/types.js +7 -0
- package/dist/src/codemodel/types.js.map +1 -1
- package/dist/src/tcgcadapter/adapter.d.ts +1 -0
- package/dist/src/tcgcadapter/adapter.d.ts.map +1 -1
- package/dist/src/tcgcadapter/adapter.js +171 -46
- package/dist/src/tcgcadapter/adapter.js.map +1 -1
- package/dist/src/utils/utils.d.ts +16 -0
- package/dist/src/utils/utils.d.ts.map +1 -1
- package/dist/src/utils/utils.js +29 -0
- package/dist/src/utils/utils.js.map +1 -1
- package/package.json +3 -3
|
@@ -222,7 +222,6 @@ export class Adapter {
|
|
|
222
222
|
};
|
|
223
223
|
terminalErrorModelNames = getTerminalErrorModelNames(this.ctx.sdkPackage.clients);
|
|
224
224
|
}
|
|
225
|
-
const processedTypes = new Set();
|
|
226
225
|
for (const model of this.ctx.sdkPackage.models) {
|
|
227
226
|
if ((model.usage & (tcgc.UsageFlags.Input | tcgc.UsageFlags.Output | tcgc.UsageFlags.Spread | tcgc.UsageFlags.Exception)) === 0) {
|
|
228
227
|
// skip types without input and output usage. this will include core
|
|
@@ -236,15 +235,7 @@ export class Adapter {
|
|
|
236
235
|
continue;
|
|
237
236
|
}
|
|
238
237
|
needsCoreAndSerde = true;
|
|
239
|
-
|
|
240
|
-
if (processedTypes.has(model.name)) {
|
|
241
|
-
continue;
|
|
242
|
-
}
|
|
243
|
-
else {
|
|
244
|
-
processedTypes.add(model.name);
|
|
245
|
-
}
|
|
246
|
-
// END workaround
|
|
247
|
-
if (model.discriminatedSubtypes) {
|
|
238
|
+
if (isPolymorphicRoot(model)) {
|
|
248
239
|
const rustUnion = this.getDiscriminatedUnion(model);
|
|
249
240
|
this.adaptNamespace(model.namespace).unions.push(rustUnion);
|
|
250
241
|
// we don't want to add the base type to the array
|
|
@@ -426,7 +417,7 @@ export class Adapter {
|
|
|
426
417
|
// aggregate the properties from the provided type and its parent types
|
|
427
418
|
const allProps = new Array();
|
|
428
419
|
for (const prop of model.properties) {
|
|
429
|
-
if (prop.discriminator && !model
|
|
420
|
+
if (prop.discriminator && !isPolymorphicRoot(model)) {
|
|
430
421
|
rustModel.flags |= rust.ModelFlags.PolymorphicSubtype;
|
|
431
422
|
}
|
|
432
423
|
allProps.push(prop);
|
|
@@ -492,7 +483,7 @@ export class Adapter {
|
|
|
492
483
|
* @returns a Rust union
|
|
493
484
|
*/
|
|
494
485
|
getDiscriminatedUnion(src) {
|
|
495
|
-
var _a, _b, _c, _d, _e, _f, _g;
|
|
486
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _j;
|
|
496
487
|
if (src.name.length === 0) {
|
|
497
488
|
throw new AdapterError('InternalError', 'unnamed union', (_a = src.__raw) === null || _a === void 0 ? void 0 : _a.node);
|
|
498
489
|
}
|
|
@@ -504,7 +495,7 @@ export class Adapter {
|
|
|
504
495
|
}
|
|
505
496
|
switch (src.kind) {
|
|
506
497
|
case 'model': {
|
|
507
|
-
if (!src
|
|
498
|
+
if (!isPolymorphicRoot(src)) {
|
|
508
499
|
// we should have verified this earlier.
|
|
509
500
|
// having this check means the compiler won't bark
|
|
510
501
|
// at us when accessing src.discriminatedSubtypes
|
|
@@ -528,13 +519,37 @@ export class Adapter {
|
|
|
528
519
|
rustUnion.unionKind = new rust.DiscriminatedUnionSealed();
|
|
529
520
|
}
|
|
530
521
|
else {
|
|
531
|
-
|
|
522
|
+
const typeName = `Unknown${utils.capitalize(src.name).replace(/\W/g, '')}${utils.capitalize(rustUnion.discriminant)}`;
|
|
523
|
+
const baseModel = this.getModel(src, undefined, typeName);
|
|
524
|
+
const module = this.adaptNamespace(src.namespace);
|
|
525
|
+
if (!module.models.includes(baseModel)) {
|
|
526
|
+
// we only fix up the base model if it's not
|
|
527
|
+
// in the collection of models for this module
|
|
528
|
+
baseModel.flags = rust.ModelFlags.PolymorphicBase;
|
|
529
|
+
// internal serde helper only
|
|
530
|
+
baseModel.visibility = 'pubCrate';
|
|
531
|
+
const lifetime = new rust.Lifetime('a');
|
|
532
|
+
baseModel.lifetime = lifetime;
|
|
533
|
+
for (const field of baseModel.fields) {
|
|
534
|
+
if (field.kind === 'modelField') {
|
|
535
|
+
// strip off the discriminator flag
|
|
536
|
+
field.flags &= ~rust.ModelFieldFlags.Discriminator;
|
|
537
|
+
}
|
|
538
|
+
if (!typeToRefType(field.type)) {
|
|
539
|
+
throw new AdapterError('InternalError', `unsupported field kind ${field.type.kind} in polymorphic base model ${baseModel.name}`, (_d = src.__raw) === null || _d === void 0 ? void 0 : _d.node);
|
|
540
|
+
}
|
|
541
|
+
field.type = this.getRefType(field.type, lifetime);
|
|
542
|
+
}
|
|
543
|
+
module.models.push(baseModel);
|
|
544
|
+
}
|
|
545
|
+
rustUnion.unionKind = new rust.DiscriminatedUnionBase(baseModel);
|
|
532
546
|
}
|
|
533
|
-
|
|
547
|
+
// we need to handle the case where src is a root with no child types
|
|
548
|
+
for (const subType of Object.values((_e = src.discriminatedSubtypes) !== null && _e !== void 0 ? _e : {})) {
|
|
534
549
|
if (!subType.discriminatorValue) {
|
|
535
|
-
throw new AdapterError('InternalError', `model ${subType.name} has no discriminator value`, (
|
|
550
|
+
throw new AdapterError('InternalError', `model ${subType.name} has no discriminator value`, (_f = subType.__raw) === null || _f === void 0 ? void 0 : _f.node);
|
|
536
551
|
}
|
|
537
|
-
const unionMemberType = this.getModel(subType);
|
|
552
|
+
const unionMemberType = subType.discriminatedSubtypes ? this.getDiscriminatedUnion(subType) : this.getModel(subType);
|
|
538
553
|
const rustUnionMember = new rust.DiscriminatedUnionMember(unionMemberType, subType.discriminatorValue);
|
|
539
554
|
rustUnion.members.push(rustUnionMember);
|
|
540
555
|
}
|
|
@@ -545,7 +560,7 @@ export class Adapter {
|
|
|
545
560
|
// we should have verified this earlier.
|
|
546
561
|
// having this check means the compiler won't bark
|
|
547
562
|
// at us when accessing src.discriminatedOptions
|
|
548
|
-
throw new AdapterError('InternalError', 'getDiscriminatedUnion called for non-discriminated union', (
|
|
563
|
+
throw new AdapterError('InternalError', 'getDiscriminatedUnion called for non-discriminated union', (_g = src.__raw) === null || _g === void 0 ? void 0 : _g.node);
|
|
549
564
|
}
|
|
550
565
|
rustUnion = new rust.DiscriminatedUnion(unionName, adaptAccessFlags(src.access), src.discriminatedOptions.discriminatorPropertyName, this.adaptNamespace(src.namespace));
|
|
551
566
|
if (src.discriminatedOptions.envelopePropertyName) {
|
|
@@ -568,12 +583,12 @@ export class Adapter {
|
|
|
568
583
|
// END WORKAROUND
|
|
569
584
|
for (const unionMember of src.variantTypes) {
|
|
570
585
|
if (unionMember.kind !== 'model') {
|
|
571
|
-
throw new AdapterError('UnsupportedTsp', `non-model union member kind ${unionMember.kind}`, (
|
|
586
|
+
throw new AdapterError('UnsupportedTsp', `non-model union member kind ${unionMember.kind}`, (_h = unionMember.__raw) === null || _h === void 0 ? void 0 : _h.node);
|
|
572
587
|
}
|
|
573
588
|
// TODO: use unionMember.discriminatorValue
|
|
574
589
|
const discriminatorValue = discriminatorValues.get(unionMember.name);
|
|
575
590
|
if (!discriminatorValue) {
|
|
576
|
-
throw new AdapterError('InternalError', `didn't find discriminant value for type ${unionMember.name}`, (
|
|
591
|
+
throw new AdapterError('InternalError', `didn't find discriminant value for type ${unionMember.name}`, (_j = unionMember.__raw) === null || _j === void 0 ? void 0 : _j.node);
|
|
577
592
|
}
|
|
578
593
|
const unionMemberType = this.getModel(unionMember);
|
|
579
594
|
const rustUnionMember = new rust.DiscriminatedUnionMember(unionMemberType, discriminatorValue);
|
|
@@ -831,6 +846,9 @@ export class Adapter {
|
|
|
831
846
|
}
|
|
832
847
|
modelField.docs.description += `Operational visibility: ${visibilityStr}`;
|
|
833
848
|
}
|
|
849
|
+
if (property.visibility && property.visibility.length === 1 && property.visibility[0] === http.Visibility.Read) {
|
|
850
|
+
modelField.flags |= rust.ModelFieldFlags.ReadOnly;
|
|
851
|
+
}
|
|
834
852
|
// if this is a literal, add a doc comment explaining its behavior
|
|
835
853
|
const unwrappedType = utils.unwrapOption(fieldType);
|
|
836
854
|
if (unwrappedType.kind === 'enumValue' || unwrappedType.kind === 'literal') {
|
|
@@ -985,7 +1003,7 @@ export class Adapter {
|
|
|
985
1003
|
if (type.external) {
|
|
986
1004
|
return this.getExternalType(type.external);
|
|
987
1005
|
}
|
|
988
|
-
else if (type
|
|
1006
|
+
else if (isPolymorphicRoot(type)) {
|
|
989
1007
|
return this.getDiscriminatedUnion(type);
|
|
990
1008
|
}
|
|
991
1009
|
else if (tcgc.isAzureCoreModel(type)) {
|
|
@@ -1305,7 +1323,7 @@ export class Adapter {
|
|
|
1305
1323
|
* @returns a Rust client
|
|
1306
1324
|
*/
|
|
1307
1325
|
recursiveAdaptClient(client, parent) {
|
|
1308
|
-
var _a, _b, _c, _d, _e;
|
|
1326
|
+
var _a, _b, _c, _d, _e, _f, _g;
|
|
1309
1327
|
let clientName = client.name;
|
|
1310
1328
|
// NOTE: if the client has the @clientName decorator applied then use that verbatim
|
|
1311
1329
|
if (parent && !hasClientNameDecorator(client.decorators)) {
|
|
@@ -1465,10 +1483,16 @@ export class Adapter {
|
|
|
1465
1483
|
break;
|
|
1466
1484
|
}
|
|
1467
1485
|
case 'method': {
|
|
1468
|
-
// https://github.com/Azure/typespec-rust/issues/849
|
|
1469
|
-
// Azure doesn't use optional (with no explicit default value) API versions anyway.
|
|
1470
1486
|
if (param.isApiVersionParam && param.optional && !param.clientDefaultValue) {
|
|
1471
|
-
|
|
1487
|
+
if (!parent && client.children && client.methods.length === 0) {
|
|
1488
|
+
// this is the top-level client for a multi-client scenario.
|
|
1489
|
+
// each sub-client will have its own api-version parameter.
|
|
1490
|
+
// we omit this "merged" api-version param as it's useless.
|
|
1491
|
+
continue;
|
|
1492
|
+
}
|
|
1493
|
+
else {
|
|
1494
|
+
throw new AdapterError('UnsupportedTsp', 'found optional apiVersion parameter with no default value', (_c = param.__raw) === null || _c === void 0 ? void 0 : _c.node);
|
|
1495
|
+
}
|
|
1472
1496
|
}
|
|
1473
1497
|
const clientParam = this.adaptClientParameter(param, rustClient.constructable);
|
|
1474
1498
|
rustClient.fields.push(new rust.StructField(clientParam.name, 'pubCrate', clientParam.type));
|
|
@@ -1506,6 +1530,33 @@ export class Adapter {
|
|
|
1506
1530
|
// as these are handled in the parent client.
|
|
1507
1531
|
continue;
|
|
1508
1532
|
}
|
|
1533
|
+
else if (prop.isApiVersionParam) {
|
|
1534
|
+
// we didn't find the api-version param in the parent which means
|
|
1535
|
+
// this is a multi-client child with its own api-version param.
|
|
1536
|
+
// we need to find the instantiable parent client.
|
|
1537
|
+
let constructable;
|
|
1538
|
+
let cur = parent;
|
|
1539
|
+
while (cur) {
|
|
1540
|
+
constructable = cur.constructable;
|
|
1541
|
+
if (constructable) {
|
|
1542
|
+
break;
|
|
1543
|
+
}
|
|
1544
|
+
cur = cur.parent;
|
|
1545
|
+
}
|
|
1546
|
+
if (!constructable || !cur) {
|
|
1547
|
+
throw new AdapterError('InternalError', `didn't find constructable client for apiVersion in client ${rustClient.name}`, (_d = prop.__raw) === null || _d === void 0 ? void 0 : _d.node);
|
|
1548
|
+
}
|
|
1549
|
+
rustClient.fields.push(new rust.StructField(utils.snakeCaseName(prop.name), 'pubCrate', this.getStringType()));
|
|
1550
|
+
// we use the client name as a prefix to disambiguate the params in the parent
|
|
1551
|
+
const clientParam = this.adaptClientParameter(prop, constructable, utils.deduplicateClientFieldName(rustClient, name));
|
|
1552
|
+
const field = new rust.StructField(clientParam.name, 'pubCrate', clientParam.type);
|
|
1553
|
+
cur.fields.push(field);
|
|
1554
|
+
// propagate this param to all client constructors
|
|
1555
|
+
for (const constructor of constructable.constructors) {
|
|
1556
|
+
constructor.params.push(clientParam);
|
|
1557
|
+
}
|
|
1558
|
+
continue;
|
|
1559
|
+
}
|
|
1509
1560
|
// unique field for this client
|
|
1510
1561
|
rustClient.fields.push(new rust.StructField(name, 'pubCrate', this.getType(prop.type)));
|
|
1511
1562
|
}
|
|
@@ -1513,7 +1564,7 @@ export class Adapter {
|
|
|
1513
1564
|
else {
|
|
1514
1565
|
throw new AdapterError('InternalError', `uninstantiatable client ${client.name} has no parent`);
|
|
1515
1566
|
}
|
|
1516
|
-
for (const child of (
|
|
1567
|
+
for (const child of (_e = client.children) !== null && _e !== void 0 ? _e : []) {
|
|
1517
1568
|
const subClient = this.recursiveAdaptClient(child, rustClient);
|
|
1518
1569
|
this.adaptClientAccessor(client, child, rustClient, subClient);
|
|
1519
1570
|
}
|
|
@@ -1525,7 +1576,7 @@ export class Adapter {
|
|
|
1525
1576
|
code: 'LroPagingNotSupported',
|
|
1526
1577
|
severity: 'warning',
|
|
1527
1578
|
message: `skip emitting Paging LRO ${method.name}`,
|
|
1528
|
-
target: (
|
|
1579
|
+
target: (_g = (_f = method.__raw) === null || _f === void 0 ? void 0 : _f.node) !== null && _g !== void 0 ? _g : tsp.NoTarget,
|
|
1529
1580
|
});
|
|
1530
1581
|
continue;
|
|
1531
1582
|
}
|
|
@@ -1566,11 +1617,12 @@ export class Adapter {
|
|
|
1566
1617
|
*
|
|
1567
1618
|
* @param param the tcgc client parameter to convert
|
|
1568
1619
|
* @param constructable contains client construction info. if the param is optional, it will go in the options type
|
|
1620
|
+
* @param name optional custom name for the parameter
|
|
1569
1621
|
* @returns the Rust client parameter
|
|
1570
1622
|
*/
|
|
1571
|
-
adaptClientParameter(param, constructable) {
|
|
1623
|
+
adaptClientParameter(param, constructable, name) {
|
|
1572
1624
|
let paramType = param.isApiVersionParam ? this.getStringType() : this.getType(param.type);
|
|
1573
|
-
const paramName = utils.snakeCaseName(param.name);
|
|
1625
|
+
const paramName = name !== null && name !== void 0 ? name : utils.snakeCaseName(param.name);
|
|
1574
1626
|
let optional = false;
|
|
1575
1627
|
// client-side default value makes the param optional
|
|
1576
1628
|
if (param.optional || param.clientDefaultValue) {
|
|
@@ -1637,7 +1689,7 @@ export class Adapter {
|
|
|
1637
1689
|
* @param rustClient the client to which the method belongs
|
|
1638
1690
|
*/
|
|
1639
1691
|
adaptMethod(method, rustClient) {
|
|
1640
|
-
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s;
|
|
1692
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s, _t, _u, _v, _w;
|
|
1641
1693
|
let srcMethodName = method.name;
|
|
1642
1694
|
if (method.kind === 'paging' && !srcMethodName.match(/^list/i)) {
|
|
1643
1695
|
const chunks = utils.deconstruct(srcMethodName);
|
|
@@ -1715,8 +1767,21 @@ export class Adapter {
|
|
|
1715
1767
|
// https://github.com/microsoft/typespec/blob/f3d792b252c6f40be0e174496d9f34d453676026/packages/http-client-csharp/emitter/src/type/operation-final-state-via.ts#L23-L27
|
|
1716
1768
|
lroFinalResultStrategy = new rust.LroFinalResultStrategyHeader('operation-location');
|
|
1717
1769
|
break;
|
|
1770
|
+
case FinalStateValue.customLink:
|
|
1771
|
+
if (((_d = method.lroMetadata.statusMonitorStep) === null || _d === void 0 ? void 0 : _d.kind) === "nextOperationLink") {
|
|
1772
|
+
const customHeaderName = method.lroMetadata.statusMonitorStep.target.property.name;
|
|
1773
|
+
if (customHeaderName.trim() === '') {
|
|
1774
|
+
throw new AdapterError('UnsupportedTsp', `lroMetadata.finalStateVia === customLink && customHeaderName === "${customHeaderName}"`, (_e = method.__raw) === null || _e === void 0 ? void 0 : _e.node);
|
|
1775
|
+
}
|
|
1776
|
+
lroFinalResultStrategy = new rust.LroFinalResultStrategyHeader(customHeaderName);
|
|
1777
|
+
}
|
|
1778
|
+
else {
|
|
1779
|
+
throw new AdapterError('UnsupportedTsp', `lroMetadata.finalStateVia === customLink && lroMetadata.statusMonitorStep?.kind === "${(_f = method.lroMetadata.statusMonitorStep) === null || _f === void 0 ? void 0 : _f.kind}"`, (_g = method.__raw) === null || _g === void 0 ? void 0 : _g.node);
|
|
1780
|
+
}
|
|
1781
|
+
break;
|
|
1718
1782
|
default:
|
|
1719
|
-
|
|
1783
|
+
/* eslint-disable-next-line @typescript-eslint/restrict-template-expressions */
|
|
1784
|
+
throw new AdapterError('UnsupportedTsp', `lroMetadata.finalStateVia ${method.lroMetadata.finalStateVia} NYI`, (_h = method.__raw) === null || _h === void 0 ? void 0 : _h.node);
|
|
1720
1785
|
}
|
|
1721
1786
|
lroFinalResultStrategy.propertyName = method.lroMetadata.finalResultPath;
|
|
1722
1787
|
}
|
|
@@ -1724,7 +1789,7 @@ export class Adapter {
|
|
|
1724
1789
|
}
|
|
1725
1790
|
break;
|
|
1726
1791
|
default:
|
|
1727
|
-
throw new AdapterError('UnsupportedTsp', `method kind ${method.kind} NYI`, (
|
|
1792
|
+
throw new AdapterError('UnsupportedTsp', `method kind ${method.kind} NYI`, (_j = method.__raw) === null || _j === void 0 ? void 0 : _j.node);
|
|
1728
1793
|
}
|
|
1729
1794
|
rustMethod.docs = this.adaptDocs(method.summary, method.doc);
|
|
1730
1795
|
rustClient.methods.push(rustMethod);
|
|
@@ -1845,7 +1910,7 @@ export class Adapter {
|
|
|
1845
1910
|
if (!fieldOptional) {
|
|
1846
1911
|
if (!paramGroup) {
|
|
1847
1912
|
if (param.type.kind !== 'model') {
|
|
1848
|
-
throw new AdapterError('InternalError', `expected model type for parameter group but got ${param.type.kind}`, (
|
|
1913
|
+
throw new AdapterError('InternalError', `expected model type for parameter group but got ${param.type.kind}`, (_k = param.__raw) === null || _k === void 0 ? void 0 : _k.node);
|
|
1849
1914
|
}
|
|
1850
1915
|
const groupName = utils.capitalize(param.type.name).replace(/\W/g, '');
|
|
1851
1916
|
const paramName = naming.getEscapedReservedName(utils.snakeCaseName(param.name), 'param', reservedParams);
|
|
@@ -1890,7 +1955,7 @@ export class Adapter {
|
|
|
1890
1955
|
}
|
|
1891
1956
|
}
|
|
1892
1957
|
else {
|
|
1893
|
-
throw new AdapterError('InternalError', `didn't find operation parameter for method ${method.name} parameter ${param.name}`, (
|
|
1958
|
+
throw new AdapterError('InternalError', `didn't find operation parameter for method ${method.name} parameter ${param.name}`, (_l = param.__raw) === null || _l === void 0 ? void 0 : _l.node);
|
|
1894
1959
|
}
|
|
1895
1960
|
}
|
|
1896
1961
|
// client params aren't included in method.parameters so
|
|
@@ -1973,16 +2038,16 @@ export class Adapter {
|
|
|
1973
2038
|
const responseFormat = getResponseFormat();
|
|
1974
2039
|
if (method.kind === 'paging') {
|
|
1975
2040
|
if (responseFormat !== 'JsonFormat' && responseFormat !== 'XmlFormat') {
|
|
1976
|
-
throw new AdapterError('InternalError', `paged method ${method.name} unexpected response format ${responseFormat}`, (
|
|
2041
|
+
throw new AdapterError('InternalError', `paged method ${method.name} unexpected response format ${responseFormat}`, (_m = method.__raw) === null || _m === void 0 ? void 0 : _m.node);
|
|
1977
2042
|
}
|
|
1978
2043
|
// for paged methods, tcgc models method.response.type as an Array<T>.
|
|
1979
2044
|
// however, we want the synthesized paged response envelope type instead.
|
|
1980
2045
|
const synthesizedType = method.operation.responses[0].type;
|
|
1981
2046
|
if (!synthesizedType) {
|
|
1982
|
-
throw new AdapterError('InternalError', `paged method ${method.name} has no synthesized response type`, (
|
|
2047
|
+
throw new AdapterError('InternalError', `paged method ${method.name} has no synthesized response type`, (_o = method.__raw) === null || _o === void 0 ? void 0 : _o.node);
|
|
1983
2048
|
}
|
|
1984
2049
|
else if (synthesizedType.kind !== 'model') {
|
|
1985
|
-
throw new AdapterError('UnsupportedTsp', `paged method ${method.name} synthesized response type has unexpected kind ${synthesizedType.kind}`, (
|
|
2050
|
+
throw new AdapterError('UnsupportedTsp', `paged method ${method.name} synthesized response type has unexpected kind ${synthesizedType.kind}`, (_p = method.__raw) === null || _p === void 0 ? void 0 : _p.node);
|
|
1986
2051
|
}
|
|
1987
2052
|
const synthesizedModel = this.getModel(synthesizedType, new Array());
|
|
1988
2053
|
const modelNs = this.adaptNamespace(synthesizedType.namespace);
|
|
@@ -1991,7 +2056,7 @@ export class Adapter {
|
|
|
1991
2056
|
}
|
|
1992
2057
|
// for the pager response type, remove the Option<T> around the Vec<T> for the page items
|
|
1993
2058
|
if (!method.pagingMetadata.pageItemsSegments) {
|
|
1994
|
-
throw new AdapterError('InternalError', `paged method ${method.name} has no pageItemsSegments`, (
|
|
2059
|
+
throw new AdapterError('InternalError', `paged method ${method.name} has no pageItemsSegments`, (_q = method.__raw) === null || _q === void 0 ? void 0 : _q.node);
|
|
1995
2060
|
}
|
|
1996
2061
|
// unwrap all of the segments for the paged response
|
|
1997
2062
|
let unwrappedCount = 0;
|
|
@@ -2002,13 +2067,13 @@ export class Adapter {
|
|
|
2002
2067
|
switch (responseFormat) {
|
|
2003
2068
|
case 'JsonFormat':
|
|
2004
2069
|
if (segment.kind !== 'property' || !segment.serializationOptions.json) {
|
|
2005
|
-
throw new AdapterError('InternalError', `paged method ${method.name} is missing JSON serialization data`, (
|
|
2070
|
+
throw new AdapterError('InternalError', `paged method ${method.name} is missing JSON serialization data`, (_r = method.__raw) === null || _r === void 0 ? void 0 : _r.node);
|
|
2006
2071
|
}
|
|
2007
2072
|
serde = segment.serializationOptions.json.name;
|
|
2008
2073
|
break;
|
|
2009
2074
|
case 'XmlFormat':
|
|
2010
2075
|
if (segment.kind !== 'property' || !segment.serializationOptions.xml) {
|
|
2011
|
-
throw new AdapterError('InternalError', `paged method ${method.name} is missing XML serialization data`, (
|
|
2076
|
+
throw new AdapterError('InternalError', `paged method ${method.name} is missing XML serialization data`, (_s = method.__raw) === null || _s === void 0 ? void 0 : _s.node);
|
|
2012
2077
|
}
|
|
2013
2078
|
serde = segment.serializationOptions.xml.name;
|
|
2014
2079
|
break;
|
|
@@ -2034,7 +2099,7 @@ export class Adapter {
|
|
|
2034
2099
|
}
|
|
2035
2100
|
}
|
|
2036
2101
|
if (unwrappedCount !== method.pagingMetadata.pageItemsSegments.length) {
|
|
2037
|
-
throw new AdapterError('InternalError', `failed to unwrap paged items for method ${method.name}`, (
|
|
2102
|
+
throw new AdapterError('InternalError', `failed to unwrap paged items for method ${method.name}`, (_t = method.__raw) === null || _t === void 0 ? void 0 : _t.node);
|
|
2038
2103
|
}
|
|
2039
2104
|
this.crate.addDependency(new rust.CrateDependency('async-trait'));
|
|
2040
2105
|
// default to nextLink. will update it as required when we have that info
|
|
@@ -2067,7 +2132,7 @@ export class Adapter {
|
|
|
2067
2132
|
const statusModel = this.getModel(method.lroMetadata.pollingInfo.responseModel, undefined, `${rustClient.name}${utils.pascalCase(rustMethod.name, false)}OperationStatus`);
|
|
2068
2133
|
const statusType = this.typeToWireType(statusModel);
|
|
2069
2134
|
if (statusType.kind !== 'model') {
|
|
2070
|
-
throw new AdapterError('InternalError', `status type for an LRO method '${method.name}' is not a model`, (
|
|
2135
|
+
throw new AdapterError('InternalError', `status type for an LRO method '${method.name}' is not a model`, (_u = method.__raw) === null || _u === void 0 ? void 0 : _u.node);
|
|
2071
2136
|
}
|
|
2072
2137
|
// the adapted type likely comes from core which means
|
|
2073
2138
|
// it will be in the root namespace. since we emit these
|
|
@@ -2124,10 +2189,10 @@ export class Adapter {
|
|
|
2124
2189
|
// can't do this until the method has been completely adapted
|
|
2125
2190
|
const pageableMethod = rustMethod;
|
|
2126
2191
|
pageableMethod.strategy = this.adaptPageableMethodStrategy(method, paramsMap, responseHeadersMap);
|
|
2127
|
-
if (((
|
|
2192
|
+
if (((_v = pageableMethod.strategy) === null || _v === void 0 ? void 0 : _v.kind) === 'nextLink') {
|
|
2128
2193
|
pageableMethod.strategy.reinjectedParams = this.adaptPageableMethodReinjectionParams(method, paramsMap);
|
|
2129
2194
|
}
|
|
2130
|
-
else if (((
|
|
2195
|
+
else if (((_w = pageableMethod.strategy) === null || _w === void 0 ? void 0 : _w.kind) === 'continuationToken') {
|
|
2131
2196
|
// set the continuation type to token on the Pager and the PagerOptions field in the method options
|
|
2132
2197
|
pageableMethod.returns.type.continuation = 'token';
|
|
2133
2198
|
for (const field of pageableMethod.options.type.type.fields) {
|
|
@@ -2195,6 +2260,8 @@ export class Adapter {
|
|
|
2195
2260
|
return type.name;
|
|
2196
2261
|
case 'hashmap':
|
|
2197
2262
|
return `${type.name}${recursiveTypeName(type.type)}`;
|
|
2263
|
+
case 'option':
|
|
2264
|
+
return `Option${recursiveTypeName(type.type)}`;
|
|
2198
2265
|
case 'ref':
|
|
2199
2266
|
return `Ref${recursiveTypeName(type.type)}`;
|
|
2200
2267
|
case 'scalar':
|
|
@@ -2369,7 +2436,7 @@ export class Adapter {
|
|
|
2369
2436
|
* @returns a Rust method parameter
|
|
2370
2437
|
*/
|
|
2371
2438
|
adaptMethodParameter(opParam, methodParam, lifetime) {
|
|
2372
|
-
var _a, _b, _c, _d, _e, _f, _g, _h;
|
|
2439
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _j;
|
|
2373
2440
|
/**
|
|
2374
2441
|
* used to create keys for this.clientMethodParams
|
|
2375
2442
|
* @param param the param for which to create a key
|
|
@@ -2498,6 +2565,12 @@ export class Adapter {
|
|
|
2498
2565
|
throw new AdapterError('InternalError', `unexpected kind ${paramType.kind} for scalar path ${opParam.serializedName}`, (_g = opParam.__raw) === null || _g === void 0 ? void 0 : _g.node);
|
|
2499
2566
|
}
|
|
2500
2567
|
adaptedParam = new rust.PathScalarParameter(paramName, opParam.serializedName, paramLoc, paramOptional, paramType, opParam.allowReserved, style);
|
|
2568
|
+
const allowEmpty = ((_h = opParam.decorators.find(d => d.name === 'Azure.ClientGenerator.Core.@clientOption'
|
|
2569
|
+
&& d.arguments['name'] === 'allowEmpty'
|
|
2570
|
+
&& d.arguments['scope'] === 'rust')) === null || _h === void 0 ? void 0 : _h.arguments['value']) === true;
|
|
2571
|
+
if (allowEmpty) {
|
|
2572
|
+
adaptedParam.minLength = 0;
|
|
2573
|
+
}
|
|
2501
2574
|
}
|
|
2502
2575
|
}
|
|
2503
2576
|
break;
|
|
@@ -2521,7 +2594,7 @@ export class Adapter {
|
|
|
2521
2594
|
case 'model':
|
|
2522
2595
|
case 'slice':
|
|
2523
2596
|
case 'str':
|
|
2524
|
-
throw new AdapterError('InternalError', `unexpected kind ${paramType.kind} for scalar query ${opParam.serializedName}`, (
|
|
2597
|
+
throw new AdapterError('InternalError', `unexpected kind ${paramType.kind} for scalar query ${opParam.serializedName}`, (_j = opParam.__raw) === null || _j === void 0 ? void 0 : _j.node);
|
|
2525
2598
|
}
|
|
2526
2599
|
// TODO: hard-coded encoding setting, https://github.com/Azure/typespec-azure/issues/1314
|
|
2527
2600
|
adaptedParam = new rust.QueryScalarParameter(paramName, opParam.serializedName, paramLoc, paramOptional, paramType, true);
|
|
@@ -2730,6 +2803,7 @@ function recursiveKeyName(root, type) {
|
|
|
2730
2803
|
switch (type.kind) {
|
|
2731
2804
|
case 'Vec':
|
|
2732
2805
|
case 'box':
|
|
2806
|
+
case 'option':
|
|
2733
2807
|
return recursiveKeyName(`${root}-${type.kind}`, type.type);
|
|
2734
2808
|
case 'encodedBytes':
|
|
2735
2809
|
return `${root}-${type.kind}-${type.encoding}${type.slice ? '-slice' : ''}`;
|
|
@@ -2904,4 +2978,55 @@ function isLibNamespace(namespace) {
|
|
|
2904
2978
|
const ns = namespace.toLowerCase();
|
|
2905
2979
|
return LIB_NAMESPACE.some((lib) => ns === lib || ns.startsWith(lib + '.'));
|
|
2906
2980
|
}
|
|
2981
|
+
/**
|
|
2982
|
+
* narrows type to a RefType within the conditional block.
|
|
2983
|
+
* this function throws if the narrowing is not possible.
|
|
2984
|
+
*/
|
|
2985
|
+
function typeToRefType(type) {
|
|
2986
|
+
switch (type.kind) {
|
|
2987
|
+
case 'bytes':
|
|
2988
|
+
case 'decimal':
|
|
2989
|
+
case 'discriminatedUnion':
|
|
2990
|
+
case 'encodedBytes':
|
|
2991
|
+
case 'enum':
|
|
2992
|
+
case 'enumValue':
|
|
2993
|
+
case 'Etag':
|
|
2994
|
+
case 'external':
|
|
2995
|
+
case 'hashmap':
|
|
2996
|
+
case 'jsonValue':
|
|
2997
|
+
case 'model':
|
|
2998
|
+
case 'offsetDateTime':
|
|
2999
|
+
case 'option':
|
|
3000
|
+
case 'safeint':
|
|
3001
|
+
case 'scalar':
|
|
3002
|
+
case 'slice':
|
|
3003
|
+
case 'str':
|
|
3004
|
+
case 'String':
|
|
3005
|
+
case 'untaggedUnion':
|
|
3006
|
+
case 'Url':
|
|
3007
|
+
case 'Vec':
|
|
3008
|
+
return true;
|
|
3009
|
+
default:
|
|
3010
|
+
throw new AdapterError('InternalError', `cannot convert ${type.kind} to a ref type`);
|
|
3011
|
+
}
|
|
3012
|
+
}
|
|
3013
|
+
/**
|
|
3014
|
+
* returns true if model is a polymorphic root type.
|
|
3015
|
+
*
|
|
3016
|
+
* @param model the model to inspect
|
|
3017
|
+
* @returns true if the model is a polymorphic root
|
|
3018
|
+
*/
|
|
3019
|
+
function isPolymorphicRoot(model) {
|
|
3020
|
+
if (model.discriminatedSubtypes) {
|
|
3021
|
+
// when there are sub-types we know for sure it's a polymorphic root
|
|
3022
|
+
return true;
|
|
3023
|
+
}
|
|
3024
|
+
else if (model.discriminatorProperty && !model.discriminatorValue) {
|
|
3025
|
+
// we can land here if it's a root but has no child types
|
|
3026
|
+
return true;
|
|
3027
|
+
}
|
|
3028
|
+
else {
|
|
3029
|
+
return false;
|
|
3030
|
+
}
|
|
3031
|
+
}
|
|
2907
3032
|
//# sourceMappingURL=adapter.js.map
|