diff --git a/tools/tsp-client/CHANGELOG.md b/tools/tsp-client/CHANGELOG.md index c2ff5ea6274..c406e461ee6 100644 --- a/tools/tsp-client/CHANGELOG.md +++ b/tools/tsp-client/CHANGELOG.md @@ -1,5 +1,9 @@ # Release +## 2024-06-21 - 0.9.0 + +- Prefer the `service-dir` parameter in the emitter configurations in tspconfig.yaml if specified. + ## 2024-06-07 - 0.8.1 - Normalize and clean up the directory property in tsp-location.yaml. diff --git a/tools/tsp-client/package-lock.json b/tools/tsp-client/package-lock.json index c8d1ed0d3fc..a69da761b70 100644 --- a/tools/tsp-client/package-lock.json +++ b/tools/tsp-client/package-lock.json @@ -1,12 +1,12 @@ { "name": "@azure-tools/typespec-client-generator-cli", - "version": "0.8.1", + "version": "0.9.0", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "@azure-tools/typespec-client-generator-cli", - "version": "0.8.1", + "version": "0.9.0", "license": "MIT", "dependencies": { "@azure/core-rest-pipeline": "^1.12.0", @@ -725,12 +725,12 @@ } }, "node_modules/braces": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", - "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", + "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", "dev": true, "dependencies": { - "fill-range": "^7.0.1" + "fill-range": "^7.1.1" }, "engines": { "node": ">=8" @@ -1094,9 +1094,9 @@ } }, "node_modules/fill-range": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", - "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==", + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", + "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", "dev": true, "dependencies": { "to-regex-range": "^5.0.1" @@ -1152,6 +1152,20 @@ "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", "dev": true }, + "node_modules/fsevents": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", + "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", + "dev": true, + "hasInstallScript": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, "node_modules/get-caller-file": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", diff --git a/tools/tsp-client/package.json b/tools/tsp-client/package.json index 88bde429c99..1a2735add9d 100644 --- a/tools/tsp-client/package.json +++ b/tools/tsp-client/package.json @@ -1,6 +1,6 @@ { "name": "@azure-tools/typespec-client-generator-cli", - "version": "0.8.1", + "version": "0.9.0", "description": "A tool to generate Azure SDKs from TypeSpec", "main": "dist/index.js", "homepage": "https://github.com/Azure/azure-sdk-tools/tree/main/tools/tsp-client#readme", diff --git a/tools/tsp-client/src/index.ts b/tools/tsp-client/src/index.ts index 452e9969871..3fbb55f7f34 100644 --- a/tools/tsp-client/src/index.ts +++ b/tools/tsp-client/src/index.ts @@ -8,7 +8,7 @@ import { addSpecFiles, checkoutCommit, cloneRepo, getRepoRoot, sparseCheckout } import { doesFileExist } from "./network.js"; import { parse as parseYaml } from "yaml"; import { joinPaths, normalizePath, resolvePath } from "@typespec/compiler"; -import { formatAdditionalDirectories, getAdditionalDirectoryName, makeSparseSpecDir } from "./utils.js"; +import { formatAdditionalDirectories, getAdditionalDirectoryName, getServiceDir, makeSparseSpecDir } from "./utils.js"; import { resolve } from "node:path"; import { config as dotenvConfig } from "dotenv"; @@ -51,11 +51,7 @@ async function sdkInit( throw new Error(`tspconfig.yaml is empty at ${tspConfigPath}`); } const configYaml = parseYaml(data); - const serviceDir = configYaml?.parameters?.["service-dir"]?.default; - if (!serviceDir) { - throw new Error(`Parameter service-dir is not defined correctly in tspconfig.yaml. Please refer to https://github.com/Azure/azure-rest-api-specs/blob/main/specification/contosowidgetmanager/Contoso.WidgetManager/tspconfig.yaml for the right schema.`) - } - Logger.debug(`Service directory: ${serviceDir}`) + const serviceDir = getServiceDir(configYaml, emitter); const packageDir: string | undefined = configYaml?.options?.[emitter]?.["package-dir"]; if (!packageDir) { throw new Error(`Missing package-dir in ${emitter} options of tspconfig.yaml. Please refer to https://github.com/Azure/azure-rest-api-specs/blob/main/specification/contosowidgetmanager/Contoso.WidgetManager/tspconfig.yaml for the right schema.`); @@ -84,11 +80,7 @@ async function sdkInit( throw new Error(`tspconfig.yaml is empty at ${config}`); } const configYaml = parseYaml(data); - const serviceDir = configYaml?.parameters?.["service-dir"]?.default; - if (!serviceDir) { - throw new Error(`Parameter service-dir is not defined correctly in tspconfig.yaml. Please refer to https://github.com/Azure/azure-rest-api-specs/blob/main/specification/contosowidgetmanager/Contoso.WidgetManager/tspconfig.yaml for the right schema.`) - } - Logger.debug(`Service directory: ${serviceDir}`) + const serviceDir = getServiceDir(configYaml, emitter); const additionalDirOutput = formatAdditionalDirectories(configYaml?.parameters?.dependencies?.additionalDirectories); const packageDir = configYaml?.options?.[emitter]?.["package-dir"]; if (!packageDir) { diff --git a/tools/tsp-client/src/utils.ts b/tools/tsp-client/src/utils.ts index 7633d12aba5..f1d4b1add9b 100644 --- a/tools/tsp-client/src/utils.ts +++ b/tools/tsp-client/src/utils.ts @@ -1,6 +1,7 @@ import { joinPaths, normalizeSlashes } from "@typespec/compiler"; import { randomUUID } from "node:crypto"; import { mkdir } from "node:fs/promises"; +import { Logger } from "./log.js"; export function formatAdditionalDirectories(additionalDirectories?: string[]): string { let additionalDirOutput = ""; @@ -27,3 +28,14 @@ export async function makeSparseSpecDir(repoRoot: string): Promise { await mkdir(spareSpecPath, { recursive: true }); return spareSpecPath; } + +export function getServiceDir(configYaml: any, emitter: string): string { + // Check if service-dir is defined in the emitter specific configurations in tspconfig.yaml. + // Default to the top level service-dir parameter in tspconfig.yaml. + const serviceDir = configYaml?.options?.[emitter]?.["service-dir"] ?? configYaml?.parameters?.["service-dir"]?.default; + if (!serviceDir) { + throw new Error(`Parameter service-dir is not defined correctly in tspconfig.yaml. Please refer to https://github.com/Azure/azure-rest-api-specs/blob/main/specification/contosowidgetmanager/Contoso.WidgetManager/tspconfig.yaml for the right schema.`) + } + Logger.debug(`Service directory: ${serviceDir}`) + return serviceDir; +} diff --git a/tools/tsp-client/test/examples/tspconfig-custom-service-dir.yaml b/tools/tsp-client/test/examples/tspconfig-custom-service-dir.yaml new file mode 100644 index 00000000000..27f3ba21104 --- /dev/null +++ b/tools/tsp-client/test/examples/tspconfig-custom-service-dir.yaml @@ -0,0 +1,39 @@ +parameters: + "service-dir": + default: "sdk/contosowidgetmanager" + "dependencies": + "additionalDirectories": + - "specification/contosowidgetmanager/Contoso.WidgetManager.Shared/" + default: "" +emit: + - "@azure-tools/typespec-autorest" +linter: + extends: + - "@azure-tools/typespec-azure-rulesets/data-plane" +options: + "@azure-tools/typespec-autorest": + azure-resource-provider-folder: "data-plane" + emit-lro-options: "none" + emitter-output-dir: "{project-root}/.." + examples-directory: "examples" + output-file: "{azure-resource-provider-folder}/{service-name}/{version-status}/{version}/widgets.json" + "@azure-tools/typespec-python": + package-dir: "azure-contoso-widgetmanager" + package-name: "{package-dir}" + flavor: azure + "@azure-tools/typespec-csharp": + package-dir: "Azure.Template.Contoso" + clear-output-folder: true + model-namespace: false + namespace: "{package-dir}" + flavor: azure + "@azure-tools/typespec-ts": + service-dir: "sdk/contosowidgetmanager/widget" + package-dir: "contosowidgetmanager-rest" + packageDetails: + name: "@azure-rest/contoso-widgetmanager-rest" + flavor: azure + "@azure-tools/typespec-java": + package-dir: "azure-contoso-widgetmanager" + namespace: com.azure.contoso.widgetmanager + flavor: azure diff --git a/tools/tsp-client/test/utils.spec.ts b/tools/tsp-client/test/utils.spec.ts new file mode 100644 index 00000000000..cec517bc09a --- /dev/null +++ b/tools/tsp-client/test/utils.spec.ts @@ -0,0 +1,21 @@ +import { describe, it } from "node:test"; +import { getServiceDir } from "../src/utils.js"; +import { parse as parseYaml } from "yaml"; +import { assert } from "chai"; +import { readFile } from "node:fs/promises"; + +describe("get the right service dir from tspconfig.yaml", function () { + it("Get custom emitter service-dir", async function () { + const data = await readFile("./test/examples/tspconfig-custom-service-dir.yaml", "utf8"); + const configYaml = parseYaml(data); + const serviceDir = getServiceDir(configYaml, "@azure-tools/typespec-ts"); + assert.strictEqual(serviceDir, "sdk/contosowidgetmanager/widget"); + }); + + it("Get default service-dir", async function () { + const data = await readFile("./test/examples/tspconfig-custom-service-dir.yaml", "utf8"); + const configYaml = parseYaml(data); + const serviceDir = getServiceDir(configYaml, "@azure-tools/typespec-python"); + assert.strictEqual(serviceDir, "sdk/contosowidgetmanager"); + }); +});